Rails日志配置:将api/v1接口请求日志输出至api.log
api/v1 Request Logs to log/api.log in Rails Got it, let's get your api/v1 requests logging to a separate file instead of the default development.log. Here are two reliable, Rails-friendly ways to make this happen:
Method 1: Controller-Based Approach (Clean if you have an API base controller)
If all your v1 API controllers inherit from a shared base controller (like Api::V1::BaseController), this is the most straightforward method:
Set up your dedicated API logger in an initializer. Create
config/initializers/api_logger.rb:# Initialize a daily-rotated logger for API requests, matching default Rails log settings ApiLogger = ActiveSupport::Logger.new(Rails.root.join('log', 'api.log'), 'daily') ApiLogger.formatter = Rails.logger.formatter ApiLogger.level = Rails.logger.levelThis ensures the API log uses the same format and verbosity as your default logs, with daily rotation to keep file sizes manageable.
Override the logger in your API base controller (
app/controllers/api/v1/base_controller.rb):class Api::V1::BaseController < ApplicationController # Force all child controllers under Api::V1:: to use the custom API logger def logger ApiLogger end endAny controller that inherits from this base (like your
TestsController) will now log all requests tolog/api.log.
Method 2: Middleware-Based Approach (Works for any path-based routing)
If you don't have a shared API base controller, or want to target requests purely by their URL path, use a custom middleware:
Create the middleware file at
app/middleware/api_log_middleware.rb:class ApiLogMiddleware def initialize(app) @app = app @default_logger = Rails.logger # Initialize API logger with same settings as default @api_logger = ActiveSupport::Logger.new(Rails.root.join('log', 'api.log'), 'daily') @api_logger.formatter = @default_logger.formatter @api_logger.level = @default_logger.level end def call(env) # Swap logger if request starts with /api/v1 if env['PATH_INFO'].start_with?('/api/v1') Rails.logger = @api_logger end # Process the request as normal response = @app.call(env) # Restore default logger after request completes Rails.logger = @default_logger response end endRegister the middleware in
config/application.rb:module YourAppName class Application < Rails::Application # ... other existing configs ... # Insert before Rails' built-in logger middleware to ensure swap takes effect config.middleware.insert_before Rails::Rack::Logger, ApiLogMiddleware end end
Test It Out
After setting up either method:
- Restart your Rails server
- Send a request to your
v1/tests/testendpoint - Check
log/api.log—you’ll see the full request details there, and they won’t appear indevelopment.loganymore.
Quick Notes
- For production, you can adjust log rotation rules (like retention days) in the
ActiveSupport::Loggerinitialization. - If you use structured logging tools (like Lograge), update the
ApiLogger.formatterto match your preferred structure.
内容的提问来源于stack exchange,提问作者AnCo ngCo Danh Bun

