Skip to content
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

ApolloErrorInterceptor does not respect RequestChain callback queue #1530

Closed
yliu342 opened this issue Nov 20, 2020 · 3 comments
Closed

ApolloErrorInterceptor does not respect RequestChain callback queue #1530

yliu342 opened this issue Nov 20, 2020 · 3 comments
Labels
duplicate Issues that have been determined to be a dupe of another issue networking-stack

Comments

@yliu342
Copy link

yliu342 commented Nov 20, 2020

Version: 0.34.1
Dependency Manager: SPM

Hi,

I've recently come across this issue when add an additionalErrorInterceptor to a chain request.
The protocol ApolloErrorInterceptor has a required method handleErrorAsync(error:chain:request:response:completion:).

When implementing this method, I would like to call the completion on the callback queue which specified by the RequestChain object. However, the callbackQueue is a private method inside RequestChain which prevent me to do so.

I'm wondering if there are any plans to make callbackQueue public?

What I'm currently do is remove the additionalErrorHandler and call handleErrorAsync to make sure it is called on the callback queue.

func handleErrorAsync<Operation: GraphQLOperation>(
            error: Error,
            chain: RequestChain,
            request: HTTPRequest<Operation>,
            response: HTTPResponse<Operation>?,
            completion: @escaping (Result<GraphQLResult<Operation.Data>, Error>) -> Void) {
            // .... Do request
            if success {
                chain.retry(request: request, completion: completion)
            } else {
                chain.additionalErrorHandler = nil
                chain.handleErrorAsync(error, request: request, response: response, completion: completion)
            }
        }

But really what I'm expecting is something like:

chain.callbackQueue.async {
        completion(.failure(error))
      }

Any suggestions are welcomed.

@designatednerd
Copy link
Contributor

Hi! This was fixed in 0.37.0 - please update to that version. Thank you!

@designatednerd designatednerd added duplicate Issues that have been determined to be a dupe of another issue networking-stack labels Nov 20, 2020
@designatednerd
Copy link
Contributor

Going to close this out as a duplicate of #1468.

@vfumin
Copy link

vfumin commented Nov 26, 2020

Hi, i try to retry request from errorinterceptor, after refreshtoken, request sends, but i can't get completion event in fetch method


class RefreshTokenInterceptor: ApolloErrorInterceptor {

    private let requestManager: RequestManager
    private let bag = DisposeBag()

    init(requestManager: RequestManager) {
        self.requestManager = requestManager
    }

    /// Asynchronously handles the receipt of an error at any point in the chain.
    ///
    /// - Parameters:
    ///   - error: The received error
    ///   - chain: The chain the error was received on
    ///   - request: The request, as far as it was constructed
    ///   - response: [optional] The response, if one was received
    ///   - completion: The completion closure to fire when the operation has completed. Note that if you call `retry` on the chain, you will not want to call the completion block in this method.
    func handleErrorAsync<Operation: GraphQLOperation>(
        error: Error,
        chain: RequestChain,
        request: HTTPRequest<Operation>,
        response: HTTPResponse<Operation>?,
        completion: @escaping (Result<GraphQLResult<Operation.Data>, Error>) -> Void) {
        guard response?.httpResponse.statusCode == 401 else {
            completion(.failure(error))
            return
        }
        requestManager.refreshToken()
            .subscribe(
                onSuccess: { [chain] in
                    chain.retry(request: request, completion: completion)
                },
                onError: { error in
                    completion(.failure(error))
                }
            )
            .disposed(by: bag)
    }
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
duplicate Issues that have been determined to be a dupe of another issue networking-stack
Projects
None yet
Development

No branches or pull requests

3 participants