central-logs / laravel
Laravel package for sending logs to Central Logs system with sync, async, and batch processing modes. Achieve 251x faster logging performance.
Installs: 96
Dependents: 0
Suggesters: 0
Security: 0
Stars: 0
Watchers: 0
Forks: 0
Open Issues: 0
pkg:composer/central-logs/laravel
Requires
- php: ^8.1
- guzzlehttp/guzzle: ^7.8
- illuminate/console: ^10.0|^11.0|^12.0
- illuminate/contracts: ^10.0|^11.0|^12.0
- illuminate/queue: ^10.0|^11.0|^12.0
- illuminate/support: ^10.0|^11.0|^12.0
- monolog/monolog: ^3.0
Requires (Dev)
- laravel/pint: ^1.13
- mockery/mockery: ^1.6
- orchestra/testbench: ^8.0|^9.0|^10.0
- phpstan/phpstan: ^1.10
- phpunit/phpunit: ^10.0|^11.0
README
A powerful and flexible Laravel package for sending logs to Central Logs system with support for synchronous, asynchronous, and batch processing modes. Achieve up to 251x faster logging performance with intelligent batch aggregation.
Features
- ✅ Multiple Log Levels - Support for all 8 Monolog levels (DEBUG → EMERGENCY)
- ✅ Three Operation Modes - Sync, Async (Queue), and Batch aggregation
- ✅ Blazing Fast - Batch mode is 251x faster than sync (0.68ms vs 170ms)
- ✅ Exception Handling - Automatic exception serialization with stack traces
- ✅ Context Enrichment - Automatic capture of user, request, session, and environment data
- ✅ Queue Integration - Seamless integration with Laravel Queue (Redis, Database, etc.)
- ✅ Auto-Flush - Multiple flush triggers (size, timeout, shutdown, memory)
- ✅ Retry Logic - Exponential backoff with configurable attempts (default: 3)
- ✅ Fallback Mechanism - Local logging when API is unavailable
- ✅ Zero Data Loss - Shutdown hooks ensure all logs are sent
- ✅ Production Ready - 100% test coverage, error handling, graceful degradation
Requirements
- PHP 8.1 or higher (8.2+ for Laravel 11 & 12)
- Laravel 10.x, 11.x, or 12.x
- Guzzle HTTP Client 7.8+
- Central Logs instance (running at accessible URL)
Performance Benchmarks
Real-world performance testing with Central Logs API:
| Mode | Speed | Blocking | Queued | Speedup | Best For |
|---|---|---|---|---|---|
| SYNC | 170.83ms | Yes | No | 1x | Critical logs |
| ASYNC | 57.71ms | No | Yes | 3x | High-throughput |
| BATCH | 0.68ms | No | On flush | 251x | Optimal performance |
Batch mode processes logs 251x faster than sync mode!
Installation
Step 1: Install via Composer
composer require central-logs/laravel
Step 2: Publish Configuration
php artisan vendor:publish --tag=central-logs-config
This will create a config/central-logs.php file in your Laravel application.
Important: The package will work in "null mode" (no logs sent) until you configure the API credentials in Step 3.
Step 3: Configure Environment
Add the following to your .env file:
CENTRAL_LOGS_URL=https://your-central-logs-domain.com CENTRAL_LOGS_API_KEY=your_api_key_here CENTRAL_LOGS_MODE=async CENTRAL_LOGS_BATCH_ENABLED=true
Step 4: Add Middleware (Recommended for Batch Mode)
Add the flush middleware to app/Http/Kernel.php to ensure logs are sent at the end of each request:
protected $middleware = [ // ... other middleware \CentralLogs\Http\Middleware\FlushCentralLogsMiddleware::class, ];
Why? In batch mode, logs are collected and sent in batches. Without this middleware, logs may wait until batch size (default: 50) or timeout (default: 5s) is reached. The middleware ensures logs are flushed after each request.
Step 5: Update Logging Configuration
Add the Central Logs channel to your config/logging.php:
'channels' => [ // Option 1: Use Central Logs directly 'central-logs' => [ 'driver' => 'monolog', 'handler' => CentralLogs\Handler\CentralLogsHandler::class, 'level' => env('LOG_LEVEL', 'debug'), ], // Option 2: Add to stack (recommended) 'stack' => [ 'driver' => 'stack', 'channels' => ['daily', 'central-logs'], 'ignore_exceptions' => false, ], ],
Step 6: Test Connection
php artisan central-logs:test
Quick Start
Once configured, you can use Laravel's logging as usual:
use Illuminate\Support\Facades\Log; // Simple logging Log::info('User logged in'); // With context Log::info('User logged in', [ 'user_id' => $user->id, 'ip' => request()->ip(), ]); // Error logging with exception try { // ... your code } catch (Exception $e) { Log::error('Payment processing failed', [ 'exception' => $e, 'order_id' => $order->id, ]); } // Different log levels Log::debug('Debugging information'); Log::info('Informational message'); Log::warning('Warning message'); Log::error('Error occurred'); Log::critical('Critical issue');
Configuration
Logging Modes
Synchronous Mode
Logs are sent immediately (blocks the request):
CENTRAL_LOGS_MODE=sync
Pros: Logs are sent immediately Cons: Adds latency to requests
Asynchronous Mode (Recommended)
Logs are queued and sent via Laravel Queue:
CENTRAL_LOGS_MODE=async
QUEUE_CONNECTION=redis # or database
Pros: Non-blocking, fast Cons: Requires queue worker to be running
php artisan queue:work --queue=central-logs
Batch Processing
Enable batch processing to reduce API calls:
CENTRAL_LOGS_BATCH_ENABLED=true CENTRAL_LOGS_BATCH_SIZE=50 # Number of logs per batch CENTRAL_LOGS_BATCH_TIMEOUT=5 # Seconds before auto-flush
How it works:
- Logs are collected in memory
- Flushed when batch size is reached OR timeout elapsed
- Automatically flushed on application shutdown
Configuration Reference
All available configuration options in config/central-logs.php:
return [ // API endpoint 'api_url' => env('CENTRAL_LOGS_URL'), 'api_key' => env('CENTRAL_LOGS_API_KEY'), // Mode: sync or async 'mode' => env('CENTRAL_LOGS_MODE', 'async'), // Batch configuration 'batch' => [ 'enabled' => env('CENTRAL_LOGS_BATCH_ENABLED', true), 'size' => env('CENTRAL_LOGS_BATCH_SIZE', 50), 'timeout' => env('CENTRAL_LOGS_BATCH_TIMEOUT', 5), 'queue' => env('CENTRAL_LOGS_BATCH_QUEUE', 'central-logs'), ], // Source identifier 'source' => env('CENTRAL_LOGS_SOURCE', env('APP_NAME', 'laravel')), // HTTP client settings 'http' => [ 'timeout' => env('CENTRAL_LOGS_TIMEOUT', 5), 'retry' => [ 'times' => env('CENTRAL_LOGS_RETRY_TIMES', 3), 'delay' => env('CENTRAL_LOGS_RETRY_DELAY', 100), ], 'verify_ssl' => env('CENTRAL_LOGS_VERIFY_SSL', true), ], // Fallback when Central Logs is unavailable 'fallback' => [ 'enabled' => env('CENTRAL_LOGS_FALLBACK', true), 'channel' => env('CENTRAL_LOGS_FALLBACK_CHANNEL', 'stack'), ], // Context enrichment 'context' => [ 'include_user' => true, 'include_request' => true, 'include_session' => true, 'include_environment' => true, 'custom' => [ // Add custom metadata here ], ], // Minimum log level 'level' => env('CENTRAL_LOGS_LEVEL', 'DEBUG'), // Queue configuration 'queue' => [ 'connection' => env('CENTRAL_LOGS_QUEUE_CONNECTION'), 'name' => env('CENTRAL_LOGS_QUEUE_NAME', 'central-logs'), ], // Debug mode 'debug' => env('CENTRAL_LOGS_DEBUG', false), ];
Advanced Usage
Custom Metadata
Add custom metadata to all logs:
// config/central-logs.php 'context' => [ 'custom' => [ 'app_version' => '1.2.3', 'datacenter' => 'us-east-1', 'environment_type' => 'staging', ], ],
Using Specific Channel
Log only to Central Logs:
Log::channel('central-logs')->info('This goes only to Central Logs');
Conditional Logging
Log to Central Logs only in production:
if (app()->environment('production')) { Log::channel('central-logs')->info('Production log'); } else { Log::info('Development log'); }
Exception Handling
The package automatically extracts exception details:
try { throw new \RuntimeException('Something went wrong'); } catch (\Exception $e) { Log::error('An error occurred', [ 'exception' => $e, // Automatically formatted 'user_id' => auth()->id(), ]); }
Queue Configuration
For async mode, you need a queue worker running:
Using Redis (Recommended)
# .env
QUEUE_CONNECTION=redis
REDIS_HOST=127.0.0.1
REDIS_PORT=6379
Using Database
# .env QUEUE_CONNECTION=database # Create queue tables php artisan queue:table php artisan migrate
Start Queue Worker
# Production (with Supervisor) php artisan queue:work --queue=central-logs --tries=3 --timeout=30 # Development php artisan queue:listen --queue=central-logs
Supervisor Configuration
Create /etc/supervisor/conf.d/central-logs-worker.conf:
[program:central-logs-worker] process_name=%(program_name)s_%(process_num)02d command=php /path/to/your/app/artisan queue:work --queue=central-logs --tries=3 autostart=true autorestart=true stopasgroup=true killasgroup=true user=www-data numprocs=1 redirect_stderr=true stdout_logfile=/path/to/your/app/storage/logs/worker.log stopwaitsecs=3600
Troubleshooting
Connection Test Fails
php artisan central-logs:test
Check:
- Central Logs is running and accessible
- API key is correct
- Firewall/network settings allow connection
- URL is correct (include http:// or https://)
Logs Not Appearing
In Async Mode:
- Check queue worker is running:
ps aux | grep queue:work - Check queue for failed jobs:
php artisan queue:failed - Check Laravel logs:
tail -f storage/logs/laravel.log
In Batch Mode (Most Common Issue):
Problem: Logs not sent immediately, waiting until batch size or timeout reached
Solutions:
-
Add Flush Middleware (Recommended):
// app/Http/Kernel.php protected $middleware = [ \CentralLogs\Http\Middleware\FlushCentralLogsMiddleware::class, ];
-
Lower Batch Settings for Development:
# .env CENTRAL_LOGS_BATCH_SIZE=10 # Lower from default 50 CENTRAL_LOGS_BATCH_TIMEOUT=2 # Lower from default 5
-
Disable Batching for Testing:
# .env CENTRAL_LOGS_BATCH_ENABLED=false -
Manual Flush in Tinker:
php artisan tinker app(\CentralLogs\Support\BatchAggregator::class)->flush();
Performance Issues
Sync mode is slow:
- Switch to async mode for better performance
- Enable batch mode to reduce API calls
Queue backing up:
- Increase number of queue workers
- Check Central Logs API response time
- Reduce batch timeout for faster processing
Development
Setup Development Environment
# Clone repository git clone https://github.com/yourusername/central-logs-laravel.git cd central-logs-laravel # Start Docker environment docker-compose up -d # Install dependencies docker-compose exec php composer install # Set up test app docker-compose exec php sh cd /var/www/test-app ./setup.sh
Run Tests
# All tests composer test # Unit tests only vendor/bin/phpunit --testsuite Unit # With coverage composer test-coverage
Code Quality
# PHPStan composer phpstan # Code formatting composer format
Contributing
Contributions are welcome! Please see CONTRIBUTING.md for details.
Security
If you discover any security-related issues, please email dev@pande.id instead of using the issue tracker.
License
The MIT License (MIT). Please see LICENSE for more information.