How to Use context.WithValue in Go (And When Not To)

Use context.WithValue to pass small, request-scoped data through goroutine boundaries, but avoid it for large objects or data that can be passed as explicit arguments.

Use context.WithValue to attach request-scoped data to a context, but only when passing data through goroutine boundaries where no other mechanism exists. Never use it for passing large objects, sensitive data, or data that can be passed as explicit function arguments.

ctx := context.WithValue(parentCtx, key, value)
// Use ctx in child goroutines or functions
// Always cancel the context when done
defer cancel()

When NOT to use it:

  • Passing data that can be an explicit argument
  • Storing large objects (causes memory leaks)
  • Storing sensitive data (passwords, tokens) unless encrypted
  • Using string keys (use struct{} to avoid collisions)