Rack

Integrate Timber with Rack

The Timber Rails integration requires installation of the base timber Ruby gem first. Additionally, if your application is a Rails app please see the Rails integration which includes the Rack integration.

Timber integrates with Rack through the timber_rack Ruby gem which captures useful context and metadata, turning your Rack logs into rich structured events.

Installation

  1. In your Gemfile, add the timber-rack gem:

    Gemfile
    gem 'timber-rack', '~> 1.0'
  2. In your shell run bundle install

  3. Install the Rack middleware:

    use Timber::Integrations::Rack::HTTPContext
    use Timber::Integrations::Rack::UserContext
    use Timber::Integrations::Rack::HTTPEvents
    use Timber::Integrations::Rack::ErrorEvent

Configuration

collapse_into_single_event

If you're a fan of lograge, you'll appreciate this setting which reduces the HTTP log events into a single event.

config/initializers/timber.rb
Timber.config.integrations.rack.http_events.collapse_into_single_event = true

It turns this:

Started GET "/"
Completed 200 OK in 1.2ms

Into this:

GET / completed with 200 OK in 1.2ms

silence_request

Silencing noisy requests can be helpful for silencing load balance health checks, bot scanning, or activity that generally is not meaningful to you. The following will silence all [GET] /_health requests:

Timber.config.integrations.rack.http_events.silence_request = lambda do |rack_env, rack_request|
rack_request.path == "/_health"
end

We require a block because it gives you complete control over how you want to silence requests. The first parameter being the traditional Rack env hash, the second being a Rack Request object.

custom_user_hash

By default Timber automatically captures user context for most of the popular authentication libraries (Devise, and Clearance). See Timber::Integrations::Rack::UserContext for a complete list.

In cases where you Timber doesn't support your strategy, or you want to customize it further, you can do so like:

Timber.config.integrations.rack.user_context.custom_user_hash = lambda do |rack_env|
user = rack_env['warden'].user
if user
{
id: user.id, # unique identifier for the user, can be an integer or string,
name: user.name, # identifiable name for the user,
email: user.email, # user's email address
}
else
nil
end
end

Available Context

context.http

HTTP context is only available is you install the Timber::Integrations::Rack::HTTPContext middleware as shown in Installation.

HTTP context captures structured data on incoming HTTP requests:

{
"context": {
"http": {
"request_id": "30f14c6c1fc85cba12bfd093aa8f90e3",
"method": "get",
"host": "myhost.com",
"path": "/"
}
}
}

Field

Type

Description

context.http.request_id

string

Unique identifier for the request

context.http.method

string

Method of the HTTP request

context.http.host

string

Host of the HTTP request

context.http.path

string

Path of the HTTP request

context.user

User context is only available is you install the Timber::Integrations::Rack::UserContext middleware as shown in Installation.

User context captures structured data about the current logged in user.:

{
"context": {
"user": {
"id": "abcd1234",
"email": "paul@bunyan.com",
"name": "Paul Bunyan"
}
}
}

Field

Type

Description

context.user.id

string

Unique identifier for the user

context.http.email

string

Email address of the user, if available.

context.http.name

string

Name of the user, if available.

Events

http_request_received

The http_request_received event is emitted when a HTTP request is received.

{
"http_request_received": {
"method": "get",
"scheme": "https",
"host": "sub.mydomain.com",
"path": "/"
}
}

Field

Type

Description

http_request_received.method

string

Method of the HTTP request

http_request.scheme

string

Scheme of the HTTP request (http or https)

http_request_received.host

string

Host of the HTTP request

http_request_received.path

string

Path of the HTTP request

http_request_received.params_json

string

JSON representation of the incoming parameters. See this guide to understand why we encode this data.

Where's the body? Timber purposefully leaves out the HTTP request body because it can be represented in many different formats. Instead, we log the parameters in the controller_called event which will be in a normalized structured.

http_response_sent

The http_response_sent event is emitted when a HTTP response is sent back to the user.

{
"http_response_sent": {
"status": 200,
"duration_ms": 50.4
}
}

Field

Type

Description

http_response_sent.status

string

HTTP status code of the response

http_response_sent.duration_ms

float

Duration of processing the entire request

Guides

To keep things consolidated and simple, all guides are located in the Ruby Guides section.