// src/services/voiceDiag/checks/wan/wanAppRtpJitter.js // // Per-application audio jitter — measured on ACTUAL RTP voice // traffic via Prisma DPI. Metric name on the v2.6 monitor/metrics // endpoint is `AppPerfUDPAudioJitter` (unit: milliseconds), takes // filter.direction="Ingress" AND filter.path_type=[all]. // // See wanAppRtpMos.js for the app-selection contract — the check is // app-agnostic; the tenant picks which voice app to grade via env. // // Grades against the WORST-window jitter — same reasoning as the // MOS + loss checks: a brief burst that ruins in-flight calls is // exactly what needs surfacing. // // Skipped when the voice-app env is not configured. import { maybeSkippedByKillSwitch, getAppAudio, evaluateAppAudioMetric, getAppJitterWarnMs, getAppJitterErrorMs, } from './_helpers.js'; export const WAN_APP_RTP_JITTER_STANDARDS = Object.freeze({ maxWarnMs: 30, maxErrorMs: 50, unit: 'ms', reference: 'RFC 3550 (jitter buffer tolerance)', gradeAgainst: 'worst-window', }); export const wanAppRtpJitterCheck = { id: 'wanAppRtpJitter', label: 'SD-WAN Voice Traffic Jitter (worst window)', requires: ['sdwanSite'], scope: null, standards: WAN_APP_RTP_JITTER_STANDARDS, async run(ctx) { const skip = maybeSkippedByKillSwitch(wanAppRtpJitterCheck); if (skip) return skip; const audio = getAppAudio(ctx, 'jitter'); const warnThresh = getAppJitterWarnMs(); const errorThresh = getAppJitterErrorMs(); return evaluateAppAudioMetric({ audio, label: 'jitter', unit: 'ms', warnThresh, errorThresh, lowIsBad: false, standardLabel: `warn > ${warnThresh}ms, error > ${errorThresh}ms`, }); }, };