skip to content

Request Lifecycle & Routing

How a framework takes a parsed request from the server, resolves a route, runs the hook chain and handler, and commits a response. Asked because 'why did my hook not run' bugs live in this order.

on this pageshow

explore

questions

30

In a server-side web framework, what ordered stages does one request pass through from route resolution to the written response?

level: juniorimportance: must knowfreq 72%

answer

  1. in, then back out
  2. resolve before anything route-scoped runs
  3. binding sits between hooks and handler
  4. rendering turns a value into bytes
  5. failures divert, they do not continue

basics

~20 s

One dispatch runs in order: resolve the route, run pre-handler hooks, bind the request into handler inputs, invoke the handler, render what it returned, then unwind the post-handler hooks. A failure at any stage diverts to the error stage instead.

solid answer

~40 s

A dispatch is an ordered pipeline, not one function call. The framework first **resolves the route** — method and path become a chosen handler plus any variables pulled out of the path. It then runs the **pre-handler hook chain** (authentication, correlation ids, logging, rate limiting), then **binds** the raw request into the handler's typed inputs: path variables, query values, headers, and a deserialized body. Only then is the **handler** invoked. What the handler returns goes through **rendering**, which turns a value into a status, response headers and bytes. Control then **unwinds back out** through the hooks that already ran, and the request's resources are released. Any stage that fails leaves the straight line and enters the **error stage**. Names differ across frameworks — filters, middleware, interceptors, phases — but the inbound-then-outbound shape is near-universal.

go deeper

for a junior

Be able to recite the order out loud: resolve, hooks in, bind, handle, render, hooks out, with errors diverting to an error stage. That alone answers most screening versions of this question.

for a middle

Explain why the order is forced — each stage needs the previous stage's output — and what each stage can still change. Name the inbound and outbound halves and say what information each half has.

for a senior

Use the order to diagnose: a hook that sees no route metadata, a size check that fires too late, a header added after flush. Say which stage the symptom points at before touching a debugger.

for a principal

Decide which responsibilities the platform owns as pipeline stages versus what each service writes itself, and accept the cost: a stage placed outermost is uniform but blind to route detail, while a route-scoped one sees everything and is easy to forget.

