Go Module 14
context and cancellation interview questions
Interview questions on context and cancellation: short warm-ups, then what each harder question tests, the first step of a good answer and its follow-ups.
Warm-up questions
Short questions with short answers, each answered in full.
-
Fresher
What is the difference between context.Background and context.TODO?
Answered in the lesson context: cancellation, deadlines and values
-
Mid
What does context.Cause return for a context ended by a plain CancelFunc?
Answered in the lesson Cancellation causes, AfterFunc and WithoutCancel
-
Mid
Why should a handler pass r.Context() to db.QueryContext?
Answered in the lesson Deadlines across a service: budgets and retries
Questions with model answers
What each question tests, the first step of a good answer and the follow-ups to expect.
-
Mid to senior
A nightly job ships 200,000 orders. Inside its loop it calls ctx, cancel := context.WithTimeout(parent, 5*time.Second) and defer cancel(), then ships the order. Memory climbs through the run and the job is killed near the end. Explain why, fix it, and say what go vet would and would not have caught.
- What it tests
- Knowing that deferred calls run at function exit, what a live timeout context holds, how to release each pass's context, and the limits of the lostcancel check.
- First step
- Look at when each cancel runs: defer schedules it for the end of the function, not the end of the pass, so after n orders there are n live contexts, each with a timer and a link from its parent, and n deferred calls waiting. At 200,000 orders that is 200,000 of each until the job returns.
- Follow-ups
-
- Why does vet stay quiet about this code?
- Is calling cancel() right after ship enough, or does a panic change things?
- Would one context for the whole job be better?
From the lesson context: cancellation, deadlines and values
Model answer, Pro. Model answers open with any pass; prices are in the notice on this page.Opening the model answers with your pass…
Model answers open with any MySmartCoPilot pass.
- Pro pass · 1 week₹79$2.99
- 30 days₹179$5.99
- 1 year₹1,699$45
One payment; a pass never renews. The price shown is the total you pay: no fees or charges are added at checkout.
Passes can’t be bought right now, so the model answers can’t be opened at the moment. If you have a pass, enter your licence key.
It also opens every other in-depth part in Learn and every Pro tool. Sales are final, except where the law gives you a right to withdraw, for example in the EU and the UK (refund policy).
In the answer:
- Model answer
- Follow-up answers
- Common mistakes
- Rubric
- Variants
- about 3 minutes
-
Mid to staff
A codebase passes the database handle, a logger, a feature-flag client and a dryRun flag through context values under string keys, so that function signatures stay short. Judge the design: what goes wrong in practice, what belongs in a context, and how you would change it.
- What it tests
- Knowing the documented scope of context values, the cost of untyped hidden dependencies, key collisions with built-in key types, and how to refactor towards explicit dependencies.
- First step
- Sort the four items by the documentation's rule: context values are for request-scoped data that crosses API boundaries, never optional parameters. The database handle, logger and flag client are shared dependencies, and dryRun changes behaviour; none belongs to one request, so all four are parameters or fields hidden in an untyped map.
- Follow-ups
-
- What does a string key risk that an unexported key type does not?
- Is a request-scoped logger, with the request ID attached, a fair exception?
- How would you migrate the codebase without one huge change?
From the lesson context: cancellation, deadlines and values
Model answer, Pro.In the answer:
- Model answer
- Follow-up answers
- Common mistakes
- Rubric
- Variants
- about 3 minutes
-
Mid to senior
Your API logs about 4,000 "context canceled" errors an hour, and nobody can tell client disconnects from quota limits, slow dependencies or deploys. Design the change: what each component records, what the log line holds, and how alerts use it.
- What it tests
- Using WithCancelCause, WithTimeoutCause and signal causes deliberately, keeping Err checks working, logging err and cause apart, and alerting on causes rather than on a single error string.
- First step
- Start where contexts end: the middleware that enforces quotas, the calls that set timeouts, and shutdown. Make each end the context with a named cause, then log ctx.Err() and context.Cause(ctx) as two attributes. Err keeps existing checks working; the cause turns 4,000 identical lines into counts per reason.
- Follow-ups
-
- Which of the four endings is normal, and must never page anyone?
- How do you keep errors.Is checks for timeouts working once timeouts have named causes?
- What does the shutdown path log, and what do in-flight requests log?
From the lesson Cancellation causes, AfterFunc and WithoutCancel
Model answer, Pro.In the answer:
- Model answer
- Follow-up answers
- Common mistakes
- Rubric
- Variants
- about 3 minutes
-
Mid to senior
A download manager streams files through io.Copy, which takes no context, into name.part files. When the user cancels, the copy must stop and the partial file must be removed exactly once, even if the download finishes at the same moment. Design it with context.AfterFunc.
- What it tests
- Using AfterFunc to interrupt a call that takes no context, reading stop's result to decide ownership, avoiding races on cleanup, and choosing what wins a tie between cancel and completion.
- First step
- Separate interrupting from cleaning up. Something has to make io.Copy return when the context ends, and exactly one piece of code must own the part file. Then decide what the result of AfterFunc's stop function tells you about which of the two endings happened.
- Follow-ups
-
- Which piece of code removes the part file, and why that one?
- The cancel arrives after the last byte but before stop. What should the download report?
- Would an HTTP response body need AfterFunc at all?
From the lesson Cancellation causes, AfterFunc and WithoutCancel
Model answer, Pro.In the answer:
- Model answer
- Follow-up answers
- Common mistakes
- Rubric
- Variants
- about 3 minutes
-
Mid to staff
After a payment succeeds, an audit record must be written even if the client disconnects. A teammate starts a goroutine that writes it with context.Background(). What is lost, how do you do it with WithoutCancel, and what stops detached writes from piling up or being cut off by a deploy?
- What it tests
- Knowing what WithoutCancel keeps and drops, adding a limit of its own, tracking detached work for shutdown, and estimating how much can be in flight when a dependency hangs.
- First step
- Compare what the two contexts carry: Background escapes the request's cancellation but drops its values, so the audit loses the request ID and trace. WithoutCancel escapes the cancellation and keeps them. Neither has a limit, so wrap it: WithTimeout(context.WithoutCancel(ctx), 2*time.Second).
- Follow-ups
-
- How many writes can be in flight when the audit store hangs?
- How does shutdown wait for detached writes without waiting for ever?
- When is a queue better than a detached goroutine?
From the lesson Cancellation causes, AfterFunc and WithoutCancel
Model answer, Pro.In the answer:
- Model answer
- Follow-up answers
- Common mistakes
- Rubric
- Variants
- about 3 minutes
-
Mid to senior
A checkout endpoint must answer within 800 ms. It calls inventory (p99 120 ms), pricing (p99 200 ms) and payment (p99 350 ms) in sequence. Design the per-call timeouts, what happens when pricing is slow, and what the client sees in each case.
- What it tests
- Deriving per-call timeouts from the time left, keeping a reserve, refusing calls that cannot finish, and choosing what to tell the client and the callee.
- First step
- Add up the p99s first: 670 ms of the 800, so 130 ms of slack before the reserve for the response. Then give each call what is left, less the reserve, rather than a fixed share, and give each a minimum near its p99, so a call that can no longer finish is not started.
- Follow-ups
-
- Which calls could run in parallel, and what does that do to the budget?
- Should payment ever be cut short once it has started?
- What status should the client get when the budget runs out?
From the lesson Deadlines across a service: budgets and retries
Model answer, Pro.In the answer:
- Model answer
- Follow-up answers
- Common mistakes
- Rubric
- Variants
- about 3 minutes
-
Mid to staff
A dependency was down for 30 seconds. When it came back, 5,000 clients retrying with exponential backoff without jitter knocked it over again, twice. Explain why, and design retries that let it recover, with numbers.
- What it tests
- Seeing synchronised retries, applying full jitter and caps, bounding total load with a retry budget, and keeping retries inside each request's deadline and to idempotent calls.
- First step
- Work out when the retries land if every client failed at the same moment and then waits the same 100, 200 and 400 ms, and compare each moment's load with what the service carried before it went down.
- Follow-ups
-
- Jitter spreads the load. What limits the total?
- How do retries interact with each request's deadline?
- Which calls must never be retried automatically?
From the lesson Deadlines across a service: budgets and retries
Model answer, Pro.In the answer:
- Model answer
- Follow-up answers
- Common mistakes
- Rubric
- Variants
- about 3 minutes
-
Mid to senior
A service builds its outgoing client as http.Client{Timeout: 10 * time.Second} and also passes each request's context, which often has 2 s left. Which limit ends a slow call, what error does the caller see, and which other timeouts would you still set, on the client and on the server?
- What it tests
- Knowing how the client's timeout and the request's context combine, what each one covers, how to read their errors, and which transport and server timeouts to set.
- First step
- Compare the two deadlines on each call: the context's 2 s comes first, so the context ends the slow call, whatever the client's 10 s. Then ask what each limit covers beyond that call, and what the error should tell the caller about which limit fired.
- Follow-ups
-
- What does Client.Timeout cover that a ResponseHeaderTimeout does not?
- What does a test of this inside a synctest bubble print, and why?
- Which server timeouts does a zero http.Server leave unset, and what does that allow?
From the lesson Deadlines across a service: budgets and retries
Model answer, Pro.In the answer:
- Model answer
- Follow-up answers
- Common mistakes
- Rubric
- Variants
- about 3 minutes