Hone logo
Hone
Problems

Implementing Context with Timeout in Go

Contexts are fundamental in Go for managing request-scoped values, cancellation signals, and deadlines. This challenge focuses on implementing a function that leverages context.WithTimeout to create a context with a specified timeout duration. This is crucial for building robust and responsive applications that gracefully handle long-running operations and prevent resource exhaustion.

Problem Description

You are tasked with creating a Go function named WithTimeoutContext that takes a parent context and a timeout duration as input. The function should return a new context derived from the parent context, but with a timeout applied. If the timeout expires before any operations using the new context are completed, the context should be canceled. The function should also return the cancel function associated with the new context, allowing the caller to explicitly cancel the context if needed (though this isn't strictly required for the core functionality).

Key Requirements:

  • The function must accept a context.Context and a time.Duration as input.
  • It must use context.WithTimeout to create a new context with the specified timeout.
  • The function must return the new context and the associated cancel function.
  • The returned context should be derived from the parent context, inheriting its values and cancellation signals.

Expected Behavior:

When the timeout duration elapses, the returned context should be automatically canceled. Any operations using this context should receive a context.Canceled error. If the parent context is canceled before the timeout expires, the new context should also be canceled immediately.

Edge Cases to Consider:

  • What happens if the timeout duration is zero?
  • What happens if the parent context is already canceled?
  • How does the function handle potential errors during context creation (though context.WithTimeout rarely errors)?

Examples

Example 1:

Input: parentContext := context.Background(); timeout := 2 * time.Second
Output: newContext, cancel := WithTimeoutContext(parentContext, timeout)
Explanation: A new context is created derived from `context.Background()` with a timeout of 2 seconds.  If no operations are performed on `newContext` within 2 seconds, it will be canceled.

Example 2:

Input: parentContext := context.Background(); timeout := 0 * time.Second
Output: newContext, cancel := WithTimeoutContext(parentContext, timeout)
Explanation: A new context is created derived from `context.Background()` with a timeout of 0 seconds. The context will be immediately canceled.

Example 3:

Input: parentContext := context.Canceled(); timeout := 1 * time.Second
Output: newContext, cancel := WithTimeoutContext(parentContext, timeout)
Explanation: Since the parent context is already canceled, the new context will also be immediately canceled, regardless of the timeout duration.

Constraints

  • The timeout duration must be a non-negative time.Duration.
  • The parent context must be a valid context.Context.
  • The function should be efficient and avoid unnecessary allocations.
  • The function should not panic under any circumstances.

Notes

  • Consider using defer cancel() within the function to ensure the cancel function is always called, even if an error occurs.
  • The cancel function is provided for more granular control over context cancellation, but the core requirement is to create a context with a timeout.
  • Think about how the parent context's cancellation signals are propagated to the new context.
Loading editor...
go