The iOS page script posts five actions with no callbackId, and the Swift dispatcher answers all five anyway. resolveCallback and rejectCallback both open with guard let id = callbackId else { return }, so every one of those answers is thrown away. This is the same shape as #203 (share), which is being fixed separately.
| page call | posts | what the native side says that the page never hears |
|---|---|---|
craft.haptic(style) | {action: 'haptic', style} | CAPABILITY_DISABLED when enableHaptics is off |
craft.startListening() | {action: 'startListening'} | CAPABILITY_DISABLED when enableSpeechRecognition is off |
craft.geolocation.watchPosition(cb) | {action: 'watchPosition'} | CAPABILITY_DISABLED when enableGeolocation is off; the callback simply never fires |
craft.geolocation.clearWatch() and craft.location.clearWatch(id) | {action: 'clearWatch'} | true |
craft.vibrate(pattern) | {action: 'vibrate', pattern} | true |
The first three are the ones that hurt. A page that calls them with the capability disabled gets no error and no event, which reads the same as "still waiting". The contract wrappers make it worse: craft.haptics.impact() returns Promise.resolve() after calling craft.haptic, so it reports success for a call that was refused.
The last two only lose a true. They are listed because they have the same shape, and a page cannot tell a lost true from a lost rejection.
What guards it now
ios_conformance_test.zig scans every postMessage in the page script. It fails when a post carries no callbackId for an action whose Swift case answers through one, unless the action is on a recorded list. These five are that list. The second half of the test fails when a listed action gets fixed without being removed, so the list can only shrink.
Fixing one
Give the page method a callbackId and return the promise, the way openCamera does. Then take the action off unanswered_posts. For haptic and vibrate, also check the craft.haptics wrappers, which currently return Promise.resolve() whatever native says.
Found while fixing #203.