## What "dispatch" means Once a server has read and parsed an incoming HTTP message, something must decide **which** piece of application code runs and **what** gets written back. That decision, plus everything wrapped around it, is the **dispatch pipeline**: a fixed, ordered sequence of stages the framework runs for every request. The vocabulary differs between frameworks — filters, middleware, interceptors, plugins, phases — but the shape is stable, because each stage consumes what the previous one produced. You cannot bind a body to a handler's parameters before you know which handler was chosen, and you cannot render a result before there is one. A useful mental model is a funnel with a mirror at the bottom: the request travels **inward** through a series of stages, the handler sits at the centre, and the response travels **outward** through the same stages in reverse. ## The stages, in order 1. **Route resolution.** The request's method and path (sometimes also headers) are turned into a decision: this handler, plus the variables extracted from the path. If nothing matches, dispatch ends here — typically 404 — and nothing scoped to a route ever runs. 2. **Pre-handler hooks.** The inbound half of the hook chain: identity, correlation ids, request logging, rate limiting, opening a unit of work. Each element may pass the request on or stop it and produce a response itself. 3. **Binding.** Raw strings and bytes become the handler's typed inputs: path variables, query values, headers, and a body deserialized according to its declared content type. Conversion failures and, in most frameworks, declarative validation surface here — **before** the handler. 4. **Handler invocation.** Application code runs. It returns a value, writes to the response directly, or returns something that completes later if the framework supports asynchronous results. 5. **Rendering.** The returned value becomes a status code, response headers and a byte stream — serialization, content negotiation, template expansion, or a straight pass-through for a stream. 6. **Post-handler hooks.** The outbound half: the elements that already ran regain control, now able to observe the status and the elapsed time. 7. **Error stage.** Not a step on the straight line. Any stage that fails diverts here, and this stage produces a response of its own. After stage 7 the request's **lifetime** closes: per-request context is torn down, the body and any borrowed resources are released, and buffers may be recycled. ## Inbound half versus outbound half | | Inbound (stages 1-4) | Outbound (stages 5-6) | |---|---|---| | Knows | who is calling, what was asked for | what was answered, how long it took | | Can still change | the request, which handler runs, whether to proceed at all | the response, until its first bytes are flushed | | Typical work | authentication, quotas, parsing, starting a unit of work | metrics, access logs, adding response headers, cleanup | | Skipped when | an earlier element stops the request | its inbound half never ran | The asymmetry in the last row is where most confusion lives: the outbound half is not a separate list that always runs, it is the **return path** of the inbound half. An element that never got control on the way in has nothing to return from. ## Where frameworks differ Frameworks differ on three points, and it is worth knowing which model you are in rather than which framework does which. Some model hook elements as **wrappers** that explicitly call the next element and regain control when it returns, so inbound and outbound work live in one function; others let you register **separate before and after callbacks**, which run as two independent lists. Some expose **binding** as a stage with its own extension points; others fold it into the invocation step. And some run a globally mounted outermost chain *around* route resolution, so even unmatched requests pass through it, while anything scoped to a route necessarily runs after resolution. ## Why interviewers ask this Because ordering bugs are the classic trap, and they are diagnosed by knowing the order rather than by reading a stack trace: - A hook that reads the matched route's metadata sees nothing, because it was mounted outside route resolution. - A body-size check placed after binding never fires — binding has already read and materialised the body. - A handler's own error handling does not cover serialization of the value it returned, because rendering happens after the handler has returned. - A response header added in a post-handler hook is missing, because bytes were already flushed by then. All four are the same mistake: reasoning about the pipeline as a bag of features rather than as a sequence. Learn the sequence once and the diagnoses follow from it.

  • Why does route resolution usually come before the hook chain rather than after it?
    Because hooks are commonly scoped to a route or a group of routes, the framework must know which route matched before it can decide which hooks apply. Resolving first also lets an unmatched path end cheaply without running per-route work. A globally mounted outermost chain can still wrap resolution itself — but anything route-scoped cannot.
  • Is binding a stage of its own, or just part of invoking the handler?
    Conceptually it is its own stage: it reads the request model and produces typed inputs, and it can fail before a single line of handler code runs — which is why a malformed body yields a 400 with nothing in the handler's log. Some frameworks expose it with its own extension points; others fold it into the invocation step.
  • Where does a response header added by a post-handler hook go if the body has already been streamed?
    Nowhere. Headers travel ahead of the body, so once the first bytes are flushed the status and header set are fixed and a later addition is silently dropped or raises an error. Work that must affect headers belongs on the inbound side or in the rendering step, not on the way back out.

saying these in an interview costs you the question

  • Thinks the handler is the first thing the framework runs for a request.
  • Assumes hooks only run inbound and never regain control on the way out.
  • Believes a handler's own error handling covers serialization of what it returned.
  • Says binding failures reach the handler as null or empty arguments.
  • Treats the error stage as just another element in the normal chain.
open as a page

In a web framework's request object, how do the accessors for path variables, query parameters and headers differ?

level: juniorimportance: must knowfreq 72%

basics

~20 s

Path variables come from the matched route template, so they exist whenever the handler runs. Query parameters and headers come from the client, so either may be missing or repeated, which is why frameworks expose both single- and multi-value accessors.

open as a page

In a server-side web framework, why must a handler set the response status, headers and cookies before writing body bytes?

level: juniorimportance: must knowfreq 66%

basics

~20 s

An HTTP response carries its status line and header block ahead of the body, so the framework sends them first. Once body bytes are flushed the response is committed, and later status, header or cookie changes are lost.

open as a page

In a web framework's router, how does a path template with a variable segment differ from a fully static path?

level: juniorimportance: must knowfreq 70%

basics

~20 s

A static path matches one exact sequence of literal segments. A template such as /orders/{id} matches any single segment in that position and captures its text as a named path variable the handler can read.

open as a page

In a server-side web framework, what does registering a route mean, and what do route groups and prefixes give you?

level: juniorimportance: must knowfreq 62%

basics

~20 s

Registering a route binds an HTTP method and path template to a handler in the routing table before requests arrive. A group registers many routes under a shared prefix and shared hooks, writing the common part once.

open as a page

When a pre-handler hook short-circuits a request in a framework's dispatch pipeline, which stages still run and which are skipped?

level: middleimportance: must knowfreq 58%

basics

~20 s

Everything downstream is skipped: the remaining hooks, binding, the handler and normal rendering. The hooks that already ran still get control back on the way out, and the response the short-circuiting hook produced is still written before the request's resources are released.

open as a page

Why does a web framework's request body often read as empty the second time, and what makes it read-once?

level: middleimportance: must knowfreq 66%

basics

~20 s

The body is a forward-only stream over the connection rather than a stored value: the first reader consumes the bytes and nothing rewinds them, so a later read reaches end-of-stream and produces nothing, usually without any error.

open as a page

In a web framework, what does it mean that a response has been committed, and what does commit freeze?

level: middleimportance: must knowfreq 74%

basics

~20 s

A response is committed once its first bytes reach the client. Commit freezes the status line and every header, cookies included; only body bytes may still be appended. Buffer overflow, an explicit flush or the handler ending triggers it.

open as a page

When several registered route templates all match one request path, how does a router decide which handler runs?

level: middleimportance: must knowfreq 66%

basics

~10 s

Two rules are in use. Most-specific-wins ranks templates structurally, so a literal segment beats a placeholder and a placeholder beats a catch-all whatever the order. First-match-wins simply takes the earliest registration that matches.

open as a page

What are the main route registration styles in server-side web frameworks, and what does each one cost?

level: middleimportance: must knowfreq 70%

basics

~20 s

Three styles dominate: declarative metadata attached to the handler, an explicit route table built by registration calls, and a convention that derives paths from file or name layout. They trade locality against a single readable inventory, and discovery against explicitness.

open as a page

At the boundary between an HTTP server and a web framework, what does the server hand over, and what does the framework hand back?

level: middleimportance: must knowfreq 62%

basics

~20 s

The server hands over one parsed request - method, target, headers, body stream and connection facts - plus a way to answer. The framework returns a status, headers and body, or writes them into the response handle.

open as a page

Which request-size limits does an HTTP server enforce before handing a request to the framework, and what does the client see when one trips?

level: middleimportance: must knowfreq 52%

basics

~20 s

Servers cap the request line, the header block and the body before hand-off. An over-long target usually returns 414, an over-large header block 431, an over-large body 413 - produced below the seam, so the application never sees the request.

open as a page

A handler fails halfway through writing a large response and the client receives a success status with a truncated body instead of your error page. Why, and how do you fix it?

level: seniorimportance: must knowfreq 58%

basics

~20 s

The response committed before the failure, so the success status and headers were already on the wire and the error stage had nothing left to set. Do fallible work before the first byte, and give streamed responses a completeness signal.

open as a page

When a web framework's request object is read-only, how can a pre-handler hook change what the handler sees?

level: middleimportance: should knowfreq 44%

basics

~20 s

By wrapping rather than mutating: the hook builds a delegating object that forwards every accessor to the original except the ones it overrides, then invokes the next stage with the wrapper instead of the original request.

open as a page

In a web framework, what decides whether a response can declare its content length, and how does flushing affect that?

level: middleimportance: should knowfreq 54%

basics

~20 s

A framework can declare a length only if it knows the total body size when the header block goes out. That holds when the whole body is still buffered; an early flush commits first, so the response is delimited instead.

open as a page

Why must a router collect every route matching the request path before it can choose between 404 and 405?

level: middleimportance: should knowfreq 55%

basics

~20 s

A path miss and a method miss are different failures. If no template matches the path, the answer is 404; if templates match but none takes the request method, it is 405 and the matched set names the accepted methods.

open as a page

How can a router treat a trailing slash or a case difference between the request path and a registered template?

level: middleimportance: should knowfreq 44%

basics

~20 s

Three policies are common: strict matching treats the spellings as different paths and misses, lenient matching sends both to one handler, and canonicalising redirects to the preferred form. Path segments are case-sensitive by specification, so ignoring case is an opt-in.

open as a page

Why do web frameworks offer named routes and reverse URL generation instead of hardcoded paths in code and templates?

level: middleimportance: should knowfreq 44%

basics

~20 s

Reverse generation asks the router to build a path from a route's name plus parameter values, so the template exists in one place. Change the template and every generated link follows; the generator also encodes parameters and applies group prefixes.

