Skip to content

πŸ› [Bug]: Context.Background() used as default in request path β€” breaks cancellation chainΒ #4338

@pageton

Description

@pageton

Bug Description

DefaultCtx.Context() returns context.Background() by default when no user context has been set via SetContext(). This means any middleware or handler that calls c.Context() and passes it to I/O operations gets an uncancellable context by default.

How to Reproduce

Steps to reproduce the behavior:

  1. Create a handler that uses c.Context() without calling SetContext() first
  2. Pass the context to a storage or HTTP operation
  3. The client disconnects
  4. The operation runs to completion because context.Background() never signals cancellation
app.Get("/", func(c fiber.Ctx) error {
    // c.Context() returns context.Background() by default
    result, err := cache.GetWithContext(c.Context(), "key")
    // This operation cannot be cancelled
})

Affected Code

ctx.go:129-138:

func (c *DefaultCtx) Context() context.Context {
    if c.fasthttp == nil {
        return context.Background()
    }
    if ctx, ok := c.fasthttp.UserValue(userContextKey).(context.Context); ok && ctx != nil {
        return ctx
    }
    ctx := context.Background()  // default fallback
    c.SetContext(ctx)             // cached β€” persists for the request
    return ctx
}

Impact

Every middleware or handler that calls c.Context() without first calling c.SetContext() gets a context that cannot signal cancellation. This affects:

  • Storage operations (GetWithContext, SetWithContext)
  • Database queries (QueryContext, ExecContext)
  • Outbound HTTP requests (NewRequestWithContext)
  • Any library accepting context.Context

Expected Behavior

Consider adding middleware that automatically creates a proper context.Context from the request lifecycle (e.g., with client-disconnect detection). At minimum, document prominently that c.Context() returns context.Background() by default and that c.SetContext() should be called early in the middleware chain.

Related

Fiber Version

v3 (latest main branch)

Metadata

Metadata

Assignees

No one assigned

    Type

    No type
    No fields configured for issues without a type.

    Projects

    Status
    No status

    Milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions