Weave Code
Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Zabbix Sender Laravel Package

okitsu/zabbix-sender

PHP/Laravel package for sending metrics to Zabbix trapper items using the zabbix_sender protocol. Define host and key values, then push them from your app through a simple API to feed custom monitoring data into Zabbix dashboards, triggers, and alerts. Ideal for app-level telemetry and health checks...

View on GitHub
Deep Wiki
Context7

Getting Started

The package is a thin, framework-agnostic implementation of the Zabbix sender protocol plus a parser for zabbix_agentd.conf. It ships no Laravel service provider, facade, or config file, so the first hour of work is wiring it in the way you want it.

composer require okitsu/zabbix-sender

Two classes matter. Read them first:

  • Zabbix\Sender — opens a TCP socket to the Zabbix server/trapper port (default 10051) and writes the sender protocol frame.
  • Zabbix\AgentConfig — parses an agent config file so you can reuse Server=, Hostname=, ServerActive= instead of duplicating them in .env.

Minimal first call:

use Zabbix\Sender;

$sender = new Sender('zabbix.internal', 10051);
$sender->send('web-01', 'app.orders.count', 42);

Before that call works, the Zabbix side must exist: a host whose name exactly matches the first argument, and an item of type Zabbix trapper with the key you used (app.orders.count). Trapper items do not poll — nothing arrives until your app pushes, and a wrong key/host silently drops the value with only a server-side log line.

The first genuinely useful use case for a Laravel app is business/queue metrics that the stock agent cannot see: app.queue.pending, app.orders.created, app.payments.failed, app.http.p95. These are one-liners:

app(Sender::class)->send(config('zabbix.host'), 'app.queue.pending', Queue::size());

Ship that, confirm it lands in Latest data in the Zabbix UI, and only then build the plumbing below.

Implementation Patterns

Bind a singleton with a small config file. Sender is stateless per call, but a singleton avoids re-reading config and keeps the facade ergonomic.

// config/zabbix.php
return [
    'server'    => env('ZABBIX_SERVER', '127.0.0.1'),
    'port'      => (int) env('ZABBIX_PORT', 10051),
    'host'      => env('ZABBIX_HOST', gethostname()),
    'timeout'   => (int) env('ZABBIX_TIMEOUT', 2),
    'enabled'   => (bool) env('ZABBIX_ENABLED', true),
];
// app/Providers/ZabbixServiceProvider.php
public function register(): void
{
    $this->mergeConfigFrom(__DIR__.'/../../config/zabbix.php', 'zabbix');

    $this->app->singleton(Sender::class, fn ($app) => new Sender(
        $app['config']->get('zabbix.server'),
        $app['config']->get('zabbix.port'),
    ));
}

Wrap it in your own class — do not inject Zabbix\Sender directly into controllers. This is the single most important pattern given the package's maturity (36 stars, zero dependents). A ZabbixMetrics service with gauge(string $key, int|float|string $value) lets you swap implementations, add the enabled kill switch, and centralise the try/catch.

Batch aggressively. Every send() is a synchronous TCP round-trip. For a dashboard-load or a batch job, use the multi-item form so all values travel in one frame:

$this->sender->sendMulti($host, [
    'app.orders.created' => 12,
    'app.orders.failed'  => 1,
    'app.orders.p95'     => 0.42,
]);

Push non-critical metrics off the request path. A queue job is the right home for anything measured in a request but not needed inline:

class SendZabbixMetric implements ShouldQueue
{
    use Dispatchable, Queueable;

    public function __construct(public string $key, public mixed $value) {}

    public function handle(Sender $sender): void
    {
        $sender->send(config('zabbix.host'), $this->key, $this->value);
    }
}

Bound the job with $tries = 1 and $timeout — a metrics job that retries five times against an unreachable Zabbix server is worse than a lost datapoint.

Use middleware for latency percentiles only if you are sampling. Measuring every request and sending every request will double your outbound connections under load. Aggregate in Redis (INCRBY/HINCRBY) and flush from the scheduler.

Drive everything from the scheduler for periodic metrics. Kernel::schedule() + ->everyFiveMinutes() calling a command that reads queue depth, cache hit ratio, stale-record counts, and sends them in one sendMulti is the highest-value, lowest-risk integration.

Use AgentConfig for host identity in containerised/VM environments where the agent is already installed and configured. Parsing zabbix_agentd.conf for Hostname= avoids the classic "I set ZABBIX_HOST wrong and my values went to /dev/null on the server" failure. Fall back to gethostname() when the file is absent.

Wire it into the exception handler for a app.exceptions.total counter — but only the counter, never the exception payload; trapper text values are length-limited and you do not want stack traces on the wire.

Gotchas and Tips

  • Failures are exceptions, and they will bite you in render(). Any network hiccup throws. Always wrap calls in try/catch (\Throwable) inside your wrapper and Log::warning — never let a metrics push 500 a user request.
  • Host name is exact-match. web-01 and web-01.domain.local are different hosts to Zabbix. This is the #1 cause of "the data isn't showing up." Cross-check against Configuration → Hosts before debugging code.
  • Item type must be Zabbix trapper. Sending to an active-agent or SNMP item produces nothing useful. Likewise, the value type (Numeric (unsigned), Numeric (float), Text, Log) must match what you send, or the server rejects the value.
  • Timestamps and clock skew. The sender protocol carries a timestamp; if app containers drift relative to the Zabbix server, points can be dropped or plotted in the wrong bucket. Run NTP; don't hand-roll timestamps unless you need backfill.
  • No TLS, no auth. The sender protocol is plaintext with no authentication. Only use it over a trusted network/VPC, and never expose port 10051 publicly.
  • AgentConfig and Include= directives. Real-world zabbix_agentd.conf files often split settings into included files. If Hostname comes back empty, check whether it lives in an include rather than the main file — verify by reading the file yourself before assuming the parser is broken.
  • Debugging is easier with the reference tool. When a push "succeeds" but nothing appears, run zabbix_sender -z <server> -s <host> -k <key> -o <value> -vv from the same machine. If that works, your code is wrong; if it doesn't, your Zabbix config is wrong. Don't debug both at once.
  • Maintenance risk is real. Zero dependents and a low star count mean no security review pipeline and no guarantee of PHP-version support. Pin the version in composer.json, and keep ZabbixMetrics as an interface so replacing the transport (there are several alternative sender implementations) is a one-file change.
  • Kill switch is mandatory. A ZABBIX_ENABLED=false env var that short-circuits your wrapper is what stops a Zabbix outage from becoming an application outage during an incident.
  • Extension point: if you need retry/backoff, batching across requests, or a dry-run mode for local dev, subclass Sender or (better) implement it in your wrapper rather than forking the package.
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
htinlynn/genius-helper
maco-studios/hephaestus
elmogy/larafast
xeviant/laravel-paystack
gorilladash/laravel-website-sdk
martialbe/flysystem-oss
chondal/3312client
jeroen-g/flickr
opscale-co/nova-genbi
itsjustvita/laravel-retention
tequilarapido/trackit
gregsphotography/site-builder-filament
cabaoctavio/laravel-query-log
gregsphotography/site-builder-components
io-digital/clickatell
snowsoft/laravel-admin
oxygen/auth
relicsoftware/barakah-payment-gateway
tobya/work-with-composer
equipc/laravel-email-validator