Only time out the intended call

previously a followup call could get clobbered by the previous calls
timeout

// FREEBIE
This commit is contained in:
Michael Kirk 2017-02-08 14:27:29 -05:00
parent 6d757d3a50
commit 6cdf13ea5f

View file

@ -74,7 +74,7 @@ enum CallError: Error {
case assertionError(description: String)
case disconnected
case externalError(underlyingError: Error)
case timeout(description: String)
case timeout(description: String, call: SignalCall)
}
// Should be roughly synced with Android client for consistency
@ -318,7 +318,7 @@ protocol CallServiceObserver: class {
// Don't let the outgoing call ring forever. We don't support inbound ringing forever anyway.
let timeout: Promise<Void> = after(interval: TimeInterval(connectingTimeoutSeconds)).then { () -> Void in
// rejecting a promise by throwing is safely a no-op if the promise has already been fulfilled
throw CallError.timeout(description: "timed out waiting to receive call answer")
throw CallError.timeout(description: "timed out waiting to receive call answer", call: call)
}
return race(timeout, callConnectedPromise)
@ -450,7 +450,7 @@ protocol CallServiceObserver: class {
call = newCall
let backgroundTask = UIApplication.shared.beginBackgroundTask {
let timeout = CallError.timeout(description: "background task time ran out before call connected.")
let timeout = CallError.timeout(description: "background task time ran out before call connected.", call: newCall)
DispatchQueue.main.async {
guard self.call == newCall else {
return
@ -496,7 +496,7 @@ protocol CallServiceObserver: class {
let timeout: Promise<Void> = after(interval: TimeInterval(connectingTimeoutSeconds)).then { () -> Void in
// rejecting a promise by throwing is safely a no-op if the promise has already been fulfilled
throw CallError.timeout(description: "timed out waiting for call to connect")
throw CallError.timeout(description: "timed out waiting for call to connect", call: newCall)
}
// This will be fulfilled (potentially) by the RTCDataChannel delegate method
@ -1090,6 +1090,14 @@ protocol CallServiceObserver: class {
Logger.error("\(TAG) call failed with error: \(error)")
if let call = self.call {
if case .timeout(description: _, call: let timedOutCall) = error {
guard timedOutCall == call else {
Logger.debug("Ignoring timeout for previous call")
return
}
}
// It's essential to set call.state before terminateCall, because terminateCall nils self.call
call.error = error
call.state = .localFailure