Skip to content

proposal: context: context.Expired #73533

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
sivchari opened this issue Apr 29, 2025 · 4 comments
Open

proposal: context: context.Expired #73533

sivchari opened this issue Apr 29, 2025 · 4 comments
Labels
LibraryProposal Issues describing a requested change to the Go standard library or x/ libraries, but not to a tool Proposal
Milestone

Comments

@sivchari
Copy link
Contributor

Proposal Details

Proposal Details

Proposed addition:

func Expired(err error) bool

Motivation

Currently, many codebases should check whether the error is context.Canceled or context.DeadlineExceeded like this.

x, err := doFunc(ctx) // call 
if err != nil {
    if errors.Is(err, context.Canceled) || errors.Is(err, context.DeadlineExceeded)
        // handle
    }
    return err
}

As the above case, it's right if developer want to detect any context cancellation, but this handling is redundant.
This syntax search shows:

Of course it's fine that's only redundant, unfortunately, some bugs can be happened since the returning error is different by Cancel and Timeout.
These are example that happens bugs.

trinodb/trino-go-client#140
argoproj/argo-cd#22824

These cases tried to consider cancellation correctly, but the difference between the explicit cancellation and timeouted cancellation couldn't be considered. To reduce these subtle incorrect handling, I propose above new API.
Of course, we can use Canceled and DeadlineExceeded separately to distinguish these error.

@gopherbot gopherbot added this to the Proposal milestone Apr 29, 2025
@gabyhelp gabyhelp added the LibraryProposal Issues describing a requested change to the Go standard library or x/ libraries, but not to a tool label Apr 29, 2025
@mateusz834
Copy link
Member

mateusz834 commented Apr 29, 2025

I think that if we go with this this should be a:

var Expired error = expiredError{}

And then we can define an Is method.

So the use would look like this:

if errors.Is(err, context.Expired) {
    // ....
}

@seankhliao
Copy link
Member

Is this sufficient though? Now that there's WithCancelCause / WithDeadlineCause / WithTimeoutCause, a context may be canceled without matching either error.

@mateusz834
Copy link
Member

Now that there's WithCancelCause / WithDeadlineCause / WithTimeoutCause, a context may be canceled without matching either error.

Cause errors are only returned through context.Cause(err), and i don't think that we can match the error in any way, as such errors are not wrapped. So that would only work for code using ctx.Err().

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
LibraryProposal Issues describing a requested change to the Go standard library or x/ libraries, but not to a tool Proposal
Projects
None yet
Development

No branches or pull requests

5 participants