Skip to content

Best practice for deduplicating in-flight requests #919

Description

@bartoszirzyk

Motivation

Hello,
I wanted to ask how to approach with removing duplicated request in flight? I was wondering about creating dedicated Middleware that will catch all simultaneous calls, fire first one and on return share result with other callers. This might work fine, but I faced an issue where the first call is cancelled. This triggers cancel handler in URLSessionTransport that cancels request and returns nothing. This propagates to all callers waiting for the response.

Proposed solution

In iOS 27 there will be shield mechanism https://developer.apple.com/documentation/swift/withtaskcancellationshield(operation:)
but I need to have compatibility with older iOS versions.

I thought about shared detached Task, but ClientMiddleware protocol assumes that next closure is non escaping, which would be required in order to pass it into a new task.

Other option I would see is to be able to control cancel behaviour in URLSessionTransport. A flag in configuration that determines if canceling task means that dataTask is cancelled/ operation checks for cancellation. Right now call is fired anyway by URLSession, but later checks in e. g. bidirectionalStreamingRequest:

            try Task.checkCancellation()
            return (try HTTPResponse(response), responseBody)

makes impossible to react in higher layers. I would like to have more freedom of controlling such behaviour. If task is cancelled, it would make sense to still have a response and its body to evaluate and maybe clean up.

Alternatives considered

No response

Additional information

No response

Metadata

Metadata

Assignees

No one assigned

    Labels

    kind/featureNew feature.status/triageCollecting information required to triage the issue.

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions