fix(#12): Implement structured logging with request correlation and security event marking
Some checks are pending
Docker Test / test (push) Waiting to run
Some checks are pending
Docker Test / test (push) Waiting to run
This commit is contained in:
parent
32480438c7
commit
0679332c77
3 changed files with 77 additions and 2 deletions
51
backend/middleware/logger.js
Normal file
51
backend/middleware/logger.js
Normal file
|
|
@ -0,0 +1,51 @@
|
|||
const { format, createLogger, transports } = require('winston');
|
||||
|
||||
const logger = createLogger({
|
||||
format: format.combine(
|
||||
format.timestamp(),
|
||||
format.json()
|
||||
),
|
||||
transports: [
|
||||
new transports.Console()
|
||||
]
|
||||
});
|
||||
|
||||
// Middleware to generate a unique request ID
|
||||
const requestId = (req, res, next) => {
|
||||
req.id = `${Date.now()}-${Math.random().toString(36).substr(2, 9)}`;
|
||||
next();
|
||||
};
|
||||
|
||||
// Middleware to log requests
|
||||
const requestLogger = (req, res, next) => {
|
||||
logger.info({
|
||||
timestamp: new Date().toISOString(),
|
||||
method: req.method,
|
||||
url: req.url,
|
||||
requestId: req.id
|
||||
});
|
||||
next();
|
||||
};
|
||||
|
||||
// Middleware to log errors
|
||||
const errorLogger = (err, req, res, next) => {
|
||||
const isSecurityEvent = err.message.includes('Authentication') ||
|
||||
err.message.includes('Authorization') ||
|
||||
err.message.includes('Security');
|
||||
const level = isSecurityEvent ? 'security' : 'error';
|
||||
|
||||
logger[level]({
|
||||
timestamp: new Date().toISOString(),
|
||||
error: err.message,
|
||||
stack: err.stack,
|
||||
requestId: req.id,
|
||||
route: req.route ? req.route.path : req.path
|
||||
});
|
||||
next(err);
|
||||
};
|
||||
|
||||
module.exports = {
|
||||
requestId,
|
||||
requestLogger,
|
||||
errorLogger
|
||||
};
|
||||
|
|
@ -5,7 +5,8 @@ function logger(req, res, next) {
|
|||
method: req.method,
|
||||
url: req.url,
|
||||
requestId: req.requestId,
|
||||
level: 'info'
|
||||
level: 'info',
|
||||
route: req.route ? req.route.path : 'unknown'
|
||||
}));
|
||||
res.on('finish', () => {
|
||||
const securityEvent = [401, 403].includes(res.statusCode);
|
||||
|
|
@ -16,7 +17,8 @@ function logger(req, res, next) {
|
|||
status: res.statusCode,
|
||||
requestId: req.requestId,
|
||||
level: res.statusCode >= 400 ? 'error' : 'info',
|
||||
securityEvent: securityEvent
|
||||
securityEvent: securityEvent,
|
||||
route: req.route ? req.route.path : 'unknown'
|
||||
}));
|
||||
});
|
||||
next();
|
||||
|
|
|
|||
22
docs/adr/structured-logging.md
Normal file
22
docs/adr/structured-logging.md
Normal file
|
|
@ -0,0 +1,22 @@
|
|||
# Structured Logging
|
||||
|
||||
## Status
|
||||
|
||||
Accepted
|
||||
|
||||
## Context
|
||||
|
||||
For operational debugging, structured logs are needed for API errors and security events. This includes timestamps, log levels, request IDs, and routes.
|
||||
|
||||
## Decision
|
||||
|
||||
We implement a centralized logging middleware that:
|
||||
1. Logs all requests with timestamp, method, URL, request ID, and route
|
||||
2. Logs error responses with correlation via request ID
|
||||
3. Marks security-relevant events (401, 403) separately
|
||||
|
||||
## Consequences
|
||||
|
||||
- Logs are structured and filterable
|
||||
- Security events can be easily identified
|
||||
- Debugging is improved through correlation of requests and errors
|
||||
Loading…
Add table
Add a link
Reference in a new issue