When debugging API responses or troubleshooting web applications, developers often need to inspect the actual response body sent by the server. While Nginx's access log is excellent for logging request details, it doesn't natively include response body content.
The default Nginx access_log
directive captures:
- Client IP address - Request time - HTTP method - Request URI - Status code - Response size - Referrer - User agent
But crucially, it omits the actual response content, which can be critical for debugging JSON APIs, error messages, or custom headers.
The most effective approach is to use Nginx's Lua module (ngx_http_lua_module) to capture and log response bodies:
http { lua_package_path "/path/to/lua/scripts/?.lua;;"; log_format response_body '$remote_addr - $remote_user [$time_local] ' '"$request" $status $body_bytes_sent ' '"$http_referer" "$http_user_agent" "$resp_body"'; server { location / { access_log /var/log/nginx/access-with-body.log response_body; # Capture response body set $resp_body ""; body_filter_by_lua ' local resp_body = string.sub(ngx.arg[1], 1, 1000) ngx.ctx.buffered = (ngx.ctx.buffered or "") .. resp_body if ngx.arg[2] then ngx.var.resp_body = ngx.ctx.buffered end '; } } }
1. Performance Impact: Logging response bodies significantly increases I/O operations
2. Security: Never use this in production for sensitive data
3. Size Limits: The example above limits to 1000 characters to prevent log bloating
For production debugging, consider creating a dedicated logging endpoint:
location /debug-logger { internal; content_by_lua ' local cjson = require "cjson" ngx.req.read_body() local args = ngx.req.get_post_args() ngx.log(ngx.INFO, "Response: ", cjson.encode(args)) ngx.exit(204) '; } location /api { proxy_pass http://backend; post_action /debug-logger; }
After implementing either solution, verify with:
tail -f /var/log/nginx/access-with-body.log curl http://localhost/api/test
Remember to remove response body logging before deploying to production environments, as it may expose sensitive information and impact performance.
When debugging web applications, developers often need to inspect the actual response body being served by Nginx. While the access logs naturally capture request data and response headers, logging the response body requires special configuration.
Nginx doesn't provide built-in variables for response body logging, but we can implement workarounds:
# Option 1: Use Lua module (requires ngx_http_lua_module)
location /debug {
log_subrequest on;
access_log /var/log/nginx/response.log custom_format;
content_by_lua_block {
ngx.log(ngx.INFO, "Response: ", ngx.arg[1])
ngx.say("Your response data")
}
}
For static content, you can inject logging via sub_filter:
server {
sub_filter '