tonhowtf/omniget · warning
[omnidisc] call ring failed
Error message
[omnidisc] call ring failed
What it means
The dispatch channel listener (`omnidisc://dispatch`, carrying call rings) wraps handleDispatch in try/catch; a throw inside handleDispatch — typically a malformed DispatchPayload or unhandled ring state — is logged as this warning. The listener remains attached and later events still process.
Solutions
- Log event.payload with the error to find which dispatch variant throws.
- Add explicit cases/guards in handleDispatch for unknown or stale rings (ignore instead of throw).
- Regenerate DispatchPayload types from the Rust definitions to fix field skew.
- Debounce/dedupe rings per caller id before dispatching.
Example fix
// before
handleDispatch(event.payload);
// after
try { handleDispatch(event.payload); }
catch (e) { console.warn("[omnidisc] call ring failed", errorText(e), event.payload); } Defensive patterns
Strategy: type-guard
Validate before calling
function isDispatchPayload(p: unknown): p is DispatchPayload {
return typeof p === 'object' && p !== null && 'kind' in p;
} Type guard
function isDispatchPayload(p: unknown): p is DispatchPayload {
return (
typeof p === 'object' && p !== null &&
'kind' in p && typeof (p as { kind: unknown }).kind === 'string'
);
} Try / catch
listen<DispatchPayload>("omnidisc://dispatch", (event) => {
try {
if (!isDispatchPayload(event.payload)) return;
handleDispatch(event.payload);
} catch (e) {
console.warn("[omnidisc] call ring failed", errorText(e), event.payload);
}
}); Prevention
- Guard the dispatch payload shape before handling.
- Handle stale/duplicate rings (unknown call, session active) by ignoring, not throwing.
- Log the payload with the warning to identify failing variants quickly.
- Keep the dispatch switch exhaustive with a default no-op case.
When it happens
Trigger: A dispatch payload that fails handleDispatch's assumptions: ring for an unknown/already-ended call, missing caller id fields, duplicate ring while a session is active, or type skew between Rust DispatchPayload and TS.
Common situations: Rapid incoming calls racing the accept/decline state; caller disconnecting between ring emission and handling; added dispatch variants not yet handled in the frontend switch.
Related errors
- [omnidisc] voice event failed
- [omnidisc] could not subscribe to voice events
- [omnidisc] could not subscribe to call rings
- [omnidisc] stream events subscribe failed
- [omnidisc] voice leave failed
AI-assisted analysis of tonhowtf/omniget@8600b91f42 (2026-09-12).
Data as JSON: /api/errors/53f0ab4aa7a9d279.
Report an issue: GitHub.
Appendix: source
Thrown at src/lib/stores/omnidisc-voice-store.svelte.ts:500
try {
unlisten = await listen<VoiceEventPayload>("omnidisc://voice", (event) => {
try {
handleEvent(event.payload);
} catch (e) {
console.warn("[omnidisc] voice event failed", errorText(e));
}
});
} catch (e) {
initialized = false;
console.warn("[omnidisc] could not subscribe to voice events", errorText(e));
return;
}
try {
unlistenDispatch = await listen<DispatchPayload>("omnidisc://dispatch", (event) => {
try {
handleDispatch(event.payload);
} catch (e) {
console.warn("[omnidisc] call ring failed", errorText(e));
}
});
} catch (e) {
console.warn("[omnidisc] could not subscribe to call rings", errorText(e));
}
try {
applyStatus(await invoke<VoiceStatusWire>("omnidisc_voice_status"));
} catch {
return;
}
}
export function teardownVoice() {
if (unlisten) unlisten();
unlisten = null;
if (unlistenDispatch) unlistenDispatch();
unlistenDispatch = null;
initialized = false;View on GitHub (pinned to 8600b91f42)