open as a page

When an HTTP server builds the request object it hands to a web framework, which parts are parsed already and which are left untouched?

level: middleimportance: should knowfreq 44%

basics

~20 s

The start line and the whole header block are parsed and validated before hand-off; the body is usually handed over unread. Query strings and structured header values are often left raw, parsed on demand above the seam.

open as a page

In a framework's dispatch pipeline, where do an unmatched route, a binding failure, a handler exception and a rendering failure each exit?

level: seniorimportance: should knowfreq 50%

basics

~20 s

An unmatched route exits at resolution; a binding failure exits before the handler; a handler exception unwinds into the error stage; a rendering failure reaches it too, but may arrive after the first bytes are already on the wire.

open as a page

In a framework's dispatch pipeline, when does one request's lifetime end, and why can work a handler starts outlive it?

level: seniorimportance: should knowfreq 44%

basics

~20 s

A request's lifetime runs from the hand-off into the pipeline until dispatch completes and its resources are released. Work handed to a separate executor is not bound to that window, so it can outlive the request object and its per-request context.

open as a page

When a web framework is told to trust forwarded headers, what changes about the client address, scheme and host it reports?

level: seniorimportance: should knowfreq 58%

basics

~20 s

The same accessors stop describing the immediate connection and start reporting what forwarded header fields claim about the original client. Those fields are ordinary request text, so the framework believes them only where it is configured to trust the peer.

open as a page

In a router, a newly added route never runs because an older catch-all serves its path — how do you diagnose and prevent that?

level: seniorimportance: should knowfreq 48%

basics

~20 s

Replay the exact path, then read the router's effective route table and which template it selects — the handler you are debugging never ran. Fix it by narrowing the catch-all, then pin the winner with a test.

open as a page

You mount an existing sub-application under a path prefix and its generated links now point to the wrong place — how do you diagnose and fix that?

level: seniorimportance: should knowfreq 46%

basics

~20 s

Mounting attaches a whole routing tree under a base path. Two contracts must agree: the path the inner tree matches, and the base it builds links from. Wrong links mean the base was never configured.

open as a page

What changes for a web application when the HTTP server is embedded in its own process instead of an external server hosting it?

level: seniorimportance: should knowfreq 46%

basics

~10 s

Application code barely changes, because the adapter boundary is the same either way. What moves is ownership: process lifecycle, listener and transport configuration, timeouts, size caps, shutdown behaviour and the deployment unit.

open as a page

How would you guarantee that every request is accounted for and its resources released, whichever stage of the dispatch pipeline it exits at?

level: principalimportance: should knowfreq 38%

basics

~20 s

Anchor the guarantee at the pipeline's completion boundary, not at a position in the chain that an earlier exit can skip. Cover what the pipeline never sees at the layer in front, and never let the accounting path fail the request.

open as a page

How would you set response buffering and commit policy across services that return both small payloads and very large exports?

level: principalimportance: should knowfreq 42%

basics

~20 s

Make late commit the default: size the buffer above the common payload so ordinary responses stay replaceable by an error response, and make early flushing an opt-in that owes a completeness signal and a post-commit failure metric.

open as a page

Across an edge proxy, the HTTP server and the framework, where would you own request-size and header limits for a fleet of services, and why?

level: principalimportance: should knowfreq 33%

basics

~10 s

Cap deliberately at every layer: the edge strictest as the platform default, the server looser as a process-protection backstop, the framework tightest per route. The failure to avoid is caps that differ by accident.

open as a page

How would you decide which routes get a replayable request body across a platform, and what does that cost?

level: principalimportance: nice to knowfreq 35%

basics

~20 s

Keep streaming as the default and make capture an opt-in per route, with a measured cap and a loud failure past it. Worst-case memory is peak concurrency times that cap, so upload and relay routes stay streaming permanently.

open as a page

How would you choose a route registration convention for a service with hundreds of endpoints owned by several teams?

level: principalimportance: nice to knowfreq 36%

basics

~20 s

Optimise for ownership and review, not typing. Compose per-module route trees at reserved prefixes, attach cross-cutting hooks at the group so new routes are safe by default, and keep the effective inventory printable and diffable.

open as a page