Structured Logging
Also Known As
JSON logging
structured logs PHP
Monolog JSON
log aggregation
TL;DR
Emitting log entries as machine-parseable key-value pairs (JSON) rather than free-form strings — enabling filtering, aggregation, and alerting.
Explanation
Structured logs include consistent fields: timestamp, level, message, request_id, user_id, duration_ms, context. JSON is the de facto format for structured logs. Tools like Elasticsearch, Datadog, and CloudWatch Logs Insights can query structured logs efficiently. PHP libraries: Monolog with JsonFormatter. Correlation IDs (request_id) thread a single request across all log entries — essential for debugging distributed systems. Never log PII (email, password, credit card) in plain text.
Common Misconception
✗ Log messages are for humans only. At scale, no human reads individual log lines — logs are ingested by tools that need consistent, parseable fields to surface patterns and alerts.
Why It Matters
Free-form log strings require regex parsing to extract meaning — brittle and slow at scale. Structured logs are queryable immediately: 'show all requests where duration_ms > 1000 and user_id = 42'.
Common Mistakes
- Logging PII (email addresses, passwords, tokens) in plain text — creates compliance and security risk.
- Not including a correlation/request ID — impossible to trace a single request across multiple log entries.
- Using different field names for the same concept across services — breaks cross-service log queries.
Avoid When
- Never log sensitive values — passwords, tokens, credit card numbers, or full request bodies.
- Do not use structured logging as a debugging dump during development — use a debugger instead.
When To Use
- Use structured logging in any application that runs in production — log aggregation tools require it.
- Include a correlation ID on every log entry to trace a single request across multiple services.
Code Examples
✗ Vulnerable
// Unstructured — impossible to query reliably
error_log("User $userId logged in from {$_SERVER['REMOTE_ADDR']} in {$elapsed}ms");
✓ Fixed
use Monolog\Logger;
use Monolog\Handler\StreamHandler;
use Monolog\Formatter\JsonFormatter;
$log = new Logger('app');
$handler = new StreamHandler('php://stdout');
$handler->setFormatter(new JsonFormatter());
$log->pushHandler($handler);
// Structured context — every field is queryable
$log->info('User login', [
'user_id' => $userId,
'ip' => $request->ip(),
'request_id' => $requestId,
'duration_ms'=> $elapsed,
]);
References
Tags
🤝 Adopt this term
£79/year · your link shown here
Added
31 Mar 2026
Views
27
🤖 AI Guestbook educational data only
|
|
Last 30 days
Agents 0
No pings yet today
No pings yesterday
Perplexity 9
Amazonbot 6
Ahrefs 2
Unknown AI 2
Also referenced
How they use it
crawler 19
Related categories
⚡
DEV INTEL
Tools & Severity
⚙ Fix effort: Low
⚡ Quick Fix
Use Monolog with JsonFormatter and include request_id in every log entry via a processor
📦 Applies To
PHP 8.0+
web
cli
queue-worker
🔍 Detection Hints
error_log() with string interpolation instead of Monolog/structured logger
Auto-detectable:
✓ Yes
phpstan
⚠ Related Problems
🤖 AI Agent
Confidence: Medium
False Positives: Medium
✗ Manual fix
Fix: Medium
Context: File