Search code examples
iosswiftwatchkitsendmessagewatchconnectivity

WCSession sendMessage errorHandler called multiple times


I'm using WatchKit 2.0, and am noticing a very strange behavior. If I'm using my watch app for over 5 minutes, I start getting timeout errors from the WCSession sendMessage call, which has previously been called and completed successfully. I print out the error as:

Error Domain=WCErrorDomain Code=7012 "Message reply took too long." UserInfo={NSLocalizedDescription=Message reply took too long., NSLocalizedFailureReason=Reply timeout occured.}

I can still make other calls in different Interface Controllers, but I keep getting errorHandlers called in Interface Controllers which have been closed (used back button on top).

Does anyone know what could be causing this behavior? I do not combine hierarchical and page-based interface styles in the code, and everything behaves for the first 5 minutes while using the application.

UPDATE

Here is the code:

    if WCSession.isSupported() {
        // Set the session to default session singleton
        let session = WCSession.defaultSession()

        // Fire the message to iPhone app
        session.sendMessage(["action": "getProfile", "memberId": citizen!.memberId], replyHandler: { (response) -> Void in


            if response["messageData"] != nil {
                // There is data in the reply
                let jsonObject = JSON(response["messageData"]!)

                ...

                // Display the profile details
                self.displayProfileDetails()



            } else if response["error"] != nil {
                // Get the error message and display it
                self.showAlert(nil, message: WatchUtils.getErrorString(response["error"]), action: .GET_PROFILE)
            }
            }, errorHandler: { (error) -> Void in
                print("error: \(error)")
                // Show alert
                self.showAlert(nil, message: NSLocalizedString("watch_connectivity_error", comment: "Watch can't connect to phone"), action: .GET_PROFILE)
        })
    }

The replyHandler gets called initially, but for some reason after 5 minutes the errorHandler is called, and keeps getting called every couple of seconds.


Solution

  • I experienced the same problem a few months ago. The solution I came up with was using a variable to store the id I gave to the last request made, for instance

    self.lastCallId = "watch_load_clients"

    And if the matching id isn't received (I also send the id back) then I ignore the request.

    I think it's just a Bluetooth issue.

    Edit: Also, are you making requests and not receiving a response? That is the case when your problem should happen.