Skip to content

Instantly share code, notes, and snippets.

@philipjkim
Created April 24, 2019 06:02
Show Gist options
  • Save philipjkim/53dd203c39fce6621b7c1a2de5fdecfa to your computer and use it in GitHub Desktop.
Save philipjkim/53dd203c39fce6621b7c1a2de5fdecfa to your computer and use it in GitHub Desktop.
Demo: Using context to cancel heavy jobs after timeout
package main
import (
"context"
"fmt"
"time"
)
// DemoTimeout .
func DemoTimeout(ctxTimeout time.Duration, workDuration time.Duration) error {
ctx, _ := context.WithTimeout(context.Background(), ctxTimeout)
return demoTimeoutInternal(ctx, workDuration)
}
func demoTimeoutInternal(ctx context.Context, workDuration time.Duration) error {
res := make(chan error)
go func(ctx context.Context, res chan error, workDuration time.Duration) {
fmt.Println("goroutine started")
res <- heavyJob(ctx, workDuration)
fmt.Println("goroutine finished")
}(ctx, res, workDuration)
select {
case e := <-res:
fmt.Printf("got res, error: %v\n", e)
return e
}
}
func heavyJob(ctx context.Context, duration time.Duration) error {
fmt.Println("heavy job started")
select {
case <-time.After(duration):
fmt.Println("heavy job completed")
return nil
case <-ctx.Done():
fmt.Printf("heavy job interrupted by ctx.Done: %v\n", ctx.Err())
return ctx.Err()
}
}
func main() {
err := DemoTimeout(1*time.Second, 900*time.Millisecond)
fmt.Println(err) // <nil>
err = DemoTimeout(1*time.Second, 1100*time.Millisecond)
fmt.Println(err) // context deadline exceeded
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment