PHPackages                             phel-lang/phel-log - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Logging &amp; Monitoring](/categories/logging)
4. /
5. phel-lang/phel-log

ActiveLibrary[Logging &amp; Monitoring](/categories/logging)

phel-lang/phel-log
==================

Data-driven logging library for Phel Lang. Inspired by Timbre + Monolog. Levels, namespace filtering, pluggable appenders, PSR-3 adapter, Monolog handler bridge.

v0.1.0(3w ago)51MITShellPHP &gt;=8.4CI passing

Since May 16Pushed 1w agoCompare

[ Source](https://github.com/phel-lang/phel-log)[ Packagist](https://packagist.org/packages/phel-lang/phel-log)[ Docs](https://phel-lang.org/)[ Fund](https://chemaclass.com/sponsor)[ RSS](/packages/phel-lang-phel-log/feed)WikiDiscussions main Synced 1w ago

READMEChangelog (1)Dependencies (3)Versions (2)Used By (0)

phel-log
========

[](#phel-log)

Data-driven logging library for [Phel Lang](https://phel-lang.org/). Inspired by [Timbre](https://github.com/taoensso/timbre) (Clojure) and [Monolog](https://github.com/Seldaek/monolog) (PHP).

- Pure-data config: one map, swap it at runtime.
- Levels with namespace + per-appender filters.
- Pluggable appenders: console, file, in-memory, Monolog handler bridge.
- Pluggable formatters: line, JSON, custom fn.
- Processors (middleware) for masking / enriching events.
- PSR-3 `LoggerInterface` adapter for Symfony / Laravel / Slim interop.

```
(ns my-app.users
  (:require phel.log :as log))

(log/info "user logged in" {:user-id 42})
;; 2026-05-16T10:21:33.123Z [INFO ] my-app.users - user logged in array (...)

```

Install
-------

[](#install)

```
composer require phel-lang/phel-log
```

Requires PHP 8.4+ and `phel-lang/phel-lang` 0.37+. Optional: `monolog/monolog` 3.x for the Monolog handler bridge.

Configure
---------

[](#configure)

```
(log/set-config!
  {:min-level :debug
   :appenders [(log/console-appender)
               (log/file-appender {:path "/var/log/my-app.log"
                                   :formatter :json
                                   :min-level :warn})]
   :ns-filter {:allow ["my-app.**"]
               :deny  ["my-app.noisy.**"]}
   :processors [(fn [ev] (assoc ev :data (merge (:data ev) {:trace-id (request-id)})))]
   :base-data  {:app "my-app" :env "prod"}})

```

Levels
------

[](#levels)

`:trace` -&gt; `:debug` -&gt; `:info` -&gt; `:warn` -&gt; `:error` -&gt; `:fatal` -&gt; `:report`

Each level has a macro: `log/trace`, `log/debug`, ..., `log/report`. The call-site namespace is captured at macro-expand time, no extra plumbing.

```
(log/debug "raw payload" {:body request-body})
(log/error "failed to charge card" {:order-id 7 :error e})
(log/report "deployment finished" {:sha "abc123"})  ; always loud

```

Appenders
---------

[](#appenders)

AppenderPurpose`console-appender`stdout for info-, stderr for warn+`file-appender`append-only, lock-on-write`memory-appender`capture events into an atom (tests / REPL)`monolog-appender`bridge any `Monolog\Handler\HandlerInterface`All appenders share the same shape:

```
{:name      :my-appender
 :min-level :warn          ; optional, per-appender override
 :formatter :line          ; or :json, or (fn [event] string)
 :write!    (fn [event line] ...)}

```

Write your own by returning a map of the same shape; everything in `log/write-event!` is data-driven.

Formatters
----------

[](#formatters)

- `:line` - human one-liner (timestamp, level, ns, message, data).
- `:json` - one JSON object per line; pipe straight into Loki / ELK / CloudWatch.
- `(fn [event] string)` - anything you want; the event is a plain map.

```
{:level :info
 :ns "my-app.users"
 :time-ms 1715846400123
 :message "user logged in"
 :data {:user-id 42}
 :error nil}

```

Monolog handler bridge
----------------------

[](#monolog-handler-bridge)

Re-use every existing Monolog handler (Slack, Sentry, Syslog, RotatingFile, ...):

```
(let [slack (php/new \Monolog\Handler\SlackWebhookHandler
                     webhook-url
                     "#alerts"
                     "phel-bot"
                     true
                     nil
                     false
                     false
                     (php/-> \Monolog\Level (Error)))]
  (log/update-config!
    {:appenders [(log/console-appender)
                 (log/monolog-appender {:handler slack
                                        :channel "my-app"
                                        :min-level :error})]}))

```

PSR-3 adapter
-------------

[](#psr-3-adapter)

Drop the Phel logger into a PSR-3-aware PHP framework:

```
use Phel\PhelLog\PsrLogger;

$dispatcher = static function (string $level, string $message, array $ctx): void {
    \Phel::run('my-bootstrap', 'log-from-psr', $level, $message, $ctx);
};

$logger = new PsrLogger($dispatcher, channel: 'symfony');
$container->set(\Psr\Log\LoggerInterface::class, $logger);
```

Docs
----

[](#docs)

Full index at [`docs/README.md`](docs/README.md) — start with [Quickstart](docs/quickstart.md), then [Config](docs/config.md) / [Appenders](docs/appenders.md). Integrations: [Monolog bridge](docs/monolog-bridge.md), [PSR-3](docs/psr3.md).

Contributing
------------

[](#contributing)

Run tests:

```
composer test
```

Conventional commits, PR template in `.github/PULL_REQUEST_TEMPLATE.md`.

###  Health Score

40

—

FairBetter than 86% of packages

Maintenance97

Actively maintained with recent releases

Popularity7

Limited adoption so far

Community6

Small or concentrated contributor base

Maturity41

Maturing project, gaining track record

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Unknown

Total

1

Last Release

24d ago

### Community

Maintainers

![](https://www.gravatar.com/avatar/3d166420c6770c5941e10bd68b2d26501eabb432e280d8e6eba0a344bcc1e5ae?d=identicon)[Chemaclass](/maintainers/Chemaclass)

---

Top Contributors

[![Chemaclass](https://avatars.githubusercontent.com/u/5256287?v=4)](https://github.com/Chemaclass "Chemaclass (21 commits)")

---

Tags

lisplogloggerloggingmonologphelphel-langphpphp-librarypsr-3psr-logtimbrepsr-3loggingloggermonologlisppheltimbre

### Embed Badge

![Health badge](/badges/phel-lang-phel-log/health.svg)

```
[![Health](https://phpackages.com/badges/phel-lang-phel-log/health.svg)](https://phpackages.com/packages/phel-lang-phel-log)
```

###  Alternatives

[inpsyde/wonolog

Monolog-based logging package for WordPress.

184631.3k7](/packages/inpsyde-wonolog)[analog/analog

Fast, flexible, easy PSR-3-compatible PHP logging package with dozens of handlers.

3511.6M24](/packages/analog-analog)[apix/log

Minimalist, thin and fast PSR-3 compliant (multi-bucket) logger.

521.1M20](/packages/apix-log)[markrogoyski/simplelog-php

Powerful PSR-3 logging. So easy, it's simple.

2819.1k4](/packages/markrogoyski-simplelog-php)[atrapalo/monolog-elasticsearch

A Monolog handler and formatter that makes use of the elasticsearch/elasticsearch package

1123.0k](/packages/atrapalo-monolog-elasticsearch)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
