Lesson 12 · Interceptors, middleware & auth
The middleware chain
Many interceptors, one order — and why the order matters.
Your win: explain how interceptors chain, in what order they run, and what each interceptor in your services' actual stack does.
Chaining: many interceptors → one
You rarely have just one interceptor. gRPC composes several into a single chain — via
the native grpc.ChainUnaryInterceptor or (in our repo)
grpc_middleware.WithUnaryServerChain. They execute left to
right, and each passes its ctx changes to the next.1
Order is a correctness concern
Your actual chain
The framework assembles a default set plus each service's custom interceptors (internal/golibs/bootstrap/grpc.go:98-130):
| # | Interceptor | Does |
|---|---|---|
| 1 | grpc_ctxtags | attach request tags for logs/tracing |
| 2 | grpc_zap | structured request logging |
| 3 | payload logger | log the request payload on failure |
| 4 | context-canceled remap | "context canceled" → codes.Canceled (Lesson 8) |
| 5 | recovery (non-local) | panic → codes.Unknown + stacktrace |
| 6 | timeout | wrap ctx with 5s deadline (Lesson 9) |
| 7 | auth | verify JWT from metadata, inject claims (Lesson 13) |
| 8 | activity-log tracer | emit an activity/trace span |
DefaultUnaryServerInterceptor(rsc) then authInterceptor +
tracer.UnaryActivityLogRequestInterceptor. spike/notification add a
fake-JWT interceptor for internal calls (Lesson 13). Metrics ride along via OpenCensus
GrpcServerViews (latency, request count) → Prometheus.
go-grpc-middleware (chaining) + gRPC Interceptors guide
ChainUnaryServer docs explain left-to-right execution and ctx flow; the
interceptors guide covers the concept.
→ github.com/grpc-ecosystem/go-grpc-middleware
→ grpc.io/docs/guides/interceptors
Check yourself (from memory)
Q1. Chained interceptors execute in what order?
Q2. Which interceptor should sit outermost?
Q3. Our default chain includes logging, tags, and…
grpc_middleware.WithUnaryServerChain (native:
grpc.ChainUnaryInterceptor) and run LEFT-TO-RIGHT, each passing ctx
changes to the next (nested onion — before and after the handler). Order matters:
recovery outermost (catch inner panics), auth before the handler, timeout wrapping.
Our chain: ctxtags → zap logging → payload-log → context-canceled remap → recovery →
timeout(5s) → auth → activity-log tracer → handler; metrics via OpenCensus
GrpcServerViews.1. go-grpc-middleware — ChainUnaryServer; gRPC Interceptors.