@absolutejs/voice 0.0.22-beta.453 → 0.0.22-beta.455
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/angular/index.d.ts +1 -0
- package/dist/angular/index.js +345 -224
- package/dist/angular/voice-reconnect-profile-evidence.service.d.ts +12 -0
- package/dist/client/index.d.ts +4 -0
- package/dist/client/index.js +659 -240
- package/dist/client/reconnectProfileEvidence.d.ts +19 -0
- package/dist/client/reconnectProfileEvidenceWidget.d.ts +39 -0
- package/dist/index.d.ts +2 -2
- package/dist/index.js +224 -0
- package/dist/proofTrends.d.ts +103 -0
- package/dist/react/VoiceReconnectProfileEvidence.d.ts +6 -0
- package/dist/react/index.d.ts +2 -0
- package/dist/react/index.js +1035 -526
- package/dist/react/useVoiceReconnectProfileEvidence.d.ts +8 -0
- package/dist/svelte/createVoiceReconnectProfileEvidence.d.ts +7 -0
- package/dist/svelte/index.d.ts +1 -0
- package/dist/svelte/index.js +86 -0
- package/dist/vue/VoiceReconnectProfileEvidence.d.ts +21 -0
- package/dist/vue/index.d.ts +2 -0
- package/dist/vue/index.js +941 -438
- package/dist/vue/useVoiceReconnectProfileEvidence.d.ts +9 -0
- package/package.json +1 -1
package/dist/vue/index.js
CHANGED
|
@@ -3335,6 +3335,33 @@ var maxNumber = (values) => {
|
|
|
3335
3335
|
const finite = values.filter((value) => typeof value === "number" && Number.isFinite(value));
|
|
3336
3336
|
return finite.length > 0 ? Math.max(...finite) : undefined;
|
|
3337
3337
|
};
|
|
3338
|
+
var buildVoiceReconnectProfileEvidenceSummary = (evidence, options = {}) => {
|
|
3339
|
+
const profileId = options.profileId ?? "reconnect-resume";
|
|
3340
|
+
const filtered = evidence.filter((record) => record.profileId === profileId).sort((left, right) => {
|
|
3341
|
+
const leftAt = Date.parse(left.generatedAt ?? left.createdAt);
|
|
3342
|
+
const rightAt = Date.parse(right.generatedAt ?? right.createdAt);
|
|
3343
|
+
return (Number.isFinite(rightAt) ? rightAt : 0) - (Number.isFinite(leftAt) ? leftAt : 0);
|
|
3344
|
+
});
|
|
3345
|
+
const latest = filtered[0];
|
|
3346
|
+
const sampleCount = filtered.reduce((total, record) => total + (record.reconnect?.samples ?? 1), 0);
|
|
3347
|
+
const snapshotCount = filtered.reduce((total, record) => total + (record.reconnect?.snapshotCount ?? 0), 0);
|
|
3348
|
+
const resumeLatencyP95Ms = maxNumber(filtered.map((record) => record.reconnect?.resumeLatencyP95Ms));
|
|
3349
|
+
const failed = filtered.some((record) => record.ok === false || record.reconnect?.status === "fail");
|
|
3350
|
+
const passed = filtered.some((record) => record.ok === true && record.reconnect?.resumed === true && record.reconnect?.reconnected === true);
|
|
3351
|
+
const status = filtered.length === 0 ? "empty" : failed ? "fail" : passed ? "pass" : "warn";
|
|
3352
|
+
return {
|
|
3353
|
+
evidence: filtered,
|
|
3354
|
+
generatedAt: options.generatedAt ?? new Date().toISOString(),
|
|
3355
|
+
latest,
|
|
3356
|
+
ok: status === "pass",
|
|
3357
|
+
profileId,
|
|
3358
|
+
resumeLatencyP95Ms,
|
|
3359
|
+
sampleCount,
|
|
3360
|
+
snapshotCount,
|
|
3361
|
+
sourceHref: options.sourceHref,
|
|
3362
|
+
status
|
|
3363
|
+
};
|
|
3364
|
+
};
|
|
3338
3365
|
var percentile = (values, rank) => {
|
|
3339
3366
|
const finite = values.filter((value) => Number.isFinite(value)).sort((left, right) => left - right);
|
|
3340
3367
|
if (finite.length === 0) {
|
|
@@ -3655,6 +3682,133 @@ var buildVoiceRealCallProfileEvidenceFromReconnectProofReports = (input, options
|
|
|
3655
3682
|
};
|
|
3656
3683
|
var loadVoiceRealCallProfileEvidenceFromTraceStore = async (options) => buildVoiceRealCallProfileEvidenceFromTraceEvents(await options.store.list({ limit: options.limit ?? 5000 }), options);
|
|
3657
3684
|
var loadVoiceRealCallProfileEvidenceFromStore = async (options) => options.store.list(options);
|
|
3685
|
+
var readRealCallEvidenceRuntimeKey = (evidence) => [evidence.profileId, evidence.sessionId, evidence.generatedAt ?? ""].join("\x00");
|
|
3686
|
+
var resolveRealCallEvidenceRuntimeReconnectReports = async (reports, options) => {
|
|
3687
|
+
const resolved = typeof reports === "function" ? await reports(options) : reports;
|
|
3688
|
+
if (!resolved) {
|
|
3689
|
+
return [];
|
|
3690
|
+
}
|
|
3691
|
+
return Array.isArray(resolved) ? resolved : [resolved];
|
|
3692
|
+
};
|
|
3693
|
+
var mergeRealCallEvidenceRuntimeOptions = (base, override = {}) => ({
|
|
3694
|
+
dedupe: override.dedupe ?? base.dedupe,
|
|
3695
|
+
evidenceStore: override.evidenceStore ?? base.evidenceStore,
|
|
3696
|
+
existingEvidenceLimit: override.existingEvidenceLimit ?? base.existingEvidenceLimit,
|
|
3697
|
+
history: {
|
|
3698
|
+
...base.history ?? {},
|
|
3699
|
+
...override.history ?? {}
|
|
3700
|
+
},
|
|
3701
|
+
now: override.now ?? base.now,
|
|
3702
|
+
reconnectEvidence: {
|
|
3703
|
+
...base.reconnectEvidence ?? {},
|
|
3704
|
+
...override.reconnectEvidence ?? {}
|
|
3705
|
+
},
|
|
3706
|
+
reconnectReports: override.reconnectReports ?? base.reconnectReports,
|
|
3707
|
+
traceEvidence: mergeRealCallProfileCollectorOptions(base.traceEvidence ?? {}, override.traceEvidence ?? {}),
|
|
3708
|
+
traceStore: override.traceStore ?? base.traceStore
|
|
3709
|
+
});
|
|
3710
|
+
var buildRealCallEvidenceRuntimeReport = async (options, input = {}) => {
|
|
3711
|
+
const evidence = await options.evidenceStore.list({
|
|
3712
|
+
limit: options.existingEvidenceLimit ?? 5000
|
|
3713
|
+
});
|
|
3714
|
+
const history = await buildVoiceRealCallProfileHistoryReportFromStore({
|
|
3715
|
+
...options.history ?? {},
|
|
3716
|
+
limit: options.existingEvidenceLimit ?? 5000,
|
|
3717
|
+
store: options.evidenceStore
|
|
3718
|
+
});
|
|
3719
|
+
const generatedAt = (options.now ?? (() => new Date))().toISOString();
|
|
3720
|
+
const sessions = new Set(evidence.map((record) => record.sessionId)).size;
|
|
3721
|
+
const failedProfiles = history.summary.profiles?.filter((profile) => profile.status === "fail").length;
|
|
3722
|
+
const issues = [
|
|
3723
|
+
...evidence.length === 0 ? ["No real-call profile evidence has been collected yet."] : [],
|
|
3724
|
+
...history.issues
|
|
3725
|
+
];
|
|
3726
|
+
const status = evidence.length === 0 ? "empty" : issues.length > 0 ? history.status === "pass" ? "fail" : history.status : history.status;
|
|
3727
|
+
return {
|
|
3728
|
+
appended: input.appended ?? 0,
|
|
3729
|
+
collected: input.collected ?? [],
|
|
3730
|
+
duplicateKeys: input.duplicateKeys ?? [],
|
|
3731
|
+
evidence,
|
|
3732
|
+
generatedAt,
|
|
3733
|
+
history,
|
|
3734
|
+
issues,
|
|
3735
|
+
ok: status === "pass" && issues.length === 0,
|
|
3736
|
+
skippedDuplicates: input.skippedDuplicates ?? 0,
|
|
3737
|
+
source: "real-call-evidence-runtime",
|
|
3738
|
+
status,
|
|
3739
|
+
summary: {
|
|
3740
|
+
collectedEvidence: input.collected?.length ?? 0,
|
|
3741
|
+
failedProfiles: failedProfiles ?? 0,
|
|
3742
|
+
profiles: history.summary.profileCount,
|
|
3743
|
+
sessions,
|
|
3744
|
+
storedEvidence: evidence.length
|
|
3745
|
+
}
|
|
3746
|
+
};
|
|
3747
|
+
};
|
|
3748
|
+
var collectVoiceRealCallEvidenceRuntimeEvidence = async (options) => {
|
|
3749
|
+
const evidence = [];
|
|
3750
|
+
if (options.traceStore) {
|
|
3751
|
+
evidence.push(...buildVoiceRealCallProfileEvidenceFromTraceEvents(await options.traceStore.list({
|
|
3752
|
+
limit: options.traceEvidence?.limit ?? 5000
|
|
3753
|
+
}), options.traceEvidence));
|
|
3754
|
+
}
|
|
3755
|
+
const reconnectReports = await resolveRealCallEvidenceRuntimeReconnectReports(options.reconnectReports, options);
|
|
3756
|
+
if (reconnectReports.length > 0) {
|
|
3757
|
+
evidence.push(...buildVoiceRealCallProfileEvidenceFromReconnectProofReports(reconnectReports, options.reconnectEvidence));
|
|
3758
|
+
}
|
|
3759
|
+
return evidence;
|
|
3760
|
+
};
|
|
3761
|
+
var createVoiceRealCallEvidenceRuntime = (options) => {
|
|
3762
|
+
const appendEvidence = async (evidenceInput, collectOptions = {}) => {
|
|
3763
|
+
const merged = mergeRealCallEvidenceRuntimeOptions(options, collectOptions);
|
|
3764
|
+
const evidence = Array.isArray(evidenceInput) ? [...evidenceInput] : [evidenceInput];
|
|
3765
|
+
const dedupe = merged.dedupe ?? true;
|
|
3766
|
+
const existing = dedupe ? await merged.evidenceStore.list({
|
|
3767
|
+
limit: merged.existingEvidenceLimit ?? 5000
|
|
3768
|
+
}) : [];
|
|
3769
|
+
const seen = new Set(existing.map(readRealCallEvidenceRuntimeKey));
|
|
3770
|
+
const incomingSeen = new Set;
|
|
3771
|
+
const duplicateKeys = [];
|
|
3772
|
+
let appended = 0;
|
|
3773
|
+
for (const item of evidence) {
|
|
3774
|
+
const key = readRealCallEvidenceRuntimeKey(item);
|
|
3775
|
+
if (dedupe && (seen.has(key) || incomingSeen.has(key))) {
|
|
3776
|
+
duplicateKeys.push(key);
|
|
3777
|
+
continue;
|
|
3778
|
+
}
|
|
3779
|
+
incomingSeen.add(key);
|
|
3780
|
+
await merged.evidenceStore.append(item);
|
|
3781
|
+
appended += 1;
|
|
3782
|
+
}
|
|
3783
|
+
return buildRealCallEvidenceRuntimeReport(merged, {
|
|
3784
|
+
appended,
|
|
3785
|
+
collected: evidence,
|
|
3786
|
+
duplicateKeys,
|
|
3787
|
+
skippedDuplicates: duplicateKeys.length
|
|
3788
|
+
});
|
|
3789
|
+
};
|
|
3790
|
+
return {
|
|
3791
|
+
appendEvidence,
|
|
3792
|
+
buildHistoryReport: async (historyOptions = {}) => buildVoiceRealCallProfileHistoryReportFromStore({
|
|
3793
|
+
...options.history ?? {},
|
|
3794
|
+
...historyOptions,
|
|
3795
|
+
limit: historyOptions.limit ?? options.existingEvidenceLimit ?? 5000,
|
|
3796
|
+
store: options.evidenceStore
|
|
3797
|
+
}),
|
|
3798
|
+
buildReport: async (collectOptions = {}) => buildRealCallEvidenceRuntimeReport(mergeRealCallEvidenceRuntimeOptions(options, collectOptions)),
|
|
3799
|
+
collect: async (collectOptions = {}) => {
|
|
3800
|
+
const merged = mergeRealCallEvidenceRuntimeOptions(options, collectOptions);
|
|
3801
|
+
const evidence = await collectVoiceRealCallEvidenceRuntimeEvidence(merged);
|
|
3802
|
+
return appendEvidence(evidence, {
|
|
3803
|
+
dedupe: merged.dedupe
|
|
3804
|
+
});
|
|
3805
|
+
},
|
|
3806
|
+
listEvidence: async (listOptions = {}) => await options.evidenceStore.list({
|
|
3807
|
+
limit: options.existingEvidenceLimit ?? 5000,
|
|
3808
|
+
...listOptions
|
|
3809
|
+
})
|
|
3810
|
+
};
|
|
3811
|
+
};
|
|
3658
3812
|
var realCallProfileTraceSignalTypes = new Set([
|
|
3659
3813
|
"client.barge_in",
|
|
3660
3814
|
"client.browser_media",
|
|
@@ -5241,6 +5395,31 @@ var renderVoiceRealCallProfileHistoryHTML = (report, title = "Voice Real-Call Pr
|
|
|
5241
5395
|
const issues = report.issues.length === 0 ? "<li>None</li>" : report.issues.map((issue) => `<li>${escapeHtml9(issue)}</li>`).join("");
|
|
5242
5396
|
return `<!doctype html><html lang="en"><head><meta charset="utf-8" /><meta name="viewport" content="width=device-width,initial-scale=1" /><title>${escapeHtml9(title)}</title><style>body{background:#111510;color:#f6f0dd;font-family:ui-sans-serif,system-ui,sans-serif;margin:0}main{margin:auto;max-width:1120px;padding:32px}.hero,article,.card{background:#182117;border:1px solid #32412d;border-radius:24px;margin-bottom:16px;padding:22px}.hero{background:linear-gradient(135deg,rgba(132,204,22,.16),rgba(20,184,166,.12))}.eyebrow{color:#bef264;font-weight:900;letter-spacing:.1em;text-transform:uppercase}h1{font-size:clamp(2.2rem,6vw,4.7rem);letter-spacing:-.06em;line-height:.92;margin:.2rem 0 1rem}.summary{display:flex;flex-wrap:wrap;gap:10px}.pill{border:1px solid #52624b;border-radius:999px;padding:8px 12px}.pass{border-color:rgba(34,197,94,.55)}.warn{border-color:rgba(245,158,11,.7)}.fail{border-color:rgba(239,68,68,.75)}table{border-collapse:collapse;width:100%}td,th{border-bottom:1px solid #32412d;padding:10px;text-align:left}</style></head><body><main><section class="hero"><p class="eyebrow">Real-call benchmark history</p><h1>${escapeHtml9(title)}</h1><p>Generated ${escapeHtml9(report.generatedAt)} from ${escapeHtml9(report.source)}.</p><div class="summary"><span class="pill">Status ${escapeHtml9(report.status)}</span><span class="pill">Reports ${String(report.reports)}</span><span class="pill">Profiles ${String(report.summary.profileCount)}</span><span class="pill">Defaults ${String(report.defaults.summary.actionableProfiles)}/${String(report.defaults.summary.profileCount)}</span><span class="pill">Cycles ${String(report.summary.cycles ?? 0)}</span><span class="pill">Best mix ${escapeHtml9(formatProviderMix(report.recommendations.bestProviders))}</span></div></section><section class="card"><h2>Profiles</h2><table><thead><tr><th>Profile</th><th>Status</th><th>Live p95</th><th>Provider p95</th><th>Turn p95</th><th>Provider mix</th></tr></thead><tbody>${profileRows}</tbody></table></section><section class="card"><h2>Actionable Defaults</h2><table><thead><tr><th>Profile</th><th>Status</th><th>Provider routes</th><th>Live budget</th><th>Provider budget</th><th>Turn budget</th></tr></thead><tbody>${defaultRows}</tbody></table></section>${recommendations}<section class="card"><h2>Issues</h2><ul>${issues}</ul></section></main></body></html>`;
|
|
5243
5397
|
};
|
|
5398
|
+
var renderVoiceRealCallEvidenceRuntimeMarkdown = (report, title = "Voice Real-Call Evidence Runtime") => [
|
|
5399
|
+
`# ${title}`,
|
|
5400
|
+
"",
|
|
5401
|
+
`- Status: ${report.status}`,
|
|
5402
|
+
`- Stored evidence: ${String(report.summary.storedEvidence)}`,
|
|
5403
|
+
`- Collected evidence: ${String(report.summary.collectedEvidence)}`,
|
|
5404
|
+
`- Appended: ${String(report.appended)}`,
|
|
5405
|
+
`- Skipped duplicates: ${String(report.skippedDuplicates)}`,
|
|
5406
|
+
`- Sessions: ${String(report.summary.sessions)}`,
|
|
5407
|
+
`- Profiles: ${String(report.summary.profiles)}`,
|
|
5408
|
+
"",
|
|
5409
|
+
"## Rolling Profile History",
|
|
5410
|
+
"",
|
|
5411
|
+
renderVoiceRealCallProfileHistoryMarkdown(report.history, "Rolling Real-Call Profile History"),
|
|
5412
|
+
"",
|
|
5413
|
+
"## Issues",
|
|
5414
|
+
"",
|
|
5415
|
+
...report.issues.length ? report.issues.map((issue) => `- ${issue}`) : ["- None"]
|
|
5416
|
+
].join(`
|
|
5417
|
+
`);
|
|
5418
|
+
var renderVoiceRealCallEvidenceRuntimeHTML = (report, title = "Voice Real-Call Evidence Runtime") => {
|
|
5419
|
+
const issueItems = report.issues.length === 0 ? "<li>None</li>" : report.issues.map((issue) => `<li>${escapeHtml9(issue)}</li>`).join("");
|
|
5420
|
+
const profileRows = report.history.summary.profiles?.length ? report.history.summary.profiles.map((profile) => `<tr><td>${escapeHtml9(profile.label ?? profile.id)}</td><td>${escapeHtml9(profile.status ?? "unknown")}</td><td>${escapeHtml9(profile.sessionCount ?? "n/a")}</td><td>${escapeHtml9(profile.maxLiveP95Ms ?? "n/a")}</td><td>${escapeHtml9(profile.maxProviderP95Ms ?? "n/a")}</td><td>${escapeHtml9(formatProviderMix(profile.providers ?? []))}</td></tr>`).join("") : '<tr><td colspan="6">No profile history has been collected yet.</td></tr>';
|
|
5421
|
+
return `<!doctype html><html lang="en"><head><meta charset="utf-8" /><meta name="viewport" content="width=device-width,initial-scale=1" /><title>${escapeHtml9(title)}</title><style>body{background:#0f1618;color:#f2f7f2;font-family:ui-sans-serif,system-ui,sans-serif;margin:0}main{margin:auto;max-width:1120px;padding:32px}.hero,.card{background:#162225;border:1px solid #2f4548;border-radius:24px;margin-bottom:16px;padding:22px}.hero{background:linear-gradient(135deg,rgba(20,184,166,.18),rgba(132,204,22,.1))}.eyebrow{color:#99f6e4;font-weight:900;letter-spacing:.1em;text-transform:uppercase}h1{font-size:clamp(2.1rem,6vw,4.3rem);letter-spacing:-.06em;line-height:.94;margin:.2rem 0 1rem}.summary{display:flex;flex-wrap:wrap;gap:10px}.pill{border:1px solid #4b6669;border-radius:999px;padding:8px 12px}.pass{border-color:rgba(34,197,94,.55)}.warn{border-color:rgba(245,158,11,.7)}.fail,.empty,.stale{border-color:rgba(239,68,68,.75)}table{border-collapse:collapse;width:100%}td,th{border-bottom:1px solid #2f4548;padding:10px;text-align:left}</style></head><body><main><section class="hero"><p class="eyebrow">Real-call evidence runtime</p><h1>${escapeHtml9(title)}</h1><p>Generated ${escapeHtml9(report.generatedAt)} from ${escapeHtml9(report.source)}.</p><div class="summary"><span class="pill ${escapeHtml9(report.status)}">Status ${escapeHtml9(report.status)}</span><span class="pill">Stored ${String(report.summary.storedEvidence)}</span><span class="pill">Collected ${String(report.summary.collectedEvidence)}</span><span class="pill">Appended ${String(report.appended)}</span><span class="pill">Duplicates ${String(report.skippedDuplicates)}</span><span class="pill">Sessions ${String(report.summary.sessions)}</span><span class="pill">Profiles ${String(report.summary.profiles)}</span></div></section><section class="card"><h2>Rolling Profile History</h2><table><thead><tr><th>Profile</th><th>Status</th><th>Sessions</th><th>Live p95</th><th>Provider p95</th><th>Provider mix</th></tr></thead><tbody>${profileRows}</tbody></table></section><section class="card"><h2>Issues</h2><ul>${issueItems}</ul></section></main></body></html>`;
|
|
5422
|
+
};
|
|
5244
5423
|
var createVoiceProofTrendRecommendationRoutes = (options) => {
|
|
5245
5424
|
const path = options.path ?? "/api/voice/proof-trend-recommendations";
|
|
5246
5425
|
const htmlPath = options.htmlPath === undefined ? "/voice/proof-trend-recommendations" : options.htmlPath;
|
|
@@ -5324,6 +5503,46 @@ var createVoiceRealCallProfileHistoryRoutes = (options = {}) => {
|
|
|
5324
5503
|
}
|
|
5325
5504
|
return routes;
|
|
5326
5505
|
};
|
|
5506
|
+
var createVoiceRealCallEvidenceRuntimeRoutes = (options) => {
|
|
5507
|
+
const path = options.jsonPath ?? "/api/voice/real-call-evidence-runtime";
|
|
5508
|
+
const collectPath = options.collectPath === undefined ? `${path}/collect` : options.collectPath;
|
|
5509
|
+
const htmlPath = options.htmlPath === undefined ? "/voice/real-call-evidence-runtime" : options.htmlPath;
|
|
5510
|
+
const markdownPath = options.markdownPath === undefined ? "/voice/real-call-evidence-runtime.md" : options.markdownPath;
|
|
5511
|
+
const title = options.title ?? "Voice Real-Call Evidence Runtime";
|
|
5512
|
+
const runtime = options.runtime ?? createVoiceRealCallEvidenceRuntime({
|
|
5513
|
+
...options
|
|
5514
|
+
});
|
|
5515
|
+
const routes = new Elysia4({
|
|
5516
|
+
name: options.name ?? "absolutejs-voice-real-call-evidence-runtime"
|
|
5517
|
+
});
|
|
5518
|
+
routes.get(path, async () => Response.json(await runtime.buildReport(), { headers: options.headers }));
|
|
5519
|
+
if (collectPath !== false) {
|
|
5520
|
+
routes.post(collectPath, async () => Response.json(await runtime.collect(), { headers: options.headers }));
|
|
5521
|
+
}
|
|
5522
|
+
if (htmlPath !== false) {
|
|
5523
|
+
routes.get(htmlPath, async () => {
|
|
5524
|
+
const report = await runtime.buildReport();
|
|
5525
|
+
return new Response(renderVoiceRealCallEvidenceRuntimeHTML(report, title), {
|
|
5526
|
+
headers: {
|
|
5527
|
+
"content-type": "text/html; charset=utf-8",
|
|
5528
|
+
...Object.fromEntries(new Headers(options.headers))
|
|
5529
|
+
}
|
|
5530
|
+
});
|
|
5531
|
+
});
|
|
5532
|
+
}
|
|
5533
|
+
if (markdownPath !== false) {
|
|
5534
|
+
routes.get(markdownPath, async () => {
|
|
5535
|
+
const report = await runtime.buildReport();
|
|
5536
|
+
return new Response(renderVoiceRealCallEvidenceRuntimeMarkdown(report, title), {
|
|
5537
|
+
headers: {
|
|
5538
|
+
"content-type": "text/markdown; charset=utf-8",
|
|
5539
|
+
...Object.fromEntries(new Headers(options.headers))
|
|
5540
|
+
}
|
|
5541
|
+
});
|
|
5542
|
+
});
|
|
5543
|
+
}
|
|
5544
|
+
return routes;
|
|
5545
|
+
};
|
|
5327
5546
|
var realCallProfileActionPaths = {
|
|
5328
5547
|
"collect-browser-proof": "/collect-browser-proof",
|
|
5329
5548
|
"collect-phone-proof": "/collect-phone-proof",
|
|
@@ -5821,8 +6040,290 @@ var VoiceProofTrends = defineComponent5({
|
|
|
5821
6040
|
};
|
|
5822
6041
|
}
|
|
5823
6042
|
});
|
|
6043
|
+
// src/vue/VoiceReconnectProfileEvidence.ts
|
|
6044
|
+
import { defineComponent as defineComponent6, h as h6 } from "vue";
|
|
6045
|
+
|
|
6046
|
+
// src/client/reconnectProfileEvidence.ts
|
|
6047
|
+
var fetchVoiceReconnectProfileEvidence = async (path = "/api/voice/reconnect-profile-evidence", options = {}) => {
|
|
6048
|
+
const fetchImpl = options.fetch ?? globalThis.fetch;
|
|
6049
|
+
const response = await fetchImpl(path);
|
|
6050
|
+
if (!response.ok) {
|
|
6051
|
+
throw new Error(`Voice reconnect profile evidence failed: HTTP ${response.status}`);
|
|
6052
|
+
}
|
|
6053
|
+
return await response.json();
|
|
6054
|
+
};
|
|
6055
|
+
var createVoiceReconnectProfileEvidenceStore = (path = "/api/voice/reconnect-profile-evidence", options = {}) => {
|
|
6056
|
+
const listeners = new Set;
|
|
6057
|
+
let closed = false;
|
|
6058
|
+
let timer;
|
|
6059
|
+
let snapshot = {
|
|
6060
|
+
error: null,
|
|
6061
|
+
isLoading: false
|
|
6062
|
+
};
|
|
6063
|
+
const emit = () => {
|
|
6064
|
+
for (const listener of listeners) {
|
|
6065
|
+
listener();
|
|
6066
|
+
}
|
|
6067
|
+
};
|
|
6068
|
+
const refresh = async () => {
|
|
6069
|
+
if (closed) {
|
|
6070
|
+
return snapshot.report;
|
|
6071
|
+
}
|
|
6072
|
+
snapshot = { ...snapshot, error: null, isLoading: true };
|
|
6073
|
+
emit();
|
|
6074
|
+
try {
|
|
6075
|
+
const report = await fetchVoiceReconnectProfileEvidence(path, options);
|
|
6076
|
+
snapshot = {
|
|
6077
|
+
error: null,
|
|
6078
|
+
isLoading: false,
|
|
6079
|
+
report,
|
|
6080
|
+
updatedAt: Date.now()
|
|
6081
|
+
};
|
|
6082
|
+
emit();
|
|
6083
|
+
return report;
|
|
6084
|
+
} catch (error) {
|
|
6085
|
+
snapshot = {
|
|
6086
|
+
...snapshot,
|
|
6087
|
+
error: error instanceof Error ? error.message : String(error),
|
|
6088
|
+
isLoading: false
|
|
6089
|
+
};
|
|
6090
|
+
emit();
|
|
6091
|
+
throw error;
|
|
6092
|
+
}
|
|
6093
|
+
};
|
|
6094
|
+
const close = () => {
|
|
6095
|
+
closed = true;
|
|
6096
|
+
if (timer) {
|
|
6097
|
+
clearInterval(timer);
|
|
6098
|
+
timer = undefined;
|
|
6099
|
+
}
|
|
6100
|
+
listeners.clear();
|
|
6101
|
+
};
|
|
6102
|
+
if (typeof window !== "undefined" && options.intervalMs && options.intervalMs > 0) {
|
|
6103
|
+
timer = setInterval(() => {
|
|
6104
|
+
refresh().catch(() => {});
|
|
6105
|
+
}, options.intervalMs);
|
|
6106
|
+
}
|
|
6107
|
+
return {
|
|
6108
|
+
close,
|
|
6109
|
+
getServerSnapshot: () => snapshot,
|
|
6110
|
+
getSnapshot: () => snapshot,
|
|
6111
|
+
refresh,
|
|
6112
|
+
subscribe: (listener) => {
|
|
6113
|
+
listeners.add(listener);
|
|
6114
|
+
return () => {
|
|
6115
|
+
listeners.delete(listener);
|
|
6116
|
+
};
|
|
6117
|
+
}
|
|
6118
|
+
};
|
|
6119
|
+
};
|
|
6120
|
+
|
|
6121
|
+
// src/client/reconnectProfileEvidenceWidget.ts
|
|
6122
|
+
var DEFAULT_TITLE6 = "Persisted Reconnect Evidence";
|
|
6123
|
+
var DEFAULT_DESCRIPTION6 = "Real browser reconnect/resume evidence persisted into profile history so recovery claims are backed by durable traces.";
|
|
6124
|
+
var DEFAULT_LINKS3 = [
|
|
6125
|
+
{ href: "/voice/reconnect-contract", label: "Reconnect contract" },
|
|
6126
|
+
{
|
|
6127
|
+
href: "/api/voice/real-call-profile-history",
|
|
6128
|
+
label: "Profile history JSON"
|
|
6129
|
+
}
|
|
6130
|
+
];
|
|
6131
|
+
var escapeHtml11 = (value) => value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'");
|
|
6132
|
+
var formatMs2 = (value) => typeof value === "number" && Number.isFinite(value) ? `${Math.round(value)}ms` : "n/a";
|
|
6133
|
+
var formatCount = (value) => new Intl.NumberFormat("en-US").format(value);
|
|
6134
|
+
var formatAge = (value) => {
|
|
6135
|
+
if (!value) {
|
|
6136
|
+
return "No evidence";
|
|
6137
|
+
}
|
|
6138
|
+
const elapsedMs = Date.now() - Date.parse(value);
|
|
6139
|
+
if (!Number.isFinite(elapsedMs) || elapsedMs < 0) {
|
|
6140
|
+
return "Just now";
|
|
6141
|
+
}
|
|
6142
|
+
const minutes = Math.floor(elapsedMs / 60000);
|
|
6143
|
+
if (minutes < 1) {
|
|
6144
|
+
return "Just now";
|
|
6145
|
+
}
|
|
6146
|
+
if (minutes < 60) {
|
|
6147
|
+
return `${minutes}m ago`;
|
|
6148
|
+
}
|
|
6149
|
+
const hours = Math.floor(minutes / 60);
|
|
6150
|
+
if (hours < 24) {
|
|
6151
|
+
return `${hours}h ago`;
|
|
6152
|
+
}
|
|
6153
|
+
return `${Math.floor(hours / 24)}d ago`;
|
|
6154
|
+
};
|
|
6155
|
+
var createVoiceReconnectProfileEvidenceViewModel = (snapshot, options = {}) => {
|
|
6156
|
+
const report = snapshot.report;
|
|
6157
|
+
const latest = report?.latest;
|
|
6158
|
+
const latestAt = latest?.generatedAt ?? latest?.createdAt;
|
|
6159
|
+
return {
|
|
6160
|
+
description: options.description ?? latest?.profileDescription ?? DEFAULT_DESCRIPTION6,
|
|
6161
|
+
error: snapshot.error,
|
|
6162
|
+
isLoading: snapshot.isLoading,
|
|
6163
|
+
label: snapshot.error ? "Unavailable" : report ? report.status === "pass" ? "Reconnect evidence passing" : report.status === "warn" ? "Reconnect evidence incomplete" : report.status === "fail" ? "Reconnect evidence failing" : "Waiting for reconnect evidence" : snapshot.isLoading ? "Checking" : "No reconnect evidence",
|
|
6164
|
+
latest: latest ? {
|
|
6165
|
+
profileLabel: latest.profileLabel ?? latest.profileId,
|
|
6166
|
+
sessionId: latest.sessionId,
|
|
6167
|
+
surfaces: (latest.surfaces ?? []).join(", ") || "browser"
|
|
6168
|
+
} : undefined,
|
|
6169
|
+
links: options.links ?? DEFAULT_LINKS3,
|
|
6170
|
+
metrics: [
|
|
6171
|
+
{ label: "Samples", value: formatCount(report?.sampleCount ?? 0) },
|
|
6172
|
+
{ label: "Snapshots", value: formatCount(report?.snapshotCount ?? 0) },
|
|
6173
|
+
{
|
|
6174
|
+
label: "Resume p95",
|
|
6175
|
+
value: formatMs2(report?.resumeLatencyP95Ms ?? latest?.reconnect?.resumeLatencyP95Ms)
|
|
6176
|
+
},
|
|
6177
|
+
{ label: "Last proof", value: formatAge(latestAt) }
|
|
6178
|
+
],
|
|
6179
|
+
status: snapshot.error ? "error" : report ? report.status === "pass" ? "ready" : report.status === "empty" ? "empty" : "warning" : snapshot.isLoading ? "loading" : "empty",
|
|
6180
|
+
title: options.title ?? DEFAULT_TITLE6
|
|
6181
|
+
};
|
|
6182
|
+
};
|
|
6183
|
+
var renderVoiceReconnectProfileEvidenceHTML = (snapshot, options = {}) => {
|
|
6184
|
+
const model = createVoiceReconnectProfileEvidenceViewModel(snapshot, options);
|
|
6185
|
+
const metrics = `<div class="absolute-voice-reconnect-evidence__metrics">${model.metrics.map((metric) => `<article>
|
|
6186
|
+
<span>${escapeHtml11(metric.label)}</span>
|
|
6187
|
+
<strong>${escapeHtml11(metric.value)}</strong>
|
|
6188
|
+
</article>`).join("")}</div>`;
|
|
6189
|
+
const latest = model.latest ? `<p class="absolute-voice-reconnect-evidence__latest">Latest ${escapeHtml11(model.latest.profileLabel)} \xB7 ${escapeHtml11(model.latest.sessionId)} \xB7 ${escapeHtml11(model.latest.surfaces)}</p>` : `<p class="absolute-voice-reconnect-evidence__empty">No persisted reconnect profile evidence yet.</p>`;
|
|
6190
|
+
const links = model.links.length ? `<p class="absolute-voice-reconnect-evidence__links">${model.links.map((link) => `<a href="${escapeHtml11(link.href)}">${escapeHtml11(link.label)}</a>`).join("")}</p>` : "";
|
|
6191
|
+
return `<section class="absolute-voice-reconnect-evidence absolute-voice-reconnect-evidence--${escapeHtml11(model.status)}">
|
|
6192
|
+
<header class="absolute-voice-reconnect-evidence__header">
|
|
6193
|
+
<span class="absolute-voice-reconnect-evidence__eyebrow">${escapeHtml11(model.title)}</span>
|
|
6194
|
+
<strong class="absolute-voice-reconnect-evidence__label">${escapeHtml11(model.label)}</strong>
|
|
6195
|
+
</header>
|
|
6196
|
+
<p class="absolute-voice-reconnect-evidence__description">${escapeHtml11(model.description)}</p>
|
|
6197
|
+
${metrics}
|
|
6198
|
+
${latest}
|
|
6199
|
+
${links}
|
|
6200
|
+
${model.error ? `<p class="absolute-voice-reconnect-evidence__error">${escapeHtml11(model.error)}</p>` : ""}
|
|
6201
|
+
</section>`;
|
|
6202
|
+
};
|
|
6203
|
+
var getVoiceReconnectProfileEvidenceCSS = () => `.absolute-voice-reconnect-evidence{border:1px solid #bae6fd;border-radius:20px;background:#f0f9ff;color:#0f172a;padding:18px;box-shadow:0 18px 40px rgba(14,165,233,.12);font-family:inherit}.absolute-voice-reconnect-evidence--warning,.absolute-voice-reconnect-evidence--error{border-color:#fbbf24;background:#fffbeb}.absolute-voice-reconnect-evidence__header{align-items:start;display:flex;gap:12px;justify-content:space-between}.absolute-voice-reconnect-evidence__eyebrow{color:#0369a1;font-size:12px;font-weight:800;letter-spacing:.08em;text-transform:uppercase}.absolute-voice-reconnect-evidence__label{font-size:24px;line-height:1}.absolute-voice-reconnect-evidence__description,.absolute-voice-reconnect-evidence__empty,.absolute-voice-reconnect-evidence__latest{color:#475569}.absolute-voice-reconnect-evidence__metrics{display:grid;gap:10px;grid-template-columns:repeat(4,minmax(0,1fr));margin-top:14px}.absolute-voice-reconnect-evidence__metrics article{background:#fff;border:1px solid #bae6fd;border-radius:16px;padding:12px}.absolute-voice-reconnect-evidence__metrics span{color:#64748b;display:block;font-size:11px;font-weight:800;text-transform:uppercase}.absolute-voice-reconnect-evidence__metrics strong{display:block;font-size:20px;margin-top:4px}.absolute-voice-reconnect-evidence__links{display:flex;flex-wrap:wrap;gap:8px;margin:14px 0 0}.absolute-voice-reconnect-evidence__links a{border:1px solid #7dd3fc;border-radius:999px;color:#0369a1;font-weight:800;padding:6px 10px;text-decoration:none}.absolute-voice-reconnect-evidence__error{color:#9f1239;font-weight:700}@media (max-width:720px){.absolute-voice-reconnect-evidence__metrics{grid-template-columns:repeat(2,minmax(0,1fr))}}`;
|
|
6204
|
+
var mountVoiceReconnectProfileEvidence = (element, path = "/api/voice/reconnect-profile-evidence", options = {}) => {
|
|
6205
|
+
const store = createVoiceReconnectProfileEvidenceStore(path, options);
|
|
6206
|
+
const render = () => {
|
|
6207
|
+
element.innerHTML = renderVoiceReconnectProfileEvidenceHTML(store.getSnapshot(), options);
|
|
6208
|
+
};
|
|
6209
|
+
const unsubscribe = store.subscribe(render);
|
|
6210
|
+
render();
|
|
6211
|
+
store.refresh().catch(() => {});
|
|
6212
|
+
return {
|
|
6213
|
+
close: () => {
|
|
6214
|
+
unsubscribe();
|
|
6215
|
+
store.close();
|
|
6216
|
+
},
|
|
6217
|
+
refresh: store.refresh
|
|
6218
|
+
};
|
|
6219
|
+
};
|
|
6220
|
+
var defineVoiceReconnectProfileEvidenceElement = (tagName = "absolute-voice-reconnect-profile-evidence") => {
|
|
6221
|
+
if (typeof window === "undefined" || typeof customElements === "undefined" || customElements.get(tagName)) {
|
|
6222
|
+
return;
|
|
6223
|
+
}
|
|
6224
|
+
customElements.define(tagName, class AbsoluteVoiceReconnectProfileEvidenceElement extends HTMLElement {
|
|
6225
|
+
mounted;
|
|
6226
|
+
connectedCallback() {
|
|
6227
|
+
const intervalMs = Number(this.getAttribute("interval-ms") ?? 5000);
|
|
6228
|
+
this.mounted = mountVoiceReconnectProfileEvidence(this, this.getAttribute("path") ?? "/api/voice/reconnect-profile-evidence", {
|
|
6229
|
+
description: this.getAttribute("description") ?? undefined,
|
|
6230
|
+
intervalMs: Number.isFinite(intervalMs) ? intervalMs : 5000,
|
|
6231
|
+
title: this.getAttribute("title") ?? undefined
|
|
6232
|
+
});
|
|
6233
|
+
}
|
|
6234
|
+
disconnectedCallback() {
|
|
6235
|
+
this.mounted?.close();
|
|
6236
|
+
this.mounted = undefined;
|
|
6237
|
+
}
|
|
6238
|
+
});
|
|
6239
|
+
};
|
|
6240
|
+
|
|
6241
|
+
// src/vue/useVoiceReconnectProfileEvidence.ts
|
|
6242
|
+
import { onUnmounted as onUnmounted6, ref as ref6, shallowRef as shallowRef6 } from "vue";
|
|
6243
|
+
function useVoiceReconnectProfileEvidence(path = "/api/voice/reconnect-profile-evidence", options = {}) {
|
|
6244
|
+
const store = createVoiceReconnectProfileEvidenceStore(path, options);
|
|
6245
|
+
const error = ref6(null);
|
|
6246
|
+
const isLoading = ref6(false);
|
|
6247
|
+
const report = shallowRef6(undefined);
|
|
6248
|
+
const updatedAt = ref6(undefined);
|
|
6249
|
+
const sync = () => {
|
|
6250
|
+
const snapshot = store.getSnapshot();
|
|
6251
|
+
error.value = snapshot.error;
|
|
6252
|
+
isLoading.value = snapshot.isLoading;
|
|
6253
|
+
report.value = snapshot.report;
|
|
6254
|
+
updatedAt.value = snapshot.updatedAt;
|
|
6255
|
+
};
|
|
6256
|
+
const unsubscribe = store.subscribe(sync);
|
|
6257
|
+
sync();
|
|
6258
|
+
if (typeof window !== "undefined") {
|
|
6259
|
+
store.refresh().catch(() => {});
|
|
6260
|
+
}
|
|
6261
|
+
onUnmounted6(() => {
|
|
6262
|
+
unsubscribe();
|
|
6263
|
+
store.close();
|
|
6264
|
+
});
|
|
6265
|
+
return {
|
|
6266
|
+
error,
|
|
6267
|
+
isLoading,
|
|
6268
|
+
refresh: store.refresh,
|
|
6269
|
+
report,
|
|
6270
|
+
updatedAt
|
|
6271
|
+
};
|
|
6272
|
+
}
|
|
6273
|
+
|
|
6274
|
+
// src/vue/VoiceReconnectProfileEvidence.ts
|
|
6275
|
+
var VoiceReconnectProfileEvidence = defineComponent6({
|
|
6276
|
+
name: "VoiceReconnectProfileEvidence",
|
|
6277
|
+
props: {
|
|
6278
|
+
description: String,
|
|
6279
|
+
intervalMs: Number,
|
|
6280
|
+
path: {
|
|
6281
|
+
default: "/api/voice/reconnect-profile-evidence",
|
|
6282
|
+
type: String
|
|
6283
|
+
},
|
|
6284
|
+
title: String
|
|
6285
|
+
},
|
|
6286
|
+
setup(props) {
|
|
6287
|
+
const state = useVoiceReconnectProfileEvidence(props.path, {
|
|
6288
|
+
description: props.description,
|
|
6289
|
+
intervalMs: props.intervalMs,
|
|
6290
|
+
title: props.title
|
|
6291
|
+
});
|
|
6292
|
+
return () => {
|
|
6293
|
+
const model = createVoiceReconnectProfileEvidenceViewModel({
|
|
6294
|
+
error: state.error.value,
|
|
6295
|
+
isLoading: state.isLoading.value,
|
|
6296
|
+
report: state.report.value,
|
|
6297
|
+
updatedAt: state.updatedAt.value
|
|
6298
|
+
}, {
|
|
6299
|
+
description: props.description,
|
|
6300
|
+
intervalMs: props.intervalMs,
|
|
6301
|
+
title: props.title
|
|
6302
|
+
});
|
|
6303
|
+
return h6("section", {
|
|
6304
|
+
class: [
|
|
6305
|
+
"absolute-voice-reconnect-evidence",
|
|
6306
|
+
`absolute-voice-reconnect-evidence--${model.status}`
|
|
6307
|
+
]
|
|
6308
|
+
}, [
|
|
6309
|
+
h6("header", { class: "absolute-voice-reconnect-evidence__header" }, [
|
|
6310
|
+
h6("span", { class: "absolute-voice-reconnect-evidence__eyebrow" }, model.title),
|
|
6311
|
+
h6("strong", { class: "absolute-voice-reconnect-evidence__label" }, model.label)
|
|
6312
|
+
]),
|
|
6313
|
+
h6("p", { class: "absolute-voice-reconnect-evidence__description" }, model.description),
|
|
6314
|
+
h6("div", { class: "absolute-voice-reconnect-evidence__metrics" }, model.metrics.map((metric) => h6("article", { key: metric.label }, [
|
|
6315
|
+
h6("span", metric.label),
|
|
6316
|
+
h6("strong", metric.value)
|
|
6317
|
+
]))),
|
|
6318
|
+
model.latest ? h6("p", { class: "absolute-voice-reconnect-evidence__latest" }, `Latest ${model.latest.profileLabel} \xB7 ${model.latest.sessionId} \xB7 ${model.latest.surfaces}`) : h6("p", { class: "absolute-voice-reconnect-evidence__empty" }, "No persisted reconnect profile evidence yet."),
|
|
6319
|
+
model.links.length ? h6("p", { class: "absolute-voice-reconnect-evidence__links" }, model.links.map((link) => h6("a", { href: link.href, key: link.href }, link.label))) : null,
|
|
6320
|
+
model.error ? h6("p", { class: "absolute-voice-reconnect-evidence__error" }, model.error) : null
|
|
6321
|
+
]);
|
|
6322
|
+
};
|
|
6323
|
+
}
|
|
6324
|
+
});
|
|
5824
6325
|
// src/vue/VoiceCallDebuggerLaunch.ts
|
|
5825
|
-
import { computed as computed2, defineComponent as
|
|
6326
|
+
import { computed as computed2, defineComponent as defineComponent7, h as h7 } from "vue";
|
|
5826
6327
|
|
|
5827
6328
|
// src/client/callDebugger.ts
|
|
5828
6329
|
var fetchVoiceCallDebugger = async (path, options = {}) => {
|
|
@@ -5900,10 +6401,10 @@ var createVoiceCallDebuggerStore = (path, options = {}) => {
|
|
|
5900
6401
|
};
|
|
5901
6402
|
|
|
5902
6403
|
// src/client/callDebuggerWidget.ts
|
|
5903
|
-
var
|
|
5904
|
-
var
|
|
6404
|
+
var DEFAULT_TITLE7 = "Call Debugger";
|
|
6405
|
+
var DEFAULT_DESCRIPTION7 = "Open the latest call artifact with snapshot, operations record, failure replay, provider path, transcript, and incident markdown.";
|
|
5905
6406
|
var DEFAULT_LINK_LABEL = "Open debugger";
|
|
5906
|
-
var
|
|
6407
|
+
var escapeHtml12 = (value) => value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'");
|
|
5907
6408
|
var defaultHref = (path, report) => {
|
|
5908
6409
|
if (path.startsWith("/api/voice-call-debugger/")) {
|
|
5909
6410
|
return path.replace("/api/voice-call-debugger/", "/voice-call-debugger/");
|
|
@@ -5920,7 +6421,7 @@ var createVoiceCallDebuggerLaunchViewModel = (path, state, options = {}) => {
|
|
|
5920
6421
|
const report = state.report;
|
|
5921
6422
|
const href = resolveHref(path, state, options);
|
|
5922
6423
|
return {
|
|
5923
|
-
description: options.description ??
|
|
6424
|
+
description: options.description ?? DEFAULT_DESCRIPTION7,
|
|
5924
6425
|
error: state.error,
|
|
5925
6426
|
href,
|
|
5926
6427
|
isLoading: state.isLoading,
|
|
@@ -5949,25 +6450,25 @@ var createVoiceCallDebuggerLaunchViewModel = (path, state, options = {}) => {
|
|
|
5949
6450
|
{ label: "Snapshot", value: report.snapshot.status }
|
|
5950
6451
|
] : [],
|
|
5951
6452
|
status: state.error ? "error" : report ? report.status === "healthy" ? "ready" : "warning" : state.isLoading ? "loading" : "empty",
|
|
5952
|
-
title: options.title ??
|
|
6453
|
+
title: options.title ?? DEFAULT_TITLE7,
|
|
5953
6454
|
updatedAt: state.updatedAt
|
|
5954
6455
|
};
|
|
5955
6456
|
};
|
|
5956
6457
|
var renderVoiceCallDebuggerLaunchHTML = (path, state, options = {}) => {
|
|
5957
6458
|
const model = createVoiceCallDebuggerLaunchViewModel(path, state, options);
|
|
5958
6459
|
const rows = model.rows.length ? `<dl>${model.rows.map((row) => `<div>
|
|
5959
|
-
<dt>${
|
|
5960
|
-
<dd>${
|
|
6460
|
+
<dt>${escapeHtml12(row.label)}</dt>
|
|
6461
|
+
<dd>${escapeHtml12(row.value)}</dd>
|
|
5961
6462
|
</div>`).join("")}</dl>` : '<p class="absolute-voice-call-debugger-launch__empty">Load a call debugger report to see the latest support artifact.</p>';
|
|
5962
|
-
return `<section class="absolute-voice-call-debugger-launch absolute-voice-call-debugger-launch--${
|
|
6463
|
+
return `<section class="absolute-voice-call-debugger-launch absolute-voice-call-debugger-launch--${escapeHtml12(model.status)}">
|
|
5963
6464
|
<header class="absolute-voice-call-debugger-launch__header">
|
|
5964
|
-
<span class="absolute-voice-call-debugger-launch__eyebrow">${
|
|
5965
|
-
<strong class="absolute-voice-call-debugger-launch__label">${
|
|
6465
|
+
<span class="absolute-voice-call-debugger-launch__eyebrow">${escapeHtml12(model.title)}</span>
|
|
6466
|
+
<strong class="absolute-voice-call-debugger-launch__label">${escapeHtml12(model.label)}</strong>
|
|
5966
6467
|
</header>
|
|
5967
|
-
<p class="absolute-voice-call-debugger-launch__description">${
|
|
5968
|
-
<a class="absolute-voice-call-debugger-launch__link" href="${
|
|
6468
|
+
<p class="absolute-voice-call-debugger-launch__description">${escapeHtml12(model.description)}</p>
|
|
6469
|
+
<a class="absolute-voice-call-debugger-launch__link" href="${escapeHtml12(model.href)}">${escapeHtml12(options.linkLabel ?? DEFAULT_LINK_LABEL)}</a>
|
|
5969
6470
|
${rows}
|
|
5970
|
-
${model.error ? `<p class="absolute-voice-call-debugger-launch__error">${
|
|
6471
|
+
${model.error ? `<p class="absolute-voice-call-debugger-launch__error">${escapeHtml12(model.error)}</p>` : ""}
|
|
5971
6472
|
</section>`;
|
|
5972
6473
|
};
|
|
5973
6474
|
var mountVoiceCallDebuggerLaunch = (element, path, options = {}) => {
|
|
@@ -6010,13 +6511,13 @@ var defineVoiceCallDebuggerLaunchElement = (tagName = "absolute-voice-call-debug
|
|
|
6010
6511
|
};
|
|
6011
6512
|
|
|
6012
6513
|
// src/vue/useVoiceCallDebugger.ts
|
|
6013
|
-
import { computed, onUnmounted as
|
|
6514
|
+
import { computed, onUnmounted as onUnmounted7, shallowRef as shallowRef7 } from "vue";
|
|
6014
6515
|
function useVoiceCallDebugger(path, options = {}) {
|
|
6015
6516
|
const store = createVoiceCallDebuggerStore(path, options);
|
|
6016
|
-
const error =
|
|
6017
|
-
const isLoading =
|
|
6018
|
-
const report =
|
|
6019
|
-
const updatedAt =
|
|
6517
|
+
const error = shallowRef7(null);
|
|
6518
|
+
const isLoading = shallowRef7(false);
|
|
6519
|
+
const report = shallowRef7();
|
|
6520
|
+
const updatedAt = shallowRef7();
|
|
6020
6521
|
const sync = () => {
|
|
6021
6522
|
const state = store.getSnapshot();
|
|
6022
6523
|
error.value = state.error;
|
|
@@ -6027,7 +6528,7 @@ function useVoiceCallDebugger(path, options = {}) {
|
|
|
6027
6528
|
const unsubscribe = store.subscribe(sync);
|
|
6028
6529
|
sync();
|
|
6029
6530
|
store.refresh().catch(() => {});
|
|
6030
|
-
|
|
6531
|
+
onUnmounted7(() => {
|
|
6031
6532
|
unsubscribe();
|
|
6032
6533
|
store.close();
|
|
6033
6534
|
});
|
|
@@ -6042,7 +6543,7 @@ function useVoiceCallDebugger(path, options = {}) {
|
|
|
6042
6543
|
}
|
|
6043
6544
|
|
|
6044
6545
|
// src/vue/VoiceCallDebuggerLaunch.ts
|
|
6045
|
-
var VoiceCallDebuggerLaunch =
|
|
6546
|
+
var VoiceCallDebuggerLaunch = defineComponent7({
|
|
6046
6547
|
name: "VoiceCallDebuggerLaunch",
|
|
6047
6548
|
props: {
|
|
6048
6549
|
class: { default: "", type: String },
|
|
@@ -6068,32 +6569,32 @@ var VoiceCallDebuggerLaunch = defineComponent6({
|
|
|
6068
6569
|
report: state.report.value,
|
|
6069
6570
|
updatedAt: state.updatedAt.value
|
|
6070
6571
|
}, options));
|
|
6071
|
-
return () =>
|
|
6572
|
+
return () => h7("section", {
|
|
6072
6573
|
class: [
|
|
6073
6574
|
"absolute-voice-call-debugger-launch",
|
|
6074
6575
|
`absolute-voice-call-debugger-launch--${model.value.status}`,
|
|
6075
6576
|
props.class
|
|
6076
6577
|
]
|
|
6077
6578
|
}, [
|
|
6078
|
-
|
|
6079
|
-
|
|
6080
|
-
|
|
6579
|
+
h7("header", { class: "absolute-voice-call-debugger-launch__header" }, [
|
|
6580
|
+
h7("span", { class: "absolute-voice-call-debugger-launch__eyebrow" }, model.value.title),
|
|
6581
|
+
h7("strong", { class: "absolute-voice-call-debugger-launch__label" }, model.value.label)
|
|
6081
6582
|
]),
|
|
6082
|
-
|
|
6083
|
-
|
|
6583
|
+
h7("p", { class: "absolute-voice-call-debugger-launch__description" }, model.value.description),
|
|
6584
|
+
h7("a", {
|
|
6084
6585
|
class: "absolute-voice-call-debugger-launch__link",
|
|
6085
6586
|
href: model.value.href
|
|
6086
6587
|
}, props.linkLabel ?? "Open debugger"),
|
|
6087
|
-
model.value.rows.length ?
|
|
6088
|
-
|
|
6089
|
-
|
|
6090
|
-
]))) :
|
|
6091
|
-
model.value.error ?
|
|
6588
|
+
model.value.rows.length ? h7("dl", model.value.rows.map((row) => h7("div", { key: row.label }, [
|
|
6589
|
+
h7("dt", row.label),
|
|
6590
|
+
h7("dd", row.value)
|
|
6591
|
+
]))) : h7("p", { class: "absolute-voice-call-debugger-launch__empty" }, "Load a call debugger report to see the latest support artifact."),
|
|
6592
|
+
model.value.error ? h7("p", { class: "absolute-voice-call-debugger-launch__error" }, model.value.error) : null
|
|
6092
6593
|
]);
|
|
6093
6594
|
}
|
|
6094
6595
|
});
|
|
6095
6596
|
// src/vue/VoiceSessionSnapshot.ts
|
|
6096
|
-
import { computed as computed3, defineComponent as
|
|
6597
|
+
import { computed as computed3, defineComponent as defineComponent8, h as h8 } from "vue";
|
|
6097
6598
|
|
|
6098
6599
|
// src/client/sessionSnapshot.ts
|
|
6099
6600
|
var withTurnId = (path, turnId) => {
|
|
@@ -6189,10 +6690,10 @@ var createVoiceSessionSnapshotStore = (path, options = {}) => {
|
|
|
6189
6690
|
};
|
|
6190
6691
|
|
|
6191
6692
|
// src/client/sessionSnapshotWidget.ts
|
|
6192
|
-
var
|
|
6193
|
-
var
|
|
6693
|
+
var DEFAULT_TITLE8 = "Session Snapshot";
|
|
6694
|
+
var DEFAULT_DESCRIPTION8 = "Portable call artifact with media graph, provider routing, proof, quality, and telephony evidence.";
|
|
6194
6695
|
var DEFAULT_DOWNLOAD_LABEL = "Download snapshot";
|
|
6195
|
-
var
|
|
6696
|
+
var escapeHtml13 = (value) => value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'");
|
|
6196
6697
|
var formatStatus2 = (status) => status ?? "n/a";
|
|
6197
6698
|
var createVoiceSessionSnapshotViewModel = (state, options = {}) => {
|
|
6198
6699
|
const snapshot = state.snapshot;
|
|
@@ -6208,7 +6709,7 @@ var createVoiceSessionSnapshotViewModel = (state, options = {}) => {
|
|
|
6208
6709
|
label: artifact.label,
|
|
6209
6710
|
status: formatStatus2(artifact.status)
|
|
6210
6711
|
})) ?? [],
|
|
6211
|
-
description: options.description ??
|
|
6712
|
+
description: options.description ?? DEFAULT_DESCRIPTION8,
|
|
6212
6713
|
error: state.error,
|
|
6213
6714
|
isLoading: state.isLoading,
|
|
6214
6715
|
label: state.error ? "Unavailable" : snapshot ? `${snapshot.status} \xB7 ${snapshot.sessionId}` : state.isLoading ? "Loading" : "No snapshot",
|
|
@@ -6235,30 +6736,30 @@ var createVoiceSessionSnapshotViewModel = (state, options = {}) => {
|
|
|
6235
6736
|
] : [],
|
|
6236
6737
|
showDownload: snapshot !== undefined,
|
|
6237
6738
|
status: state.error ? "error" : snapshot ? snapshot.status === "pass" ? "ready" : "warning" : state.isLoading ? "loading" : "empty",
|
|
6238
|
-
title: options.title ??
|
|
6739
|
+
title: options.title ?? DEFAULT_TITLE8,
|
|
6239
6740
|
updatedAt: state.updatedAt
|
|
6240
6741
|
};
|
|
6241
6742
|
};
|
|
6242
6743
|
var renderVoiceSessionSnapshotHTML = (state, options = {}) => {
|
|
6243
6744
|
const model = createVoiceSessionSnapshotViewModel(state, options);
|
|
6244
6745
|
const rows = model.rows.length ? `<dl>${model.rows.map((row) => `<div>
|
|
6245
|
-
<dt>${
|
|
6246
|
-
<dd>${
|
|
6746
|
+
<dt>${escapeHtml13(row.label)}</dt>
|
|
6747
|
+
<dd>${escapeHtml13(row.value)}</dd>
|
|
6247
6748
|
</div>`).join("")}</dl>` : '<p class="absolute-voice-session-snapshot__empty">Load a session snapshot to see support diagnostics.</p>';
|
|
6248
6749
|
const artifacts = model.artifacts.length ? `<div class="absolute-voice-session-snapshot__artifacts">${model.artifacts.map((artifact) => {
|
|
6249
|
-
const body = `<strong>${
|
|
6250
|
-
return artifact.href ? `<a href="${
|
|
6750
|
+
const body = `<strong>${escapeHtml13(artifact.label)}</strong><span>${escapeHtml13(artifact.status)}</span>`;
|
|
6751
|
+
return artifact.href ? `<a href="${escapeHtml13(artifact.href)}">${body}</a>` : `<div>${body}</div>`;
|
|
6251
6752
|
}).join("")}</div>` : "";
|
|
6252
|
-
return `<section class="absolute-voice-session-snapshot absolute-voice-session-snapshot--${
|
|
6753
|
+
return `<section class="absolute-voice-session-snapshot absolute-voice-session-snapshot--${escapeHtml13(model.status)}">
|
|
6253
6754
|
<header class="absolute-voice-session-snapshot__header">
|
|
6254
|
-
<span class="absolute-voice-session-snapshot__eyebrow">${
|
|
6255
|
-
<strong class="absolute-voice-session-snapshot__label">${
|
|
6755
|
+
<span class="absolute-voice-session-snapshot__eyebrow">${escapeHtml13(model.title)}</span>
|
|
6756
|
+
<strong class="absolute-voice-session-snapshot__label">${escapeHtml13(model.label)}</strong>
|
|
6256
6757
|
</header>
|
|
6257
|
-
<p class="absolute-voice-session-snapshot__description">${
|
|
6258
|
-
${model.showDownload ? `<button class="absolute-voice-session-snapshot__download" data-absolute-voice-session-snapshot-download type="button">${
|
|
6758
|
+
<p class="absolute-voice-session-snapshot__description">${escapeHtml13(model.description)}</p>
|
|
6759
|
+
${model.showDownload ? `<button class="absolute-voice-session-snapshot__download" data-absolute-voice-session-snapshot-download type="button">${escapeHtml13(options.downloadLabel ?? DEFAULT_DOWNLOAD_LABEL)}</button>` : ""}
|
|
6259
6760
|
${rows}
|
|
6260
6761
|
${artifacts}
|
|
6261
|
-
${model.error ? `<p class="absolute-voice-session-snapshot__error">${
|
|
6762
|
+
${model.error ? `<p class="absolute-voice-session-snapshot__error">${escapeHtml13(model.error)}</p>` : ""}
|
|
6262
6763
|
</section>`;
|
|
6263
6764
|
};
|
|
6264
6765
|
var downloadBlob = (blob, filename) => {
|
|
@@ -6322,13 +6823,13 @@ var defineVoiceSessionSnapshotElement = (tagName = "absolute-voice-session-snaps
|
|
|
6322
6823
|
};
|
|
6323
6824
|
|
|
6324
6825
|
// src/vue/useVoiceSessionSnapshot.ts
|
|
6325
|
-
import { onUnmounted as
|
|
6826
|
+
import { onUnmounted as onUnmounted8, shallowRef as shallowRef8 } from "vue";
|
|
6326
6827
|
function useVoiceSessionSnapshot(path, options = {}) {
|
|
6327
6828
|
const store = createVoiceSessionSnapshotStore(path, options);
|
|
6328
|
-
const error =
|
|
6329
|
-
const isLoading =
|
|
6330
|
-
const snapshot =
|
|
6331
|
-
const updatedAt =
|
|
6829
|
+
const error = shallowRef8(null);
|
|
6830
|
+
const isLoading = shallowRef8(false);
|
|
6831
|
+
const snapshot = shallowRef8();
|
|
6832
|
+
const updatedAt = shallowRef8(undefined);
|
|
6332
6833
|
const sync = () => {
|
|
6333
6834
|
const state = store.getSnapshot();
|
|
6334
6835
|
error.value = state.error;
|
|
@@ -6339,7 +6840,7 @@ function useVoiceSessionSnapshot(path, options = {}) {
|
|
|
6339
6840
|
const unsubscribe = store.subscribe(sync);
|
|
6340
6841
|
sync();
|
|
6341
6842
|
store.refresh().catch(() => {});
|
|
6342
|
-
|
|
6843
|
+
onUnmounted8(() => {
|
|
6343
6844
|
unsubscribe();
|
|
6344
6845
|
store.close();
|
|
6345
6846
|
});
|
|
@@ -6354,7 +6855,7 @@ function useVoiceSessionSnapshot(path, options = {}) {
|
|
|
6354
6855
|
}
|
|
6355
6856
|
|
|
6356
6857
|
// src/vue/VoiceSessionSnapshot.ts
|
|
6357
|
-
var VoiceSessionSnapshot =
|
|
6858
|
+
var VoiceSessionSnapshot = defineComponent8({
|
|
6358
6859
|
name: "VoiceSessionSnapshot",
|
|
6359
6860
|
props: {
|
|
6360
6861
|
class: { default: "", type: String },
|
|
@@ -6380,33 +6881,33 @@ var VoiceSessionSnapshot = defineComponent7({
|
|
|
6380
6881
|
snapshot: state.snapshot.value,
|
|
6381
6882
|
updatedAt: state.updatedAt.value
|
|
6382
6883
|
}, options));
|
|
6383
|
-
return () =>
|
|
6884
|
+
return () => h8("section", {
|
|
6384
6885
|
class: [
|
|
6385
6886
|
"absolute-voice-session-snapshot",
|
|
6386
6887
|
`absolute-voice-session-snapshot--${model.value.status}`,
|
|
6387
6888
|
props.class
|
|
6388
6889
|
]
|
|
6389
6890
|
}, [
|
|
6390
|
-
|
|
6391
|
-
|
|
6392
|
-
|
|
6891
|
+
h8("header", { class: "absolute-voice-session-snapshot__header" }, [
|
|
6892
|
+
h8("span", { class: "absolute-voice-session-snapshot__eyebrow" }, model.value.title),
|
|
6893
|
+
h8("strong", { class: "absolute-voice-session-snapshot__label" }, model.value.label)
|
|
6393
6894
|
]),
|
|
6394
|
-
|
|
6395
|
-
model.value.showDownload ?
|
|
6895
|
+
h8("p", { class: "absolute-voice-session-snapshot__description" }, model.value.description),
|
|
6896
|
+
model.value.showDownload ? h8("button", {
|
|
6396
6897
|
class: "absolute-voice-session-snapshot__download",
|
|
6397
6898
|
onClick: () => state.download(),
|
|
6398
6899
|
type: "button"
|
|
6399
6900
|
}, props.downloadLabel ?? "Download snapshot") : null,
|
|
6400
|
-
model.value.rows.length ?
|
|
6401
|
-
|
|
6402
|
-
|
|
6403
|
-
]))) :
|
|
6404
|
-
model.value.error ?
|
|
6901
|
+
model.value.rows.length ? h8("dl", model.value.rows.map((row) => h8("div", { key: row.label }, [
|
|
6902
|
+
h8("dt", row.label),
|
|
6903
|
+
h8("dd", row.value)
|
|
6904
|
+
]))) : h8("p", { class: "absolute-voice-session-snapshot__empty" }, "Load a session snapshot to see support diagnostics."),
|
|
6905
|
+
model.value.error ? h8("p", { class: "absolute-voice-session-snapshot__error" }, model.value.error) : null
|
|
6405
6906
|
]);
|
|
6406
6907
|
}
|
|
6407
6908
|
});
|
|
6408
6909
|
// src/vue/VoiceReadinessFailures.ts
|
|
6409
|
-
import { defineComponent as
|
|
6910
|
+
import { defineComponent as defineComponent9, h as h9 } from "vue";
|
|
6410
6911
|
|
|
6411
6912
|
// src/client/readinessFailures.ts
|
|
6412
6913
|
var fetchVoiceReadinessFailures = async (path = "/api/production-readiness", options = {}) => {
|
|
@@ -6484,13 +6985,13 @@ var createVoiceReadinessFailuresStore = (path = "/api/production-readiness", opt
|
|
|
6484
6985
|
};
|
|
6485
6986
|
|
|
6486
6987
|
// src/client/readinessFailuresWidget.ts
|
|
6487
|
-
var
|
|
6488
|
-
var
|
|
6489
|
-
var
|
|
6988
|
+
var DEFAULT_TITLE9 = "Readiness Gate Explanations";
|
|
6989
|
+
var DEFAULT_DESCRIPTION9 = "Structured reasons for calibrated production-readiness warnings and failures.";
|
|
6990
|
+
var DEFAULT_LINKS4 = [
|
|
6490
6991
|
{ href: "/production-readiness", label: "Readiness page" },
|
|
6491
6992
|
{ href: "/voice/slo-readiness-thresholds", label: "Gate thresholds" }
|
|
6492
6993
|
];
|
|
6493
|
-
var
|
|
6994
|
+
var escapeHtml14 = (value) => value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'");
|
|
6494
6995
|
var formatExplanationValue = (value, unit) => {
|
|
6495
6996
|
if (value === undefined || value === null) {
|
|
6496
6997
|
return "n/a";
|
|
@@ -6518,36 +7019,36 @@ var createVoiceReadinessFailuresViewModel = (snapshot, options = {}) => {
|
|
|
6518
7019
|
const failures = snapshot.report?.checks.map(toFailureView).filter((value) => !!value) ?? [];
|
|
6519
7020
|
const hasOpenIssues = failures.length > 0;
|
|
6520
7021
|
return {
|
|
6521
|
-
description: options.description ??
|
|
7022
|
+
description: options.description ?? DEFAULT_DESCRIPTION9,
|
|
6522
7023
|
error: snapshot.error,
|
|
6523
7024
|
failures,
|
|
6524
7025
|
isLoading: snapshot.isLoading,
|
|
6525
7026
|
label: snapshot.error ? "Unavailable" : snapshot.report ? hasOpenIssues ? `${failures.length} calibrated gate issue(s)` : "No calibrated gate issues" : snapshot.isLoading ? "Checking" : "No readiness report",
|
|
6526
|
-
links: options.links ??
|
|
7027
|
+
links: options.links ?? DEFAULT_LINKS4,
|
|
6527
7028
|
status: snapshot.error ? "error" : snapshot.report ? hasOpenIssues ? "warning" : "ready" : snapshot.isLoading ? "loading" : "empty",
|
|
6528
|
-
title: options.title ??
|
|
7029
|
+
title: options.title ?? DEFAULT_TITLE9,
|
|
6529
7030
|
updatedAt: snapshot.updatedAt
|
|
6530
7031
|
};
|
|
6531
7032
|
};
|
|
6532
7033
|
var renderVoiceReadinessFailuresHTML = (snapshot, options = {}) => {
|
|
6533
7034
|
const model = createVoiceReadinessFailuresViewModel(snapshot, options);
|
|
6534
|
-
const failures = model.failures.length ? `<div class="absolute-voice-readiness-failures__items">${model.failures.map((failure) => `<article class="absolute-voice-readiness-failures__item absolute-voice-readiness-failures__item--${
|
|
6535
|
-
<span>${
|
|
6536
|
-
<strong>${
|
|
6537
|
-
<p>Observed ${
|
|
6538
|
-
<p>${
|
|
6539
|
-
<p class="absolute-voice-readiness-failures__links">${failure.evidenceHref ? `<a href="${
|
|
6540
|
-
</article>`).join("")}</div>` : `<p class="absolute-voice-readiness-failures__empty">${model.error ?
|
|
6541
|
-
const links = model.links.length ? `<p class="absolute-voice-readiness-failures__links">${model.links.map((link) => `<a href="${
|
|
6542
|
-
return `<section class="absolute-voice-readiness-failures absolute-voice-readiness-failures--${
|
|
7035
|
+
const failures = model.failures.length ? `<div class="absolute-voice-readiness-failures__items">${model.failures.map((failure) => `<article class="absolute-voice-readiness-failures__item absolute-voice-readiness-failures__item--${escapeHtml14(failure.status)}">
|
|
7036
|
+
<span>${escapeHtml14(failure.status.toUpperCase())}</span>
|
|
7037
|
+
<strong>${escapeHtml14(failure.label)}</strong>
|
|
7038
|
+
<p>Observed ${escapeHtml14(failure.observed)} against ${escapeHtml14(failure.thresholdLabel)} ${escapeHtml14(failure.threshold)}.</p>
|
|
7039
|
+
<p>${escapeHtml14(failure.remediation)}</p>
|
|
7040
|
+
<p class="absolute-voice-readiness-failures__links">${failure.evidenceHref ? `<a href="${escapeHtml14(failure.evidenceHref)}">Evidence</a>` : ""}${failure.sourceHref ? `<a href="${escapeHtml14(failure.sourceHref)}">Threshold source</a>` : ""}</p>
|
|
7041
|
+
</article>`).join("")}</div>` : `<p class="absolute-voice-readiness-failures__empty">${model.error ? escapeHtml14(model.error) : "No calibrated readiness gate explanations are open."}</p>`;
|
|
7042
|
+
const links = model.links.length ? `<p class="absolute-voice-readiness-failures__links">${model.links.map((link) => `<a href="${escapeHtml14(link.href)}">${escapeHtml14(link.label)}</a>`).join("")}</p>` : "";
|
|
7043
|
+
return `<section class="absolute-voice-readiness-failures absolute-voice-readiness-failures--${escapeHtml14(model.status)}">
|
|
6543
7044
|
<header class="absolute-voice-readiness-failures__header">
|
|
6544
|
-
<span class="absolute-voice-readiness-failures__eyebrow">${
|
|
6545
|
-
<strong class="absolute-voice-readiness-failures__label">${
|
|
7045
|
+
<span class="absolute-voice-readiness-failures__eyebrow">${escapeHtml14(model.title)}</span>
|
|
7046
|
+
<strong class="absolute-voice-readiness-failures__label">${escapeHtml14(model.label)}</strong>
|
|
6546
7047
|
</header>
|
|
6547
|
-
<p class="absolute-voice-readiness-failures__description">${
|
|
7048
|
+
<p class="absolute-voice-readiness-failures__description">${escapeHtml14(model.description)}</p>
|
|
6548
7049
|
${failures}
|
|
6549
7050
|
${links}
|
|
6550
|
-
${model.error ? `<p class="absolute-voice-readiness-failures__error">${
|
|
7051
|
+
${model.error ? `<p class="absolute-voice-readiness-failures__error">${escapeHtml14(model.error)}</p>` : ""}
|
|
6551
7052
|
</section>`;
|
|
6552
7053
|
};
|
|
6553
7054
|
var getVoiceReadinessFailuresCSS = () => `.absolute-voice-readiness-failures{border:1px solid #fed7aa;border-radius:20px;background:#fff7ed;color:#1c1917;padding:18px;box-shadow:0 18px 40px rgba(234,88,12,.12);font-family:inherit}.absolute-voice-readiness-failures--ready{border-color:#86efac;background:#f0fdf4}.absolute-voice-readiness-failures--error{border-color:#fda4af;background:#fff1f2}.absolute-voice-readiness-failures__header{align-items:start;display:flex;gap:12px;justify-content:space-between}.absolute-voice-readiness-failures__eyebrow{color:#9a3412;font-size:12px;font-weight:800;letter-spacing:.08em;text-transform:uppercase}.absolute-voice-readiness-failures__label{font-size:24px;line-height:1}.absolute-voice-readiness-failures__description,.absolute-voice-readiness-failures__empty{color:#57534e}.absolute-voice-readiness-failures__items{display:grid;gap:10px;margin-top:14px}.absolute-voice-readiness-failures__item{background:white;border:1px solid #fed7aa;border-radius:16px;padding:12px}.absolute-voice-readiness-failures__item--fail{border-color:#fb7185}.absolute-voice-readiness-failures__item span{color:#9a3412;display:block;font-size:12px;font-weight:900;text-transform:uppercase}.absolute-voice-readiness-failures__item strong{display:block;font-size:18px;margin-top:4px}.absolute-voice-readiness-failures__item p{margin:.45rem 0 0}.absolute-voice-readiness-failures__links{display:flex;flex-wrap:wrap;gap:8px;margin:14px 0 0}.absolute-voice-readiness-failures__links a{border:1px solid #fdba74;border-radius:999px;color:#9a3412;font-weight:800;padding:6px 10px;text-decoration:none}.absolute-voice-readiness-failures__error{color:#9f1239;font-weight:700}`;
|
|
@@ -6588,13 +7089,13 @@ var defineVoiceReadinessFailuresElement = (tagName = "absolute-voice-readiness-f
|
|
|
6588
7089
|
};
|
|
6589
7090
|
|
|
6590
7091
|
// src/vue/useVoiceReadinessFailures.ts
|
|
6591
|
-
import { onBeforeUnmount, readonly, ref as
|
|
7092
|
+
import { onBeforeUnmount, readonly, ref as ref7 } from "vue";
|
|
6592
7093
|
var useVoiceReadinessFailures = (path = "/api/production-readiness", options = {}) => {
|
|
6593
7094
|
const store = createVoiceReadinessFailuresStore(path, options);
|
|
6594
|
-
const error =
|
|
6595
|
-
const isLoading =
|
|
6596
|
-
const report =
|
|
6597
|
-
const updatedAt =
|
|
7095
|
+
const error = ref7(null);
|
|
7096
|
+
const isLoading = ref7(false);
|
|
7097
|
+
const report = ref7(undefined);
|
|
7098
|
+
const updatedAt = ref7(undefined);
|
|
6598
7099
|
const sync = () => {
|
|
6599
7100
|
const snapshot = store.getSnapshot();
|
|
6600
7101
|
error.value = snapshot.error;
|
|
@@ -6621,7 +7122,7 @@ var useVoiceReadinessFailures = (path = "/api/production-readiness", options = {
|
|
|
6621
7122
|
};
|
|
6622
7123
|
|
|
6623
7124
|
// src/vue/VoiceReadinessFailures.ts
|
|
6624
|
-
var VoiceReadinessFailures =
|
|
7125
|
+
var VoiceReadinessFailures = defineComponent9({
|
|
6625
7126
|
name: "VoiceReadinessFailures",
|
|
6626
7127
|
props: {
|
|
6627
7128
|
description: String,
|
|
@@ -6649,40 +7150,40 @@ var VoiceReadinessFailures = defineComponent8({
|
|
|
6649
7150
|
intervalMs: props.intervalMs,
|
|
6650
7151
|
title: props.title
|
|
6651
7152
|
});
|
|
6652
|
-
return
|
|
7153
|
+
return h9("section", {
|
|
6653
7154
|
class: [
|
|
6654
7155
|
"absolute-voice-readiness-failures",
|
|
6655
7156
|
`absolute-voice-readiness-failures--${model.status}`
|
|
6656
7157
|
]
|
|
6657
7158
|
}, [
|
|
6658
|
-
|
|
6659
|
-
|
|
6660
|
-
|
|
7159
|
+
h9("header", { class: "absolute-voice-readiness-failures__header" }, [
|
|
7160
|
+
h9("span", { class: "absolute-voice-readiness-failures__eyebrow" }, model.title),
|
|
7161
|
+
h9("strong", { class: "absolute-voice-readiness-failures__label" }, model.label)
|
|
6661
7162
|
]),
|
|
6662
|
-
|
|
6663
|
-
model.failures.length ?
|
|
7163
|
+
h9("p", { class: "absolute-voice-readiness-failures__description" }, model.description),
|
|
7164
|
+
model.failures.length ? h9("div", { class: "absolute-voice-readiness-failures__items" }, model.failures.map((failure) => h9("article", {
|
|
6664
7165
|
class: [
|
|
6665
7166
|
"absolute-voice-readiness-failures__item",
|
|
6666
7167
|
`absolute-voice-readiness-failures__item--${failure.status}`
|
|
6667
7168
|
],
|
|
6668
7169
|
key: failure.label
|
|
6669
7170
|
}, [
|
|
6670
|
-
|
|
6671
|
-
|
|
6672
|
-
|
|
6673
|
-
|
|
6674
|
-
|
|
6675
|
-
failure.evidenceHref ?
|
|
6676
|
-
failure.sourceHref ?
|
|
7171
|
+
h9("span", failure.status.toUpperCase()),
|
|
7172
|
+
h9("strong", failure.label),
|
|
7173
|
+
h9("p", `Observed ${failure.observed} against ${failure.thresholdLabel} ${failure.threshold}.`),
|
|
7174
|
+
h9("p", failure.remediation),
|
|
7175
|
+
h9("p", { class: "absolute-voice-readiness-failures__links" }, [
|
|
7176
|
+
failure.evidenceHref ? h9("a", { href: failure.evidenceHref }, "Evidence") : null,
|
|
7177
|
+
failure.sourceHref ? h9("a", { href: failure.sourceHref }, "Threshold source") : null
|
|
6677
7178
|
])
|
|
6678
|
-
]))) :
|
|
6679
|
-
model.links.length ?
|
|
7179
|
+
]))) : h9("p", { class: "absolute-voice-readiness-failures__empty" }, model.error ?? "No calibrated readiness gate explanations are open."),
|
|
7180
|
+
model.links.length ? h9("p", { class: "absolute-voice-readiness-failures__links" }, model.links.map((link) => h9("a", { href: link.href, key: link.href }, link.label))) : null
|
|
6680
7181
|
]);
|
|
6681
7182
|
};
|
|
6682
7183
|
}
|
|
6683
7184
|
});
|
|
6684
7185
|
// src/vue/VoiceProviderSimulationControls.ts
|
|
6685
|
-
import { computed as computed4, defineComponent as
|
|
7186
|
+
import { computed as computed4, defineComponent as defineComponent10, h as h10 } from "vue";
|
|
6686
7187
|
|
|
6687
7188
|
// src/client/providerSimulationControls.ts
|
|
6688
7189
|
var postSimulation = async (pathPrefix, mode, provider, fetchImpl) => {
|
|
@@ -6764,7 +7265,7 @@ var createVoiceProviderSimulationControlsStore = (options) => {
|
|
|
6764
7265
|
};
|
|
6765
7266
|
|
|
6766
7267
|
// src/client/providerSimulationControlsWidget.ts
|
|
6767
|
-
var
|
|
7268
|
+
var escapeHtml15 = (value) => value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'");
|
|
6768
7269
|
var formatKind = (kind) => (kind ?? "stt").toUpperCase();
|
|
6769
7270
|
var createVoiceProviderSimulationControlsViewModel = (snapshot, options) => {
|
|
6770
7271
|
const configuredProviders = options.providers.filter((provider) => provider.configured !== false);
|
|
@@ -6784,18 +7285,18 @@ var createVoiceProviderSimulationControlsViewModel = (snapshot, options) => {
|
|
|
6784
7285
|
};
|
|
6785
7286
|
var renderVoiceProviderSimulationControlsHTML = (snapshot, options) => {
|
|
6786
7287
|
const model = createVoiceProviderSimulationControlsViewModel(snapshot, options);
|
|
6787
|
-
const failureButtons = model.failureProviders.map((provider) => `<button type="button" data-voice-provider-fail="${
|
|
6788
|
-
const recoveryButtons = model.providers.map((provider) => `<button type="button" data-voice-provider-recover="${
|
|
7288
|
+
const failureButtons = model.failureProviders.map((provider) => `<button type="button" data-voice-provider-fail="${escapeHtml15(provider.provider)}"${!model.canSimulateFailure || snapshot.isRunning ? " disabled" : ""}>Simulate ${escapeHtml15(provider.provider)} ${escapeHtml15(formatKind(options.kind))} failure</button>`).join("");
|
|
7289
|
+
const recoveryButtons = model.providers.map((provider) => `<button type="button" data-voice-provider-recover="${escapeHtml15(provider.provider)}"${snapshot.isRunning ? " disabled" : ""}>Mark ${escapeHtml15(provider.provider)} recovered</button>`).join("");
|
|
6789
7290
|
return `<section class="absolute-voice-provider-simulation absolute-voice-provider-simulation--${snapshot.error ? "error" : snapshot.isRunning ? "running" : "ready"}">
|
|
6790
7291
|
<header class="absolute-voice-provider-simulation__header">
|
|
6791
|
-
<span class="absolute-voice-provider-simulation__eyebrow">${
|
|
6792
|
-
<strong class="absolute-voice-provider-simulation__label">${
|
|
7292
|
+
<span class="absolute-voice-provider-simulation__eyebrow">${escapeHtml15(model.title)}</span>
|
|
7293
|
+
<strong class="absolute-voice-provider-simulation__label">${escapeHtml15(model.label)}</strong>
|
|
6793
7294
|
</header>
|
|
6794
|
-
<p class="absolute-voice-provider-simulation__description">${
|
|
6795
|
-
${model.canSimulateFailure ? "" : `<p class="absolute-voice-provider-simulation__empty">${
|
|
7295
|
+
<p class="absolute-voice-provider-simulation__description">${escapeHtml15(model.description)}</p>
|
|
7296
|
+
${model.canSimulateFailure ? "" : `<p class="absolute-voice-provider-simulation__empty">${escapeHtml15(options.fallbackRequiredMessage ?? "Configure fallback providers before simulating failure.")}</p>`}
|
|
6796
7297
|
<div class="absolute-voice-provider-simulation__actions">${failureButtons}${recoveryButtons}</div>
|
|
6797
|
-
${snapshot.error ? `<p class="absolute-voice-provider-simulation__error">${
|
|
6798
|
-
${model.resultText ? `<pre class="absolute-voice-provider-simulation__result">${
|
|
7298
|
+
${snapshot.error ? `<p class="absolute-voice-provider-simulation__error">${escapeHtml15(snapshot.error)}</p>` : ""}
|
|
7299
|
+
${model.resultText ? `<pre class="absolute-voice-provider-simulation__result">${escapeHtml15(model.resultText)}</pre>` : ""}
|
|
6799
7300
|
</section>`;
|
|
6800
7301
|
};
|
|
6801
7302
|
var bindVoiceProviderSimulationControls = (element, store) => {
|
|
@@ -6861,15 +7362,15 @@ var defineVoiceProviderSimulationControlsElement = (tagName = "absolute-voice-pr
|
|
|
6861
7362
|
};
|
|
6862
7363
|
|
|
6863
7364
|
// src/vue/useVoiceProviderSimulationControls.ts
|
|
6864
|
-
import { onUnmounted as
|
|
7365
|
+
import { onUnmounted as onUnmounted9, ref as ref8 } from "vue";
|
|
6865
7366
|
function useVoiceProviderSimulationControls(options) {
|
|
6866
7367
|
const store = createVoiceProviderSimulationControlsStore(options);
|
|
6867
|
-
const error =
|
|
6868
|
-
const isRunning =
|
|
6869
|
-
const lastResult =
|
|
6870
|
-
const mode =
|
|
6871
|
-
const provider =
|
|
6872
|
-
const updatedAt =
|
|
7368
|
+
const error = ref8(null);
|
|
7369
|
+
const isRunning = ref8(false);
|
|
7370
|
+
const lastResult = ref8(null);
|
|
7371
|
+
const mode = ref8(null);
|
|
7372
|
+
const provider = ref8(null);
|
|
7373
|
+
const updatedAt = ref8(undefined);
|
|
6873
7374
|
const sync = () => {
|
|
6874
7375
|
const snapshot = store.getSnapshot();
|
|
6875
7376
|
error.value = snapshot.error;
|
|
@@ -6881,7 +7382,7 @@ function useVoiceProviderSimulationControls(options) {
|
|
|
6881
7382
|
};
|
|
6882
7383
|
const unsubscribe = store.subscribe(sync);
|
|
6883
7384
|
sync();
|
|
6884
|
-
|
|
7385
|
+
onUnmounted9(() => {
|
|
6885
7386
|
unsubscribe();
|
|
6886
7387
|
store.close();
|
|
6887
7388
|
});
|
|
@@ -6897,7 +7398,7 @@ function useVoiceProviderSimulationControls(options) {
|
|
|
6897
7398
|
}
|
|
6898
7399
|
|
|
6899
7400
|
// src/vue/VoiceProviderSimulationControls.ts
|
|
6900
|
-
var VoiceProviderSimulationControls =
|
|
7401
|
+
var VoiceProviderSimulationControls = defineComponent10({
|
|
6901
7402
|
name: "VoiceProviderSimulationControls",
|
|
6902
7403
|
props: {
|
|
6903
7404
|
class: { default: "", type: String },
|
|
@@ -6939,40 +7440,40 @@ var VoiceProviderSimulationControls = defineComponent9({
|
|
|
6939
7440
|
const run = (provider, mode) => {
|
|
6940
7441
|
controls.run(provider, mode).catch(() => {});
|
|
6941
7442
|
};
|
|
6942
|
-
return () =>
|
|
7443
|
+
return () => h10("section", {
|
|
6943
7444
|
class: [
|
|
6944
7445
|
"absolute-voice-provider-simulation",
|
|
6945
7446
|
`absolute-voice-provider-simulation--${controls.error.value ? "error" : controls.isRunning.value ? "running" : "ready"}`,
|
|
6946
7447
|
props.class
|
|
6947
7448
|
]
|
|
6948
7449
|
}, [
|
|
6949
|
-
|
|
6950
|
-
|
|
6951
|
-
|
|
7450
|
+
h10("header", { class: "absolute-voice-provider-simulation__header" }, [
|
|
7451
|
+
h10("span", { class: "absolute-voice-provider-simulation__eyebrow" }, model.value.title),
|
|
7452
|
+
h10("strong", { class: "absolute-voice-provider-simulation__label" }, model.value.label)
|
|
6952
7453
|
]),
|
|
6953
|
-
|
|
6954
|
-
model.value.canSimulateFailure ? null :
|
|
6955
|
-
|
|
6956
|
-
...model.value.failureProviders.map((provider) =>
|
|
7454
|
+
h10("p", { class: "absolute-voice-provider-simulation__description" }, model.value.description),
|
|
7455
|
+
model.value.canSimulateFailure ? null : h10("p", { class: "absolute-voice-provider-simulation__empty" }, props.fallbackRequiredMessage ?? "Configure fallback providers before simulating failure."),
|
|
7456
|
+
h10("div", { class: "absolute-voice-provider-simulation__actions" }, [
|
|
7457
|
+
...model.value.failureProviders.map((provider) => h10("button", {
|
|
6957
7458
|
disabled: !model.value.canSimulateFailure || controls.isRunning.value,
|
|
6958
7459
|
key: `fail-${provider.provider}`,
|
|
6959
7460
|
onClick: () => run(provider.provider, "failure"),
|
|
6960
7461
|
type: "button"
|
|
6961
7462
|
}, `Simulate ${provider.provider} ${props.kind.toUpperCase()} failure`)),
|
|
6962
|
-
...model.value.providers.map((provider) =>
|
|
7463
|
+
...model.value.providers.map((provider) => h10("button", {
|
|
6963
7464
|
disabled: controls.isRunning.value,
|
|
6964
7465
|
key: `recover-${provider.provider}`,
|
|
6965
7466
|
onClick: () => run(provider.provider, "recovery"),
|
|
6966
7467
|
type: "button"
|
|
6967
7468
|
}, `Mark ${provider.provider} recovered`))
|
|
6968
7469
|
]),
|
|
6969
|
-
controls.error.value ?
|
|
6970
|
-
model.value.resultText ?
|
|
7470
|
+
controls.error.value ? h10("p", { class: "absolute-voice-provider-simulation__error" }, controls.error.value) : null,
|
|
7471
|
+
model.value.resultText ? h10("pre", { class: "absolute-voice-provider-simulation__result" }, model.value.resultText) : null
|
|
6971
7472
|
]);
|
|
6972
7473
|
}
|
|
6973
7474
|
});
|
|
6974
7475
|
// src/vue/VoiceProviderCapabilities.ts
|
|
6975
|
-
import { computed as computed5, defineComponent as
|
|
7476
|
+
import { computed as computed5, defineComponent as defineComponent11, h as h11 } from "vue";
|
|
6976
7477
|
|
|
6977
7478
|
// src/client/providerCapabilities.ts
|
|
6978
7479
|
var fetchVoiceProviderCapabilities = async (path = "/api/provider-capabilities", options = {}) => {
|
|
@@ -7054,9 +7555,9 @@ var createVoiceProviderCapabilitiesStore = (path = "/api/provider-capabilities",
|
|
|
7054
7555
|
};
|
|
7055
7556
|
|
|
7056
7557
|
// src/client/providerCapabilitiesWidget.ts
|
|
7057
|
-
var
|
|
7058
|
-
var
|
|
7059
|
-
var
|
|
7558
|
+
var DEFAULT_TITLE10 = "Provider Capabilities";
|
|
7559
|
+
var DEFAULT_DESCRIPTION10 = "Configured, selected, and healthy voice providers for this deployment.";
|
|
7560
|
+
var escapeHtml16 = (value) => value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'");
|
|
7060
7561
|
var formatProvider = (provider) => provider.split(/[-_\s]+/).filter(Boolean).map((part) => `${part[0]?.toUpperCase() ?? ""}${part.slice(1)}`).join(" ") || provider;
|
|
7061
7562
|
var formatKind2 = (kind) => kind.toUpperCase();
|
|
7062
7563
|
var formatStatus3 = (status) => status.split("-").map((part) => `${part[0]?.toUpperCase() ?? ""}${part.slice(1)}`).join(" ");
|
|
@@ -7100,36 +7601,36 @@ var createVoiceProviderCapabilitiesViewModel = (snapshot, options = {}) => {
|
|
|
7100
7601
|
const selectedCount = snapshot.report?.selected ?? capabilities.filter((capability) => capability.selected).length;
|
|
7101
7602
|
return {
|
|
7102
7603
|
capabilities,
|
|
7103
|
-
description: options.description ??
|
|
7604
|
+
description: options.description ?? DEFAULT_DESCRIPTION10,
|
|
7104
7605
|
error: snapshot.error,
|
|
7105
7606
|
isLoading: snapshot.isLoading,
|
|
7106
7607
|
label: snapshot.error ? "Unavailable" : capabilities.length ? warningCount > 0 ? `${warningCount} needs attention` : `${selectedCount} selected` : snapshot.isLoading ? "Checking" : "No capabilities",
|
|
7107
7608
|
status: snapshot.error ? "error" : capabilities.length ? warningCount > 0 ? "warning" : "ready" : snapshot.isLoading ? "loading" : "empty",
|
|
7108
|
-
title: options.title ??
|
|
7609
|
+
title: options.title ?? DEFAULT_TITLE10,
|
|
7109
7610
|
updatedAt: snapshot.updatedAt
|
|
7110
7611
|
};
|
|
7111
7612
|
};
|
|
7112
7613
|
var renderVoiceProviderCapabilitiesHTML = (snapshot, options = {}) => {
|
|
7113
7614
|
const model = createVoiceProviderCapabilitiesViewModel(snapshot, options);
|
|
7114
|
-
const capabilities = model.capabilities.length ? `<div class="absolute-voice-provider-capabilities__providers">${model.capabilities.map((capability) => `<article class="absolute-voice-provider-capabilities__provider absolute-voice-provider-capabilities__provider--${
|
|
7615
|
+
const capabilities = model.capabilities.length ? `<div class="absolute-voice-provider-capabilities__providers">${model.capabilities.map((capability) => `<article class="absolute-voice-provider-capabilities__provider absolute-voice-provider-capabilities__provider--${escapeHtml16(capability.status)}">
|
|
7115
7616
|
<header>
|
|
7116
|
-
<strong>${
|
|
7117
|
-
<span>${
|
|
7617
|
+
<strong>${escapeHtml16(capability.label)}</strong>
|
|
7618
|
+
<span>${escapeHtml16(formatStatus3(capability.status))}</span>
|
|
7118
7619
|
</header>
|
|
7119
|
-
<p>${
|
|
7620
|
+
<p>${escapeHtml16(capability.detail)}</p>
|
|
7120
7621
|
<dl>${capability.rows.map((row) => `<div>
|
|
7121
|
-
<dt>${
|
|
7122
|
-
<dd>${
|
|
7622
|
+
<dt>${escapeHtml16(row.label)}</dt>
|
|
7623
|
+
<dd>${escapeHtml16(row.value)}</dd>
|
|
7123
7624
|
</div>`).join("")}</dl>
|
|
7124
7625
|
</article>`).join("")}</div>` : '<p class="absolute-voice-provider-capabilities__empty">Configure provider capabilities to see deployment coverage.</p>';
|
|
7125
|
-
return `<section class="absolute-voice-provider-capabilities absolute-voice-provider-capabilities--${
|
|
7626
|
+
return `<section class="absolute-voice-provider-capabilities absolute-voice-provider-capabilities--${escapeHtml16(model.status)}">
|
|
7126
7627
|
<header class="absolute-voice-provider-capabilities__header">
|
|
7127
|
-
<span class="absolute-voice-provider-capabilities__eyebrow">${
|
|
7128
|
-
<strong class="absolute-voice-provider-capabilities__label">${
|
|
7628
|
+
<span class="absolute-voice-provider-capabilities__eyebrow">${escapeHtml16(model.title)}</span>
|
|
7629
|
+
<strong class="absolute-voice-provider-capabilities__label">${escapeHtml16(model.label)}</strong>
|
|
7129
7630
|
</header>
|
|
7130
|
-
<p class="absolute-voice-provider-capabilities__description">${
|
|
7631
|
+
<p class="absolute-voice-provider-capabilities__description">${escapeHtml16(model.description)}</p>
|
|
7131
7632
|
${capabilities}
|
|
7132
|
-
${model.error ? `<p class="absolute-voice-provider-capabilities__error">${
|
|
7633
|
+
${model.error ? `<p class="absolute-voice-provider-capabilities__error">${escapeHtml16(model.error)}</p>` : ""}
|
|
7133
7634
|
</section>`;
|
|
7134
7635
|
};
|
|
7135
7636
|
var getVoiceProviderCapabilitiesCSS = () => `.absolute-voice-provider-capabilities{border:1px solid #bfd7ea;border-radius:20px;background:#f6fbff;color:#08131f;padding:18px;box-shadow:0 18px 40px rgba(14,51,78,.12);font-family:inherit}.absolute-voice-provider-capabilities--error,.absolute-voice-provider-capabilities--warning{border-color:#f2a7a7;background:#fff5f3}.absolute-voice-provider-capabilities__header,.absolute-voice-provider-capabilities__provider header{align-items:start;display:flex;gap:12px;justify-content:space-between}.absolute-voice-provider-capabilities__eyebrow{color:#255f85;font-size:12px;font-weight:800;letter-spacing:.08em;text-transform:uppercase}.absolute-voice-provider-capabilities__label{font-size:24px;line-height:1}.absolute-voice-provider-capabilities__description,.absolute-voice-provider-capabilities__provider p,.absolute-voice-provider-capabilities__provider dt,.absolute-voice-provider-capabilities__empty{color:#405467}.absolute-voice-provider-capabilities__providers{display:grid;gap:12px;margin-top:14px}.absolute-voice-provider-capabilities__provider{background:#fff;border:1px solid #d7e7f3;border-radius:16px;padding:14px}.absolute-voice-provider-capabilities__provider--selected,.absolute-voice-provider-capabilities__provider--healthy{border-color:#86efac}.absolute-voice-provider-capabilities__provider--degraded,.absolute-voice-provider-capabilities__provider--rate-limited,.absolute-voice-provider-capabilities__provider--suppressed,.absolute-voice-provider-capabilities__provider--unconfigured{border-color:#f2a7a7}.absolute-voice-provider-capabilities__provider p{margin:10px 0}.absolute-voice-provider-capabilities__provider dl{display:grid;gap:8px;grid-template-columns:repeat(2,minmax(0,1fr));margin:0}.absolute-voice-provider-capabilities__provider div{background:#f6fbff;border:1px solid #d7e7f3;border-radius:12px;padding:8px}.absolute-voice-provider-capabilities__provider dt{font-size:12px}.absolute-voice-provider-capabilities__provider dd{font-weight:800;margin:4px 0 0}.absolute-voice-provider-capabilities__empty{margin:14px 0 0}.absolute-voice-provider-capabilities__error{color:#9f1239;font-weight:700}`;
|
|
@@ -7171,13 +7672,13 @@ var defineVoiceProviderCapabilitiesElement = (tagName = "absolute-voice-provider
|
|
|
7171
7672
|
};
|
|
7172
7673
|
|
|
7173
7674
|
// src/vue/useVoiceProviderCapabilities.ts
|
|
7174
|
-
import { onUnmounted as
|
|
7675
|
+
import { onUnmounted as onUnmounted10, shallowRef as shallowRef9 } from "vue";
|
|
7175
7676
|
function useVoiceProviderCapabilities(path = "/api/provider-capabilities", options = {}) {
|
|
7176
7677
|
const store = createVoiceProviderCapabilitiesStore(path, options);
|
|
7177
|
-
const error =
|
|
7178
|
-
const isLoading =
|
|
7179
|
-
const report =
|
|
7180
|
-
const updatedAt =
|
|
7678
|
+
const error = shallowRef9(null);
|
|
7679
|
+
const isLoading = shallowRef9(false);
|
|
7680
|
+
const report = shallowRef9();
|
|
7681
|
+
const updatedAt = shallowRef9(undefined);
|
|
7181
7682
|
const sync = () => {
|
|
7182
7683
|
const snapshot = store.getSnapshot();
|
|
7183
7684
|
error.value = snapshot.error;
|
|
@@ -7188,7 +7689,7 @@ function useVoiceProviderCapabilities(path = "/api/provider-capabilities", optio
|
|
|
7188
7689
|
const unsubscribe = store.subscribe(sync);
|
|
7189
7690
|
sync();
|
|
7190
7691
|
store.refresh().catch(() => {});
|
|
7191
|
-
|
|
7692
|
+
onUnmounted10(() => {
|
|
7192
7693
|
unsubscribe();
|
|
7193
7694
|
store.close();
|
|
7194
7695
|
});
|
|
@@ -7202,7 +7703,7 @@ function useVoiceProviderCapabilities(path = "/api/provider-capabilities", optio
|
|
|
7202
7703
|
}
|
|
7203
7704
|
|
|
7204
7705
|
// src/vue/VoiceProviderCapabilities.ts
|
|
7205
|
-
var VoiceProviderCapabilities =
|
|
7706
|
+
var VoiceProviderCapabilities = defineComponent11({
|
|
7206
7707
|
name: "VoiceProviderCapabilities",
|
|
7207
7708
|
props: {
|
|
7208
7709
|
class: {
|
|
@@ -7239,44 +7740,44 @@ var VoiceProviderCapabilities = defineComponent10({
|
|
|
7239
7740
|
report: capabilities.report.value,
|
|
7240
7741
|
updatedAt: capabilities.updatedAt.value
|
|
7241
7742
|
}, options));
|
|
7242
|
-
return () =>
|
|
7743
|
+
return () => h11("section", {
|
|
7243
7744
|
class: [
|
|
7244
7745
|
"absolute-voice-provider-capabilities",
|
|
7245
7746
|
`absolute-voice-provider-capabilities--${model.value.status}`,
|
|
7246
7747
|
props.class
|
|
7247
7748
|
]
|
|
7248
7749
|
}, [
|
|
7249
|
-
|
|
7250
|
-
|
|
7251
|
-
|
|
7750
|
+
h11("header", { class: "absolute-voice-provider-capabilities__header" }, [
|
|
7751
|
+
h11("span", { class: "absolute-voice-provider-capabilities__eyebrow" }, model.value.title),
|
|
7752
|
+
h11("strong", { class: "absolute-voice-provider-capabilities__label" }, model.value.label)
|
|
7252
7753
|
]),
|
|
7253
|
-
|
|
7254
|
-
model.value.capabilities.length ?
|
|
7754
|
+
h11("p", { class: "absolute-voice-provider-capabilities__description" }, model.value.description),
|
|
7755
|
+
model.value.capabilities.length ? h11("div", { class: "absolute-voice-provider-capabilities__providers" }, model.value.capabilities.map((capability) => h11("article", {
|
|
7255
7756
|
class: [
|
|
7256
7757
|
"absolute-voice-provider-capabilities__provider",
|
|
7257
7758
|
`absolute-voice-provider-capabilities__provider--${capability.status}`
|
|
7258
7759
|
],
|
|
7259
7760
|
key: `${capability.kind}:${capability.provider}`
|
|
7260
7761
|
}, [
|
|
7261
|
-
|
|
7262
|
-
|
|
7263
|
-
|
|
7762
|
+
h11("header", [
|
|
7763
|
+
h11("strong", capability.label),
|
|
7764
|
+
h11("span", capability.status)
|
|
7264
7765
|
]),
|
|
7265
|
-
|
|
7266
|
-
|
|
7267
|
-
|
|
7268
|
-
|
|
7766
|
+
h11("p", capability.detail),
|
|
7767
|
+
h11("dl", capability.rows.map((row) => h11("div", { key: row.label }, [
|
|
7768
|
+
h11("dt", row.label),
|
|
7769
|
+
h11("dd", row.value)
|
|
7269
7770
|
])))
|
|
7270
|
-
]))) :
|
|
7271
|
-
model.value.error ?
|
|
7771
|
+
]))) : h11("p", { class: "absolute-voice-provider-capabilities__empty" }, "Configure provider capabilities to see deployment coverage."),
|
|
7772
|
+
model.value.error ? h11("p", { class: "absolute-voice-provider-capabilities__error" }, model.value.error) : null
|
|
7272
7773
|
]);
|
|
7273
7774
|
}
|
|
7274
7775
|
});
|
|
7275
7776
|
// src/vue/VoiceProviderContracts.ts
|
|
7276
|
-
import { defineComponent as
|
|
7777
|
+
import { defineComponent as defineComponent12, h as h12 } from "vue";
|
|
7277
7778
|
|
|
7278
7779
|
// src/vue/useVoiceProviderContracts.ts
|
|
7279
|
-
import { onUnmounted as
|
|
7780
|
+
import { onUnmounted as onUnmounted11, shallowRef as shallowRef10 } from "vue";
|
|
7280
7781
|
|
|
7281
7782
|
// src/client/providerContracts.ts
|
|
7282
7783
|
var fetchVoiceProviderContracts = async (path = "/api/provider-contracts", options = {}) => {
|
|
@@ -7356,10 +7857,10 @@ var createVoiceProviderContractsStore = (path = "/api/provider-contracts", optio
|
|
|
7356
7857
|
// src/vue/useVoiceProviderContracts.ts
|
|
7357
7858
|
function useVoiceProviderContracts(path = "/api/provider-contracts", options = {}) {
|
|
7358
7859
|
const store = createVoiceProviderContractsStore(path, options);
|
|
7359
|
-
const error =
|
|
7360
|
-
const isLoading =
|
|
7361
|
-
const report =
|
|
7362
|
-
const updatedAt =
|
|
7860
|
+
const error = shallowRef10(null);
|
|
7861
|
+
const isLoading = shallowRef10(false);
|
|
7862
|
+
const report = shallowRef10();
|
|
7863
|
+
const updatedAt = shallowRef10(undefined);
|
|
7363
7864
|
const sync = () => {
|
|
7364
7865
|
const snapshot = store.getSnapshot();
|
|
7365
7866
|
error.value = snapshot.error;
|
|
@@ -7370,7 +7871,7 @@ function useVoiceProviderContracts(path = "/api/provider-contracts", options = {
|
|
|
7370
7871
|
const unsubscribe = store.subscribe(sync);
|
|
7371
7872
|
sync();
|
|
7372
7873
|
store.refresh().catch(() => {});
|
|
7373
|
-
|
|
7874
|
+
onUnmounted11(() => {
|
|
7374
7875
|
unsubscribe();
|
|
7375
7876
|
store.close();
|
|
7376
7877
|
});
|
|
@@ -7384,9 +7885,9 @@ function useVoiceProviderContracts(path = "/api/provider-contracts", options = {
|
|
|
7384
7885
|
}
|
|
7385
7886
|
|
|
7386
7887
|
// src/client/providerContractsWidget.ts
|
|
7387
|
-
var
|
|
7388
|
-
var
|
|
7389
|
-
var
|
|
7888
|
+
var DEFAULT_TITLE11 = "Provider Contracts";
|
|
7889
|
+
var DEFAULT_DESCRIPTION11 = "Production contract coverage for provider env, latency, fallback, streaming, and capabilities.";
|
|
7890
|
+
var escapeHtml17 = (value) => value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'");
|
|
7390
7891
|
var formatProvider2 = (provider) => provider.split(/[-_\s]+/).filter(Boolean).map((part) => `${part[0]?.toUpperCase() ?? ""}${part.slice(1)}`).join(" ") || provider;
|
|
7391
7892
|
var formatStatus4 = (status) => status.split("-").map((part) => `${part[0]?.toUpperCase() ?? ""}${part.slice(1)}`).join(" ");
|
|
7392
7893
|
var contractDetail = (row) => {
|
|
@@ -7418,38 +7919,38 @@ var createVoiceProviderContractsViewModel = (snapshot, options = {}) => {
|
|
|
7418
7919
|
}));
|
|
7419
7920
|
const warningCount = snapshot.report ? snapshot.report.failed + snapshot.report.warned : rows.filter((row) => row.status !== "pass").length;
|
|
7420
7921
|
return {
|
|
7421
|
-
description: options.description ??
|
|
7922
|
+
description: options.description ?? DEFAULT_DESCRIPTION11,
|
|
7422
7923
|
error: snapshot.error,
|
|
7423
7924
|
isLoading: snapshot.isLoading,
|
|
7424
7925
|
label: snapshot.error ? "Unavailable" : rows.length ? warningCount > 0 ? `${warningCount} needs attention` : `${rows.length} passing` : snapshot.isLoading ? "Checking" : "No contracts",
|
|
7425
7926
|
rows,
|
|
7426
7927
|
status: snapshot.error ? "error" : rows.length ? warningCount > 0 ? "warning" : "ready" : snapshot.isLoading ? "loading" : "empty",
|
|
7427
|
-
title: options.title ??
|
|
7928
|
+
title: options.title ?? DEFAULT_TITLE11,
|
|
7428
7929
|
updatedAt: snapshot.updatedAt
|
|
7429
7930
|
};
|
|
7430
7931
|
};
|
|
7431
7932
|
var renderVoiceProviderContractsHTML = (snapshot, options = {}) => {
|
|
7432
7933
|
const model = createVoiceProviderContractsViewModel(snapshot, options);
|
|
7433
|
-
const rows = model.rows.length ? `<div class="absolute-voice-provider-contracts__rows">${model.rows.map((row) => `<article class="absolute-voice-provider-contracts__row absolute-voice-provider-contracts__row--${
|
|
7934
|
+
const rows = model.rows.length ? `<div class="absolute-voice-provider-contracts__rows">${model.rows.map((row) => `<article class="absolute-voice-provider-contracts__row absolute-voice-provider-contracts__row--${escapeHtml17(row.status)}">
|
|
7434
7935
|
<header>
|
|
7435
|
-
<strong>${
|
|
7436
|
-
<span>${
|
|
7936
|
+
<strong>${escapeHtml17(row.label)}</strong>
|
|
7937
|
+
<span>${escapeHtml17(formatStatus4(row.status))}</span>
|
|
7437
7938
|
</header>
|
|
7438
|
-
<p>${
|
|
7439
|
-
${row.remediations.length ? `<ul class="absolute-voice-provider-contracts__remediations">${row.remediations.map((remediation) => `<li>${remediation.href ? `<a href="${
|
|
7939
|
+
<p>${escapeHtml17(row.detail)}</p>
|
|
7940
|
+
${row.remediations.length ? `<ul class="absolute-voice-provider-contracts__remediations">${row.remediations.map((remediation) => `<li>${remediation.href ? `<a href="${escapeHtml17(remediation.href)}">${escapeHtml17(remediation.label)}</a>` : `<strong>${escapeHtml17(remediation.label)}</strong>`}<span>${escapeHtml17(remediation.detail)}</span></li>`).join("")}</ul>` : ""}
|
|
7440
7941
|
<dl>${row.rows.map((item) => `<div>
|
|
7441
|
-
<dt>${
|
|
7442
|
-
<dd>${
|
|
7942
|
+
<dt>${escapeHtml17(item.label)}</dt>
|
|
7943
|
+
<dd>${escapeHtml17(item.value)}</dd>
|
|
7443
7944
|
</div>`).join("")}</dl>
|
|
7444
7945
|
</article>`).join("")}</div>` : '<p class="absolute-voice-provider-contracts__empty">Configure provider contracts to see production coverage.</p>';
|
|
7445
|
-
return `<section class="absolute-voice-provider-contracts absolute-voice-provider-contracts--${
|
|
7946
|
+
return `<section class="absolute-voice-provider-contracts absolute-voice-provider-contracts--${escapeHtml17(model.status)}">
|
|
7446
7947
|
<header class="absolute-voice-provider-contracts__header">
|
|
7447
|
-
<span class="absolute-voice-provider-contracts__eyebrow">${
|
|
7448
|
-
<strong class="absolute-voice-provider-contracts__label">${
|
|
7948
|
+
<span class="absolute-voice-provider-contracts__eyebrow">${escapeHtml17(model.title)}</span>
|
|
7949
|
+
<strong class="absolute-voice-provider-contracts__label">${escapeHtml17(model.label)}</strong>
|
|
7449
7950
|
</header>
|
|
7450
|
-
<p class="absolute-voice-provider-contracts__description">${
|
|
7951
|
+
<p class="absolute-voice-provider-contracts__description">${escapeHtml17(model.description)}</p>
|
|
7451
7952
|
${rows}
|
|
7452
|
-
${model.error ? `<p class="absolute-voice-provider-contracts__error">${
|
|
7953
|
+
${model.error ? `<p class="absolute-voice-provider-contracts__error">${escapeHtml17(model.error)}</p>` : ""}
|
|
7453
7954
|
</section>`;
|
|
7454
7955
|
};
|
|
7455
7956
|
var getVoiceProviderContractsCSS = () => `.absolute-voice-provider-contracts{border:1px solid #b8dcc7;border-radius:20px;background:#f7fff9;color:#09140d;padding:18px;box-shadow:0 18px 40px rgba(21,83,45,.12);font-family:inherit}.absolute-voice-provider-contracts--error,.absolute-voice-provider-contracts--warning{border-color:#f2a7a7;background:#fff7f4}.absolute-voice-provider-contracts__header,.absolute-voice-provider-contracts__row header{align-items:start;display:flex;gap:12px;justify-content:space-between}.absolute-voice-provider-contracts__eyebrow{color:#166534;font-size:12px;font-weight:800;letter-spacing:.08em;text-transform:uppercase}.absolute-voice-provider-contracts__label{font-size:24px;line-height:1}.absolute-voice-provider-contracts__description,.absolute-voice-provider-contracts__row p,.absolute-voice-provider-contracts__row dt,.absolute-voice-provider-contracts__empty{color:#405448}.absolute-voice-provider-contracts__rows{display:grid;gap:12px;margin-top:14px}.absolute-voice-provider-contracts__row{background:#fff;border:1px solid #d6eadb;border-radius:16px;padding:14px}.absolute-voice-provider-contracts__row--pass{border-color:#86efac}.absolute-voice-provider-contracts__row--warn,.absolute-voice-provider-contracts__row--fail{border-color:#f2a7a7}.absolute-voice-provider-contracts__row p{margin:10px 0}.absolute-voice-provider-contracts__remediations{display:grid;gap:8px;list-style:none;margin:0 0 10px;padding:0}.absolute-voice-provider-contracts__remediations li{background:#fff7ed;border:1px solid #fed7aa;border-radius:12px;display:grid;gap:3px;padding:8px}.absolute-voice-provider-contracts__remediations a,.absolute-voice-provider-contracts__remediations strong{color:#9a3412}.absolute-voice-provider-contracts__remediations span{color:#7c2d12}.absolute-voice-provider-contracts__row dl{display:grid;gap:8px;grid-template-columns:repeat(2,minmax(0,1fr));margin:0}.absolute-voice-provider-contracts__row div{background:#f7fff9;border:1px solid #d6eadb;border-radius:12px;padding:8px}.absolute-voice-provider-contracts__row dt{font-size:12px}.absolute-voice-provider-contracts__row dd{font-weight:800;margin:4px 0 0}.absolute-voice-provider-contracts__error{color:#9f1239;font-weight:700}`;
|
|
@@ -7491,7 +7992,7 @@ var defineVoiceProviderContractsElement = (tagName = "absolute-voice-provider-co
|
|
|
7491
7992
|
};
|
|
7492
7993
|
|
|
7493
7994
|
// src/vue/VoiceProviderContracts.ts
|
|
7494
|
-
var VoiceProviderContracts =
|
|
7995
|
+
var VoiceProviderContracts = defineComponent12({
|
|
7495
7996
|
name: "VoiceProviderContracts",
|
|
7496
7997
|
props: {
|
|
7497
7998
|
description: String,
|
|
@@ -7519,49 +8020,49 @@ var VoiceProviderContracts = defineComponent11({
|
|
|
7519
8020
|
intervalMs: props.intervalMs,
|
|
7520
8021
|
title: props.title
|
|
7521
8022
|
});
|
|
7522
|
-
return
|
|
8023
|
+
return h12("section", {
|
|
7523
8024
|
class: [
|
|
7524
8025
|
"absolute-voice-provider-contracts",
|
|
7525
8026
|
`absolute-voice-provider-contracts--${model.status}`
|
|
7526
8027
|
]
|
|
7527
8028
|
}, [
|
|
7528
|
-
|
|
7529
|
-
|
|
7530
|
-
|
|
8029
|
+
h12("header", { class: "absolute-voice-provider-contracts__header" }, [
|
|
8030
|
+
h12("span", { class: "absolute-voice-provider-contracts__eyebrow" }, model.title),
|
|
8031
|
+
h12("strong", { class: "absolute-voice-provider-contracts__label" }, model.label)
|
|
7531
8032
|
]),
|
|
7532
|
-
|
|
7533
|
-
model.rows.length ?
|
|
8033
|
+
h12("p", { class: "absolute-voice-provider-contracts__description" }, model.description),
|
|
8034
|
+
model.rows.length ? h12("div", { class: "absolute-voice-provider-contracts__rows" }, model.rows.map((row) => h12("article", {
|
|
7534
8035
|
class: [
|
|
7535
8036
|
"absolute-voice-provider-contracts__row",
|
|
7536
8037
|
`absolute-voice-provider-contracts__row--${row.status}`
|
|
7537
8038
|
],
|
|
7538
8039
|
key: `${row.kind}:${row.provider}`
|
|
7539
8040
|
}, [
|
|
7540
|
-
|
|
7541
|
-
|
|
7542
|
-
|
|
8041
|
+
h12("header", [
|
|
8042
|
+
h12("strong", row.label),
|
|
8043
|
+
h12("span", row.status)
|
|
7543
8044
|
]),
|
|
7544
|
-
|
|
7545
|
-
row.remediations.length ?
|
|
8045
|
+
h12("p", row.detail),
|
|
8046
|
+
row.remediations.length ? h12("ul", {
|
|
7546
8047
|
class: "absolute-voice-provider-contracts__remediations"
|
|
7547
|
-
}, row.remediations.map((remediation) =>
|
|
8048
|
+
}, row.remediations.map((remediation) => h12("li", {
|
|
7548
8049
|
key: `${row.kind}:${row.provider}:${remediation.label}`
|
|
7549
8050
|
}, [
|
|
7550
|
-
remediation.href ?
|
|
7551
|
-
|
|
8051
|
+
remediation.href ? h12("a", { href: remediation.href }, remediation.label) : h12("strong", remediation.label),
|
|
8052
|
+
h12("span", remediation.detail)
|
|
7552
8053
|
]))) : null,
|
|
7553
|
-
|
|
7554
|
-
|
|
7555
|
-
|
|
8054
|
+
h12("dl", row.rows.map((item) => h12("div", { key: item.label }, [
|
|
8055
|
+
h12("dt", item.label),
|
|
8056
|
+
h12("dd", item.value)
|
|
7556
8057
|
])))
|
|
7557
|
-
]))) :
|
|
7558
|
-
model.error ?
|
|
8058
|
+
]))) : h12("p", { class: "absolute-voice-provider-contracts__empty" }, "Configure provider contracts to see production coverage."),
|
|
8059
|
+
model.error ? h12("p", { class: "absolute-voice-provider-contracts__error" }, model.error) : null
|
|
7559
8060
|
]);
|
|
7560
8061
|
};
|
|
7561
8062
|
}
|
|
7562
8063
|
});
|
|
7563
8064
|
// src/vue/VoiceProviderStatus.ts
|
|
7564
|
-
import { computed as computed6, defineComponent as
|
|
8065
|
+
import { computed as computed6, defineComponent as defineComponent13, h as h13 } from "vue";
|
|
7565
8066
|
|
|
7566
8067
|
// src/client/providerStatus.ts
|
|
7567
8068
|
var fetchVoiceProviderStatus = async (path = "/api/provider-status", options = {}) => {
|
|
@@ -7644,9 +8145,9 @@ var createVoiceProviderStatusStore = (path = "/api/provider-status", options = {
|
|
|
7644
8145
|
};
|
|
7645
8146
|
|
|
7646
8147
|
// src/client/providerStatusWidget.ts
|
|
7647
|
-
var
|
|
7648
|
-
var
|
|
7649
|
-
var
|
|
8148
|
+
var DEFAULT_TITLE12 = "Voice Providers";
|
|
8149
|
+
var DEFAULT_DESCRIPTION12 = "Live provider health, fallback counts, latency, and suppression state from your self-hosted trace store.";
|
|
8150
|
+
var escapeHtml18 = (value) => value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'");
|
|
7650
8151
|
var formatProvider3 = (provider) => provider.split(/[-_\s]+/).filter(Boolean).map((part) => `${part[0]?.toUpperCase() ?? ""}${part.slice(1)}`).join(" ") || provider;
|
|
7651
8152
|
var formatStatus5 = (status) => status.split("-").map((part) => `${part[0]?.toUpperCase() ?? ""}${part.slice(1)}`).join(" ");
|
|
7652
8153
|
var formatLatency = (value) => typeof value === "number" ? `${value}ms` : "No samples";
|
|
@@ -7690,37 +8191,37 @@ var createVoiceProviderStatusViewModel = (snapshot, options = {}) => {
|
|
|
7690
8191
|
const warningCount = providers.filter((provider) => isWarningStatus2(provider.status)).length;
|
|
7691
8192
|
const healthyCount = providers.filter((provider) => provider.status === "healthy").length;
|
|
7692
8193
|
return {
|
|
7693
|
-
description: options.description ??
|
|
8194
|
+
description: options.description ?? DEFAULT_DESCRIPTION12,
|
|
7694
8195
|
error: snapshot.error,
|
|
7695
8196
|
isLoading: snapshot.isLoading,
|
|
7696
8197
|
label: snapshot.error ? "Unavailable" : providers.length ? warningCount > 0 ? `${warningCount} needs attention` : `${healthyCount} healthy` : snapshot.isLoading ? "Checking" : "No provider traffic",
|
|
7697
8198
|
providers,
|
|
7698
8199
|
status: snapshot.error ? "error" : providers.length ? warningCount > 0 ? "warning" : "ready" : snapshot.isLoading ? "loading" : "empty",
|
|
7699
|
-
title: options.title ??
|
|
8200
|
+
title: options.title ?? DEFAULT_TITLE12,
|
|
7700
8201
|
updatedAt: snapshot.updatedAt
|
|
7701
8202
|
};
|
|
7702
8203
|
};
|
|
7703
8204
|
var renderVoiceProviderStatusHTML = (snapshot, options = {}) => {
|
|
7704
8205
|
const model = createVoiceProviderStatusViewModel(snapshot, options);
|
|
7705
|
-
const providers = model.providers.length ? `<div class="absolute-voice-provider-status__providers">${model.providers.map((provider) => `<article class="absolute-voice-provider-status__provider absolute-voice-provider-status__provider--${
|
|
8206
|
+
const providers = model.providers.length ? `<div class="absolute-voice-provider-status__providers">${model.providers.map((provider) => `<article class="absolute-voice-provider-status__provider absolute-voice-provider-status__provider--${escapeHtml18(provider.status)}">
|
|
7706
8207
|
<header>
|
|
7707
|
-
<strong>${
|
|
7708
|
-
<span>${
|
|
8208
|
+
<strong>${escapeHtml18(provider.label)}</strong>
|
|
8209
|
+
<span>${escapeHtml18(formatStatus5(provider.status))}</span>
|
|
7709
8210
|
</header>
|
|
7710
|
-
<p>${
|
|
8211
|
+
<p>${escapeHtml18(provider.detail)}</p>
|
|
7711
8212
|
<dl>${provider.rows.map((row) => `<div>
|
|
7712
|
-
<dt>${
|
|
7713
|
-
<dd>${
|
|
8213
|
+
<dt>${escapeHtml18(row.label)}</dt>
|
|
8214
|
+
<dd>${escapeHtml18(row.value)}</dd>
|
|
7714
8215
|
</div>`).join("")}</dl>
|
|
7715
8216
|
</article>`).join("")}</div>` : '<p class="absolute-voice-provider-status__empty">Run voice traffic to see provider health.</p>';
|
|
7716
|
-
return `<section class="absolute-voice-provider-status absolute-voice-provider-status--${
|
|
8217
|
+
return `<section class="absolute-voice-provider-status absolute-voice-provider-status--${escapeHtml18(model.status)}">
|
|
7717
8218
|
<header class="absolute-voice-provider-status__header">
|
|
7718
|
-
<span class="absolute-voice-provider-status__eyebrow">${
|
|
7719
|
-
<strong class="absolute-voice-provider-status__label">${
|
|
8219
|
+
<span class="absolute-voice-provider-status__eyebrow">${escapeHtml18(model.title)}</span>
|
|
8220
|
+
<strong class="absolute-voice-provider-status__label">${escapeHtml18(model.label)}</strong>
|
|
7720
8221
|
</header>
|
|
7721
|
-
<p class="absolute-voice-provider-status__description">${
|
|
8222
|
+
<p class="absolute-voice-provider-status__description">${escapeHtml18(model.description)}</p>
|
|
7722
8223
|
${providers}
|
|
7723
|
-
${model.error ? `<p class="absolute-voice-provider-status__error">${
|
|
8224
|
+
${model.error ? `<p class="absolute-voice-provider-status__error">${escapeHtml18(model.error)}</p>` : ""}
|
|
7724
8225
|
</section>`;
|
|
7725
8226
|
};
|
|
7726
8227
|
var getVoiceProviderStatusCSS = () => `.absolute-voice-provider-status{border:1px solid #d8d2c4;border-radius:20px;background:#fffaf0;color:#16130d;padding:18px;box-shadow:0 18px 40px rgba(47,37,18,.12);font-family:inherit}.absolute-voice-provider-status--error,.absolute-voice-provider-status--warning{border-color:#f2a7a7;background:#fff5f3}.absolute-voice-provider-status__header,.absolute-voice-provider-status__provider header{align-items:start;display:flex;gap:12px;justify-content:space-between}.absolute-voice-provider-status__eyebrow{color:#73664f;font-size:12px;font-weight:800;letter-spacing:.08em;text-transform:uppercase}.absolute-voice-provider-status__label{font-size:24px;line-height:1}.absolute-voice-provider-status__description,.absolute-voice-provider-status__provider p,.absolute-voice-provider-status__provider dt,.absolute-voice-provider-status__empty{color:#514733}.absolute-voice-provider-status__providers{display:grid;gap:12px;margin-top:14px}.absolute-voice-provider-status__provider{background:#fff;border:1px solid #eee4d2;border-radius:16px;padding:14px}.absolute-voice-provider-status__provider--degraded,.absolute-voice-provider-status__provider--rate-limited,.absolute-voice-provider-status__provider--suppressed{border-color:#f2a7a7}.absolute-voice-provider-status__provider--recoverable{border-color:#fbbf24}.absolute-voice-provider-status__provider p{margin:10px 0}.absolute-voice-provider-status__provider dl{display:grid;gap:8px;grid-template-columns:repeat(2,minmax(0,1fr));margin:0}.absolute-voice-provider-status__provider div{background:#fffaf0;border:1px solid #eee4d2;border-radius:12px;padding:8px}.absolute-voice-provider-status__provider dt{font-size:12px}.absolute-voice-provider-status__provider dd{font-weight:800;margin:4px 0 0}.absolute-voice-provider-status__empty{margin:14px 0 0}.absolute-voice-provider-status__error{color:#9f1239;font-weight:700}`;
|
|
@@ -7762,13 +8263,13 @@ var defineVoiceProviderStatusElement = (tagName = "absolute-voice-provider-statu
|
|
|
7762
8263
|
};
|
|
7763
8264
|
|
|
7764
8265
|
// src/vue/useVoiceProviderStatus.ts
|
|
7765
|
-
import { onUnmounted as
|
|
8266
|
+
import { onUnmounted as onUnmounted12, ref as ref9, shallowRef as shallowRef11 } from "vue";
|
|
7766
8267
|
function useVoiceProviderStatus(path = "/api/provider-status", options = {}) {
|
|
7767
8268
|
const store = createVoiceProviderStatusStore(path, options);
|
|
7768
|
-
const error =
|
|
7769
|
-
const isLoading =
|
|
7770
|
-
const providers =
|
|
7771
|
-
const updatedAt =
|
|
8269
|
+
const error = ref9(null);
|
|
8270
|
+
const isLoading = ref9(false);
|
|
8271
|
+
const providers = shallowRef11([]);
|
|
8272
|
+
const updatedAt = ref9(undefined);
|
|
7772
8273
|
const sync = () => {
|
|
7773
8274
|
const snapshot = store.getSnapshot();
|
|
7774
8275
|
error.value = snapshot.error;
|
|
@@ -7779,7 +8280,7 @@ function useVoiceProviderStatus(path = "/api/provider-status", options = {}) {
|
|
|
7779
8280
|
const unsubscribe = store.subscribe(sync);
|
|
7780
8281
|
sync();
|
|
7781
8282
|
store.refresh().catch(() => {});
|
|
7782
|
-
|
|
8283
|
+
onUnmounted12(() => {
|
|
7783
8284
|
unsubscribe();
|
|
7784
8285
|
store.close();
|
|
7785
8286
|
});
|
|
@@ -7793,7 +8294,7 @@ function useVoiceProviderStatus(path = "/api/provider-status", options = {}) {
|
|
|
7793
8294
|
}
|
|
7794
8295
|
|
|
7795
8296
|
// src/vue/VoiceProviderStatus.ts
|
|
7796
|
-
var VoiceProviderStatus =
|
|
8297
|
+
var VoiceProviderStatus = defineComponent13({
|
|
7797
8298
|
name: "VoiceProviderStatus",
|
|
7798
8299
|
props: {
|
|
7799
8300
|
class: {
|
|
@@ -7830,41 +8331,41 @@ var VoiceProviderStatus = defineComponent12({
|
|
|
7830
8331
|
providers: status.providers.value,
|
|
7831
8332
|
updatedAt: status.updatedAt.value
|
|
7832
8333
|
}, options));
|
|
7833
|
-
return () =>
|
|
8334
|
+
return () => h13("section", {
|
|
7834
8335
|
class: [
|
|
7835
8336
|
"absolute-voice-provider-status",
|
|
7836
8337
|
`absolute-voice-provider-status--${model.value.status}`,
|
|
7837
8338
|
props.class
|
|
7838
8339
|
]
|
|
7839
8340
|
}, [
|
|
7840
|
-
|
|
7841
|
-
|
|
7842
|
-
|
|
8341
|
+
h13("header", { class: "absolute-voice-provider-status__header" }, [
|
|
8342
|
+
h13("span", { class: "absolute-voice-provider-status__eyebrow" }, model.value.title),
|
|
8343
|
+
h13("strong", { class: "absolute-voice-provider-status__label" }, model.value.label)
|
|
7843
8344
|
]),
|
|
7844
|
-
|
|
7845
|
-
model.value.providers.length ?
|
|
8345
|
+
h13("p", { class: "absolute-voice-provider-status__description" }, model.value.description),
|
|
8346
|
+
model.value.providers.length ? h13("div", { class: "absolute-voice-provider-status__providers" }, model.value.providers.map((provider) => h13("article", {
|
|
7846
8347
|
class: [
|
|
7847
8348
|
"absolute-voice-provider-status__provider",
|
|
7848
8349
|
`absolute-voice-provider-status__provider--${provider.status}`
|
|
7849
8350
|
],
|
|
7850
8351
|
key: provider.provider
|
|
7851
8352
|
}, [
|
|
7852
|
-
|
|
7853
|
-
|
|
7854
|
-
|
|
8353
|
+
h13("header", [
|
|
8354
|
+
h13("strong", provider.label),
|
|
8355
|
+
h13("span", provider.status)
|
|
7855
8356
|
]),
|
|
7856
|
-
|
|
7857
|
-
|
|
7858
|
-
|
|
7859
|
-
|
|
8357
|
+
h13("p", provider.detail),
|
|
8358
|
+
h13("dl", provider.rows.map((row) => h13("div", { key: row.label }, [
|
|
8359
|
+
h13("dt", row.label),
|
|
8360
|
+
h13("dd", row.value)
|
|
7860
8361
|
])))
|
|
7861
|
-
]))) :
|
|
7862
|
-
model.value.error ?
|
|
8362
|
+
]))) : h13("p", { class: "absolute-voice-provider-status__empty" }, "Run voice traffic to see provider health."),
|
|
8363
|
+
model.value.error ? h13("p", { class: "absolute-voice-provider-status__error" }, model.value.error) : null
|
|
7863
8364
|
]);
|
|
7864
8365
|
}
|
|
7865
8366
|
});
|
|
7866
8367
|
// src/vue/VoiceRoutingStatus.ts
|
|
7867
|
-
import { computed as computed7, defineComponent as
|
|
8368
|
+
import { computed as computed7, defineComponent as defineComponent14, h as h14 } from "vue";
|
|
7868
8369
|
|
|
7869
8370
|
// src/client/routingStatus.ts
|
|
7870
8371
|
var fetchVoiceRoutingStatus = async (path = "/api/routing/latest", options = {}) => {
|
|
@@ -7947,9 +8448,9 @@ var createVoiceRoutingStatusStore = (path = "/api/routing/latest", options = {})
|
|
|
7947
8448
|
};
|
|
7948
8449
|
|
|
7949
8450
|
// src/client/routingStatusWidget.ts
|
|
7950
|
-
var
|
|
7951
|
-
var
|
|
7952
|
-
var
|
|
8451
|
+
var DEFAULT_TITLE13 = "Voice Routing";
|
|
8452
|
+
var DEFAULT_DESCRIPTION13 = "Latest provider routing decision from the self-hosted trace store.";
|
|
8453
|
+
var escapeHtml19 = (value) => value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'");
|
|
7953
8454
|
var formatValue = (value, fallback = "None") => typeof value === "string" && value.trim() ? value : typeof value === "number" && Number.isFinite(value) ? String(value) : fallback;
|
|
7954
8455
|
var formatProviderRoutes = (routes) => routes && typeof routes === "object" ? Object.entries(routes).map(([role, provider]) => `${role}: ${formatValue(provider)}`).join(", ") || "None" : "None";
|
|
7955
8456
|
var getProviderRoute = (routes, role) => routes && typeof routes === "object" ? formatValue(routes[role], "Not configured") : "Not configured";
|
|
@@ -8018,35 +8519,35 @@ var createVoiceRoutingStatusViewModel = (snapshot, options = {}) => {
|
|
|
8018
8519
|
return {
|
|
8019
8520
|
activeStack,
|
|
8020
8521
|
decision,
|
|
8021
|
-
description: options.description ??
|
|
8522
|
+
description: options.description ?? DEFAULT_DESCRIPTION13,
|
|
8022
8523
|
error: snapshot.error,
|
|
8023
8524
|
isLoading: snapshot.isLoading,
|
|
8024
8525
|
label: snapshot.error ? "Unavailable" : decision ? `${formatValue(decision.kind).toUpperCase()} ${formatValue(decision.status, "unknown")}` : snapshot.isLoading ? "Checking" : "No routing yet",
|
|
8025
8526
|
rows,
|
|
8026
8527
|
status: snapshot.error ? "error" : decision ? "ready" : snapshot.isLoading ? "loading" : "empty",
|
|
8027
|
-
title: options.title ??
|
|
8528
|
+
title: options.title ?? DEFAULT_TITLE13,
|
|
8028
8529
|
updatedAt: snapshot.updatedAt
|
|
8029
8530
|
};
|
|
8030
8531
|
};
|
|
8031
8532
|
var renderVoiceRoutingStatusHTML = (snapshot, options = {}) => {
|
|
8032
8533
|
const model = createVoiceRoutingStatusViewModel(snapshot, options);
|
|
8033
8534
|
const activeStack = model.activeStack.length ? `<div class="absolute-voice-routing-status__stack" aria-label="Active voice stack">${model.activeStack.map((item) => `<div>
|
|
8034
|
-
<span>${
|
|
8035
|
-
<strong>${
|
|
8535
|
+
<span>${escapeHtml19(item.label)}</span>
|
|
8536
|
+
<strong>${escapeHtml19(item.value)}</strong>
|
|
8036
8537
|
</div>`).join("")}</div>` : "";
|
|
8037
8538
|
const rows = model.rows.length ? `<div class="absolute-voice-routing-status__grid">${model.rows.map((row) => `<div>
|
|
8038
|
-
<span>${
|
|
8039
|
-
<strong>${
|
|
8539
|
+
<span>${escapeHtml19(row.label)}</span>
|
|
8540
|
+
<strong>${escapeHtml19(row.value)}</strong>
|
|
8040
8541
|
</div>`).join("")}</div>` : '<p class="absolute-voice-routing-status__empty">Start a voice session to see the selected provider.</p>';
|
|
8041
|
-
return `<section class="absolute-voice-routing-status absolute-voice-routing-status--${
|
|
8542
|
+
return `<section class="absolute-voice-routing-status absolute-voice-routing-status--${escapeHtml19(model.status)}">
|
|
8042
8543
|
<header class="absolute-voice-routing-status__header">
|
|
8043
|
-
<span class="absolute-voice-routing-status__eyebrow">${
|
|
8044
|
-
<strong class="absolute-voice-routing-status__label">${
|
|
8544
|
+
<span class="absolute-voice-routing-status__eyebrow">${escapeHtml19(model.title)}</span>
|
|
8545
|
+
<strong class="absolute-voice-routing-status__label">${escapeHtml19(model.label)}</strong>
|
|
8045
8546
|
</header>
|
|
8046
|
-
<p class="absolute-voice-routing-status__description">${
|
|
8547
|
+
<p class="absolute-voice-routing-status__description">${escapeHtml19(model.description)}</p>
|
|
8047
8548
|
${activeStack}
|
|
8048
8549
|
${rows}
|
|
8049
|
-
${model.error ? `<p class="absolute-voice-routing-status__error">${
|
|
8550
|
+
${model.error ? `<p class="absolute-voice-routing-status__error">${escapeHtml19(model.error)}</p>` : ""}
|
|
8050
8551
|
</section>`;
|
|
8051
8552
|
};
|
|
8052
8553
|
var getVoiceRoutingStatusCSS = () => `.absolute-voice-routing-status{border:1px solid #d8d2c4;border-radius:20px;background:#fffaf0;color:#16130d;padding:18px;box-shadow:0 18px 40px rgba(47,37,18,.12);font-family:inherit}.absolute-voice-routing-status--error{border-color:#f2a7a7;background:#fff5f3}.absolute-voice-routing-status__header{align-items:start;display:flex;gap:12px;justify-content:space-between}.absolute-voice-routing-status__eyebrow{color:#73664f;font-size:12px;font-weight:800;letter-spacing:.08em;text-transform:uppercase}.absolute-voice-routing-status__label{font-size:24px;line-height:1}.absolute-voice-routing-status__description{color:#514733;margin:12px 0 0}.absolute-voice-routing-status__stack{background:linear-gradient(135deg,#16130d,#49391f);border-radius:18px;color:#fff;display:grid;gap:8px;grid-template-columns:repeat(5,minmax(0,1fr));margin-top:14px;padding:12px}.absolute-voice-routing-status__stack div{border-left:1px solid rgba(255,255,255,.18);padding-left:10px}.absolute-voice-routing-status__stack div:first-child{border-left:0;padding-left:0}.absolute-voice-routing-status__stack span{color:#e9d9b8;display:block;font-size:11px;font-weight:800;letter-spacing:.08em;margin-bottom:5px;text-transform:uppercase}.absolute-voice-routing-status__stack strong{display:block;font-size:13px;line-height:1.25;overflow-wrap:anywhere}.absolute-voice-routing-status__grid{display:grid;gap:8px;grid-template-columns:repeat(2,minmax(0,1fr));margin-top:14px}.absolute-voice-routing-status__grid div{background:#fff;border:1px solid #eee4d2;border-radius:14px;padding:10px 12px}.absolute-voice-routing-status__grid span{color:#655944;display:block;font-size:12px;margin-bottom:4px}.absolute-voice-routing-status__grid strong{overflow-wrap:anywhere}.absolute-voice-routing-status__empty{color:#655944;margin:14px 0 0}.absolute-voice-routing-status__error{color:#9f1239;font-weight:700}@media (max-width:760px){.absolute-voice-routing-status__stack{grid-template-columns:repeat(2,minmax(0,1fr))}.absolute-voice-routing-status__stack div{border-left:0;border-top:1px solid rgba(255,255,255,.18);padding-left:0;padding-top:8px}.absolute-voice-routing-status__stack div:first-child{border-top:0;padding-top:0}}`;
|
|
@@ -8088,13 +8589,13 @@ var defineVoiceRoutingStatusElement = (tagName = "absolute-voice-routing-status"
|
|
|
8088
8589
|
};
|
|
8089
8590
|
|
|
8090
8591
|
// src/vue/useVoiceRoutingStatus.ts
|
|
8091
|
-
import { onUnmounted as
|
|
8592
|
+
import { onUnmounted as onUnmounted13, ref as ref10, shallowRef as shallowRef12 } from "vue";
|
|
8092
8593
|
function useVoiceRoutingStatus(path = "/api/routing/latest", options = {}) {
|
|
8093
8594
|
const store = createVoiceRoutingStatusStore(path, options);
|
|
8094
|
-
const decision =
|
|
8095
|
-
const error =
|
|
8096
|
-
const isLoading =
|
|
8097
|
-
const updatedAt =
|
|
8595
|
+
const decision = shallowRef12(null);
|
|
8596
|
+
const error = ref10(null);
|
|
8597
|
+
const isLoading = ref10(false);
|
|
8598
|
+
const updatedAt = ref10(undefined);
|
|
8098
8599
|
const sync = () => {
|
|
8099
8600
|
const snapshot = store.getSnapshot();
|
|
8100
8601
|
decision.value = snapshot.decision;
|
|
@@ -8105,7 +8606,7 @@ function useVoiceRoutingStatus(path = "/api/routing/latest", options = {}) {
|
|
|
8105
8606
|
const unsubscribe = store.subscribe(sync);
|
|
8106
8607
|
sync();
|
|
8107
8608
|
store.refresh().catch(() => {});
|
|
8108
|
-
|
|
8609
|
+
onUnmounted13(() => {
|
|
8109
8610
|
unsubscribe();
|
|
8110
8611
|
store.close();
|
|
8111
8612
|
});
|
|
@@ -8119,7 +8620,7 @@ function useVoiceRoutingStatus(path = "/api/routing/latest", options = {}) {
|
|
|
8119
8620
|
}
|
|
8120
8621
|
|
|
8121
8622
|
// src/vue/VoiceRoutingStatus.ts
|
|
8122
|
-
var VoiceRoutingStatus =
|
|
8623
|
+
var VoiceRoutingStatus = defineComponent14({
|
|
8123
8624
|
name: "VoiceRoutingStatus",
|
|
8124
8625
|
props: {
|
|
8125
8626
|
class: {
|
|
@@ -8156,28 +8657,28 @@ var VoiceRoutingStatus = defineComponent13({
|
|
|
8156
8657
|
isLoading: status.isLoading.value,
|
|
8157
8658
|
updatedAt: status.updatedAt.value
|
|
8158
8659
|
}, options));
|
|
8159
|
-
return () =>
|
|
8660
|
+
return () => h14("section", {
|
|
8160
8661
|
class: [
|
|
8161
8662
|
"absolute-voice-routing-status",
|
|
8162
8663
|
`absolute-voice-routing-status--${model.value.status}`,
|
|
8163
8664
|
props.class
|
|
8164
8665
|
]
|
|
8165
8666
|
}, [
|
|
8166
|
-
|
|
8167
|
-
|
|
8168
|
-
|
|
8667
|
+
h14("header", { class: "absolute-voice-routing-status__header" }, [
|
|
8668
|
+
h14("span", { class: "absolute-voice-routing-status__eyebrow" }, model.value.title),
|
|
8669
|
+
h14("strong", { class: "absolute-voice-routing-status__label" }, model.value.label)
|
|
8169
8670
|
]),
|
|
8170
|
-
|
|
8171
|
-
model.value.rows.length ?
|
|
8172
|
-
|
|
8173
|
-
|
|
8174
|
-
]))) :
|
|
8175
|
-
model.value.error ?
|
|
8671
|
+
h14("p", { class: "absolute-voice-routing-status__description" }, model.value.description),
|
|
8672
|
+
model.value.rows.length ? h14("div", { class: "absolute-voice-routing-status__grid" }, model.value.rows.map((row) => h14("div", { key: row.label }, [
|
|
8673
|
+
h14("span", row.label),
|
|
8674
|
+
h14("strong", row.value)
|
|
8675
|
+
]))) : h14("p", { class: "absolute-voice-routing-status__empty" }, "Start a voice session to see the selected provider."),
|
|
8676
|
+
model.value.error ? h14("p", { class: "absolute-voice-routing-status__error" }, model.value.error) : null
|
|
8176
8677
|
]);
|
|
8177
8678
|
}
|
|
8178
8679
|
});
|
|
8179
8680
|
// src/vue/useVoiceAgentSquadStatus.ts
|
|
8180
|
-
import { onUnmounted as
|
|
8681
|
+
import { onUnmounted as onUnmounted14, ref as ref11, shallowRef as shallowRef13 } from "vue";
|
|
8181
8682
|
|
|
8182
8683
|
// src/client/traceTimeline.ts
|
|
8183
8684
|
var fetchVoiceTraceTimeline = async (path = "/api/voice-traces", options = {}) => {
|
|
@@ -8336,11 +8837,11 @@ var createVoiceAgentSquadStatusStore = (path = "/api/voice-traces", options = {}
|
|
|
8336
8837
|
// src/vue/useVoiceAgentSquadStatus.ts
|
|
8337
8838
|
function useVoiceAgentSquadStatus(path = "/api/voice-traces", options = {}) {
|
|
8338
8839
|
const store = createVoiceAgentSquadStatusStore(path, options);
|
|
8339
|
-
const current =
|
|
8340
|
-
const error =
|
|
8341
|
-
const isLoading =
|
|
8342
|
-
const report =
|
|
8343
|
-
const updatedAt =
|
|
8840
|
+
const current = shallowRef13(undefined);
|
|
8841
|
+
const error = ref11(null);
|
|
8842
|
+
const isLoading = ref11(false);
|
|
8843
|
+
const report = shallowRef13(undefined);
|
|
8844
|
+
const updatedAt = ref11(undefined);
|
|
8344
8845
|
const sync = () => {
|
|
8345
8846
|
const snapshot = store.getSnapshot();
|
|
8346
8847
|
current.value = snapshot.report.current;
|
|
@@ -8354,7 +8855,7 @@ function useVoiceAgentSquadStatus(path = "/api/voice-traces", options = {}) {
|
|
|
8354
8855
|
if (typeof window !== "undefined") {
|
|
8355
8856
|
store.refresh().catch(() => {});
|
|
8356
8857
|
}
|
|
8357
|
-
|
|
8858
|
+
onUnmounted14(() => {
|
|
8358
8859
|
unsubscribe();
|
|
8359
8860
|
store.close();
|
|
8360
8861
|
});
|
|
@@ -8368,7 +8869,7 @@ function useVoiceAgentSquadStatus(path = "/api/voice-traces", options = {}) {
|
|
|
8368
8869
|
};
|
|
8369
8870
|
}
|
|
8370
8871
|
// src/vue/VoiceTurnLatency.ts
|
|
8371
|
-
import { computed as computed8, defineComponent as
|
|
8872
|
+
import { computed as computed8, defineComponent as defineComponent15, h as h15 } from "vue";
|
|
8372
8873
|
|
|
8373
8874
|
// src/client/turnLatency.ts
|
|
8374
8875
|
var fetchVoiceTurnLatency = async (path = "/api/turn-latency", options = {}) => {
|
|
@@ -8474,56 +8975,56 @@ var createVoiceTurnLatencyStore = (path = "/api/turn-latency", options = {}) =>
|
|
|
8474
8975
|
};
|
|
8475
8976
|
|
|
8476
8977
|
// src/client/turnLatencyWidget.ts
|
|
8477
|
-
var
|
|
8478
|
-
var
|
|
8978
|
+
var DEFAULT_TITLE14 = "Turn Latency";
|
|
8979
|
+
var DEFAULT_DESCRIPTION14 = "Per-turn timing from first transcript to commit and assistant response start.";
|
|
8479
8980
|
var DEFAULT_PROOF_LABEL = "Run latency proof";
|
|
8480
|
-
var
|
|
8481
|
-
var
|
|
8981
|
+
var escapeHtml20 = (value) => value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'");
|
|
8982
|
+
var formatMs3 = (value) => typeof value === "number" ? `${Math.round(value)}ms` : "n/a";
|
|
8482
8983
|
var createVoiceTurnLatencyViewModel = (snapshot, options = {}) => {
|
|
8483
8984
|
const turns = (snapshot.report?.turns ?? []).map((turn) => ({
|
|
8484
8985
|
...turn,
|
|
8485
8986
|
label: turn.text || "Empty turn",
|
|
8486
8987
|
rows: turn.stages.map((stage) => ({
|
|
8487
8988
|
label: stage.label,
|
|
8488
|
-
value:
|
|
8989
|
+
value: formatMs3(stage.valueMs)
|
|
8489
8990
|
}))
|
|
8490
8991
|
}));
|
|
8491
8992
|
const warningCount = snapshot.report?.warnings ?? turns.filter((turn) => turn.status === "warn").length;
|
|
8492
8993
|
const failedCount = snapshot.report?.failed ?? turns.filter((turn) => turn.status === "fail").length;
|
|
8493
8994
|
return {
|
|
8494
|
-
description: options.description ??
|
|
8995
|
+
description: options.description ?? DEFAULT_DESCRIPTION14,
|
|
8495
8996
|
error: snapshot.error,
|
|
8496
8997
|
isLoading: snapshot.isLoading,
|
|
8497
|
-
label: snapshot.error ? "Unavailable" : turns.length ? failedCount > 0 ? `${failedCount} slow` : warningCount > 0 ? `${warningCount} warnings` : `avg ${
|
|
8998
|
+
label: snapshot.error ? "Unavailable" : turns.length ? failedCount > 0 ? `${failedCount} slow` : warningCount > 0 ? `${warningCount} warnings` : `avg ${formatMs3(snapshot.report?.averageTotalMs)}` : snapshot.isLoading ? "Checking" : "No turns",
|
|
8498
8999
|
proofLabel: options.proofPath ? options.proofLabel ?? DEFAULT_PROOF_LABEL : undefined,
|
|
8499
9000
|
showProofAction: Boolean(options.proofPath),
|
|
8500
9001
|
status: snapshot.error ? "error" : turns.length ? failedCount > 0 || warningCount > 0 ? "warning" : "ready" : snapshot.isLoading ? "loading" : "empty",
|
|
8501
|
-
title: options.title ??
|
|
9002
|
+
title: options.title ?? DEFAULT_TITLE14,
|
|
8502
9003
|
turns,
|
|
8503
9004
|
updatedAt: snapshot.updatedAt
|
|
8504
9005
|
};
|
|
8505
9006
|
};
|
|
8506
9007
|
var renderVoiceTurnLatencyHTML = (snapshot, options = {}) => {
|
|
8507
9008
|
const model = createVoiceTurnLatencyViewModel(snapshot, options);
|
|
8508
|
-
const turns = model.turns.length ? `<div class="absolute-voice-turn-latency__turns">${model.turns.map((turn) => `<article class="absolute-voice-turn-latency__turn absolute-voice-turn-latency__turn--${
|
|
9009
|
+
const turns = model.turns.length ? `<div class="absolute-voice-turn-latency__turns">${model.turns.map((turn) => `<article class="absolute-voice-turn-latency__turn absolute-voice-turn-latency__turn--${escapeHtml20(turn.status)}">
|
|
8509
9010
|
<header>
|
|
8510
|
-
<strong>${
|
|
8511
|
-
<span>${
|
|
9011
|
+
<strong>${escapeHtml20(turn.label)}</strong>
|
|
9012
|
+
<span>${escapeHtml20(turn.status)}</span>
|
|
8512
9013
|
</header>
|
|
8513
9014
|
<dl>${turn.rows.map((row) => `<div>
|
|
8514
|
-
<dt>${
|
|
8515
|
-
<dd>${
|
|
9015
|
+
<dt>${escapeHtml20(row.label)}</dt>
|
|
9016
|
+
<dd>${escapeHtml20(row.value)}</dd>
|
|
8516
9017
|
</div>`).join("")}</dl>
|
|
8517
9018
|
</article>`).join("")}</div>` : '<p class="absolute-voice-turn-latency__empty">Complete a voice turn to see latency diagnostics.</p>';
|
|
8518
|
-
return `<section class="absolute-voice-turn-latency absolute-voice-turn-latency--${
|
|
9019
|
+
return `<section class="absolute-voice-turn-latency absolute-voice-turn-latency--${escapeHtml20(model.status)}">
|
|
8519
9020
|
<header class="absolute-voice-turn-latency__header">
|
|
8520
|
-
<span class="absolute-voice-turn-latency__eyebrow">${
|
|
8521
|
-
<strong class="absolute-voice-turn-latency__label">${
|
|
9021
|
+
<span class="absolute-voice-turn-latency__eyebrow">${escapeHtml20(model.title)}</span>
|
|
9022
|
+
<strong class="absolute-voice-turn-latency__label">${escapeHtml20(model.label)}</strong>
|
|
8522
9023
|
</header>
|
|
8523
|
-
<p class="absolute-voice-turn-latency__description">${
|
|
8524
|
-
${model.showProofAction ? `<button class="absolute-voice-turn-latency__proof" data-absolute-voice-turn-latency-proof type="button">${
|
|
9024
|
+
<p class="absolute-voice-turn-latency__description">${escapeHtml20(model.description)}</p>
|
|
9025
|
+
${model.showProofAction ? `<button class="absolute-voice-turn-latency__proof" data-absolute-voice-turn-latency-proof type="button">${escapeHtml20(model.proofLabel ?? DEFAULT_PROOF_LABEL)}</button>` : ""}
|
|
8525
9026
|
${turns}
|
|
8526
|
-
${model.error ? `<p class="absolute-voice-turn-latency__error">${
|
|
9027
|
+
${model.error ? `<p class="absolute-voice-turn-latency__error">${escapeHtml20(model.error)}</p>` : ""}
|
|
8527
9028
|
</section>`;
|
|
8528
9029
|
};
|
|
8529
9030
|
var mountVoiceTurnLatency = (element, path = "/api/turn-latency", options = {}) => {
|
|
@@ -8574,13 +9075,13 @@ var defineVoiceTurnLatencyElement = (tagName = "absolute-voice-turn-latency") =>
|
|
|
8574
9075
|
};
|
|
8575
9076
|
|
|
8576
9077
|
// src/vue/useVoiceTurnLatency.ts
|
|
8577
|
-
import { onUnmounted as
|
|
9078
|
+
import { onUnmounted as onUnmounted15, shallowRef as shallowRef14 } from "vue";
|
|
8578
9079
|
function useVoiceTurnLatency(path = "/api/turn-latency", options = {}) {
|
|
8579
9080
|
const store = createVoiceTurnLatencyStore(path, options);
|
|
8580
|
-
const error =
|
|
8581
|
-
const isLoading =
|
|
8582
|
-
const report =
|
|
8583
|
-
const updatedAt =
|
|
9081
|
+
const error = shallowRef14(null);
|
|
9082
|
+
const isLoading = shallowRef14(false);
|
|
9083
|
+
const report = shallowRef14();
|
|
9084
|
+
const updatedAt = shallowRef14(undefined);
|
|
8584
9085
|
const sync = () => {
|
|
8585
9086
|
const snapshot = store.getSnapshot();
|
|
8586
9087
|
error.value = snapshot.error;
|
|
@@ -8591,7 +9092,7 @@ function useVoiceTurnLatency(path = "/api/turn-latency", options = {}) {
|
|
|
8591
9092
|
const unsubscribe = store.subscribe(sync);
|
|
8592
9093
|
sync();
|
|
8593
9094
|
store.refresh().catch(() => {});
|
|
8594
|
-
|
|
9095
|
+
onUnmounted15(() => {
|
|
8595
9096
|
unsubscribe();
|
|
8596
9097
|
store.close();
|
|
8597
9098
|
});
|
|
@@ -8606,7 +9107,7 @@ function useVoiceTurnLatency(path = "/api/turn-latency", options = {}) {
|
|
|
8606
9107
|
}
|
|
8607
9108
|
|
|
8608
9109
|
// src/vue/VoiceTurnLatency.ts
|
|
8609
|
-
var VoiceTurnLatency =
|
|
9110
|
+
var VoiceTurnLatency = defineComponent15({
|
|
8610
9111
|
name: "VoiceTurnLatency",
|
|
8611
9112
|
props: {
|
|
8612
9113
|
class: { default: "", type: String },
|
|
@@ -8632,47 +9133,47 @@ var VoiceTurnLatency = defineComponent14({
|
|
|
8632
9133
|
report: latency.report.value,
|
|
8633
9134
|
updatedAt: latency.updatedAt.value
|
|
8634
9135
|
}, options));
|
|
8635
|
-
return () =>
|
|
9136
|
+
return () => h15("section", {
|
|
8636
9137
|
class: [
|
|
8637
9138
|
"absolute-voice-turn-latency",
|
|
8638
9139
|
`absolute-voice-turn-latency--${model.value.status}`,
|
|
8639
9140
|
props.class
|
|
8640
9141
|
]
|
|
8641
9142
|
}, [
|
|
8642
|
-
|
|
8643
|
-
|
|
8644
|
-
|
|
9143
|
+
h15("header", { class: "absolute-voice-turn-latency__header" }, [
|
|
9144
|
+
h15("span", { class: "absolute-voice-turn-latency__eyebrow" }, model.value.title),
|
|
9145
|
+
h15("strong", { class: "absolute-voice-turn-latency__label" }, model.value.label)
|
|
8645
9146
|
]),
|
|
8646
|
-
|
|
8647
|
-
model.value.showProofAction ?
|
|
9147
|
+
h15("p", { class: "absolute-voice-turn-latency__description" }, model.value.description),
|
|
9148
|
+
model.value.showProofAction ? h15("button", {
|
|
8648
9149
|
class: "absolute-voice-turn-latency__proof",
|
|
8649
9150
|
onClick: () => {
|
|
8650
9151
|
latency.runProof().catch(() => {});
|
|
8651
9152
|
},
|
|
8652
9153
|
type: "button"
|
|
8653
9154
|
}, model.value.proofLabel) : null,
|
|
8654
|
-
model.value.turns.length ?
|
|
9155
|
+
model.value.turns.length ? h15("div", { class: "absolute-voice-turn-latency__turns" }, model.value.turns.map((turn) => h15("article", {
|
|
8655
9156
|
class: [
|
|
8656
9157
|
"absolute-voice-turn-latency__turn",
|
|
8657
9158
|
`absolute-voice-turn-latency__turn--${turn.status}`
|
|
8658
9159
|
],
|
|
8659
9160
|
key: `${turn.sessionId}:${turn.turnId}`
|
|
8660
9161
|
}, [
|
|
8661
|
-
|
|
8662
|
-
|
|
8663
|
-
|
|
9162
|
+
h15("header", [
|
|
9163
|
+
h15("strong", turn.label),
|
|
9164
|
+
h15("span", turn.status)
|
|
8664
9165
|
]),
|
|
8665
|
-
|
|
8666
|
-
|
|
8667
|
-
|
|
9166
|
+
h15("dl", turn.rows.map((row) => h15("div", { key: row.label }, [
|
|
9167
|
+
h15("dt", row.label),
|
|
9168
|
+
h15("dd", row.value)
|
|
8668
9169
|
])))
|
|
8669
|
-
]))) :
|
|
8670
|
-
model.value.error ?
|
|
9170
|
+
]))) : h15("p", { class: "absolute-voice-turn-latency__empty" }, "Complete a voice turn to see latency diagnostics."),
|
|
9171
|
+
model.value.error ? h15("p", { class: "absolute-voice-turn-latency__error" }, model.value.error) : null
|
|
8671
9172
|
]);
|
|
8672
9173
|
}
|
|
8673
9174
|
});
|
|
8674
9175
|
// src/vue/VoiceTurnQuality.ts
|
|
8675
|
-
import { computed as computed9, defineComponent as
|
|
9176
|
+
import { computed as computed9, defineComponent as defineComponent16, h as h16 } from "vue";
|
|
8676
9177
|
|
|
8677
9178
|
// src/client/turnQuality.ts
|
|
8678
9179
|
var fetchVoiceTurnQuality = async (path = "/api/turn-quality", options = {}) => {
|
|
@@ -8754,9 +9255,9 @@ var createVoiceTurnQualityStore = (path = "/api/turn-quality", options = {}) =>
|
|
|
8754
9255
|
};
|
|
8755
9256
|
|
|
8756
9257
|
// src/client/turnQualityWidget.ts
|
|
8757
|
-
var
|
|
8758
|
-
var
|
|
8759
|
-
var
|
|
9258
|
+
var DEFAULT_TITLE15 = "Turn Quality";
|
|
9259
|
+
var DEFAULT_DESCRIPTION15 = "Per-turn STT confidence, fallback selection, corrections, and transcript coverage.";
|
|
9260
|
+
var escapeHtml21 = (value) => value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'");
|
|
8760
9261
|
var formatConfidence = (value) => typeof value === "number" ? `${Math.round(value * 100)}%` : "n/a";
|
|
8761
9262
|
var formatMaybe = (value) => value === undefined || value === "" ? "n/a" : String(value);
|
|
8762
9263
|
var getTurnDetail = (turn) => {
|
|
@@ -8800,37 +9301,37 @@ var createVoiceTurnQualityViewModel = (snapshot, options = {}) => {
|
|
|
8800
9301
|
const warningCount = snapshot.report?.warnings ?? turns.filter((turn) => turn.status === "warn").length;
|
|
8801
9302
|
const failedCount = snapshot.report?.failed ?? turns.filter((turn) => turn.status === "fail").length;
|
|
8802
9303
|
return {
|
|
8803
|
-
description: options.description ??
|
|
9304
|
+
description: options.description ?? DEFAULT_DESCRIPTION15,
|
|
8804
9305
|
error: snapshot.error,
|
|
8805
9306
|
isLoading: snapshot.isLoading,
|
|
8806
9307
|
label: snapshot.error ? "Unavailable" : turns.length ? failedCount > 0 ? `${failedCount} failed` : warningCount > 0 ? `${warningCount} warnings` : `${turns.length} healthy` : snapshot.isLoading ? "Checking" : "No turns",
|
|
8807
9308
|
status: snapshot.error ? "error" : turns.length ? failedCount > 0 || warningCount > 0 ? "warning" : "ready" : snapshot.isLoading ? "loading" : "empty",
|
|
8808
|
-
title: options.title ??
|
|
9309
|
+
title: options.title ?? DEFAULT_TITLE15,
|
|
8809
9310
|
turns,
|
|
8810
9311
|
updatedAt: snapshot.updatedAt
|
|
8811
9312
|
};
|
|
8812
9313
|
};
|
|
8813
9314
|
var renderVoiceTurnQualityHTML = (snapshot, options = {}) => {
|
|
8814
9315
|
const model = createVoiceTurnQualityViewModel(snapshot, options);
|
|
8815
|
-
const turns = model.turns.length ? `<div class="absolute-voice-turn-quality__turns">${model.turns.map((turn) => `<article class="absolute-voice-turn-quality__turn absolute-voice-turn-quality__turn--${
|
|
9316
|
+
const turns = model.turns.length ? `<div class="absolute-voice-turn-quality__turns">${model.turns.map((turn) => `<article class="absolute-voice-turn-quality__turn absolute-voice-turn-quality__turn--${escapeHtml21(turn.status)}">
|
|
8816
9317
|
<header>
|
|
8817
|
-
<strong>${
|
|
8818
|
-
<span>${
|
|
9318
|
+
<strong>${escapeHtml21(turn.label)}</strong>
|
|
9319
|
+
<span>${escapeHtml21(turn.status)}</span>
|
|
8819
9320
|
</header>
|
|
8820
|
-
<p>${
|
|
9321
|
+
<p>${escapeHtml21(turn.detail)}</p>
|
|
8821
9322
|
<dl>${turn.rows.map((row) => `<div>
|
|
8822
|
-
<dt>${
|
|
8823
|
-
<dd>${
|
|
9323
|
+
<dt>${escapeHtml21(row.label)}</dt>
|
|
9324
|
+
<dd>${escapeHtml21(row.value)}</dd>
|
|
8824
9325
|
</div>`).join("")}</dl>
|
|
8825
9326
|
</article>`).join("")}</div>` : '<p class="absolute-voice-turn-quality__empty">Complete a voice turn to see STT quality diagnostics.</p>';
|
|
8826
|
-
return `<section class="absolute-voice-turn-quality absolute-voice-turn-quality--${
|
|
9327
|
+
return `<section class="absolute-voice-turn-quality absolute-voice-turn-quality--${escapeHtml21(model.status)}">
|
|
8827
9328
|
<header class="absolute-voice-turn-quality__header">
|
|
8828
|
-
<span class="absolute-voice-turn-quality__eyebrow">${
|
|
8829
|
-
<strong class="absolute-voice-turn-quality__label">${
|
|
9329
|
+
<span class="absolute-voice-turn-quality__eyebrow">${escapeHtml21(model.title)}</span>
|
|
9330
|
+
<strong class="absolute-voice-turn-quality__label">${escapeHtml21(model.label)}</strong>
|
|
8830
9331
|
</header>
|
|
8831
|
-
<p class="absolute-voice-turn-quality__description">${
|
|
9332
|
+
<p class="absolute-voice-turn-quality__description">${escapeHtml21(model.description)}</p>
|
|
8832
9333
|
${turns}
|
|
8833
|
-
${model.error ? `<p class="absolute-voice-turn-quality__error">${
|
|
9334
|
+
${model.error ? `<p class="absolute-voice-turn-quality__error">${escapeHtml21(model.error)}</p>` : ""}
|
|
8834
9335
|
</section>`;
|
|
8835
9336
|
};
|
|
8836
9337
|
var getVoiceTurnQualityCSS = () => `.absolute-voice-turn-quality{border:1px solid #e4d1a3;border-radius:20px;background:#fff9eb;color:#17120a;padding:18px;box-shadow:0 18px 40px rgba(73,48,14,.12);font-family:inherit}.absolute-voice-turn-quality--error,.absolute-voice-turn-quality--warning{border-color:#f2a7a7;background:#fff5f3}.absolute-voice-turn-quality__header,.absolute-voice-turn-quality__turn header{align-items:start;display:flex;gap:12px;justify-content:space-between}.absolute-voice-turn-quality__eyebrow{color:#8a5a0a;font-size:12px;font-weight:800;letter-spacing:.08em;text-transform:uppercase}.absolute-voice-turn-quality__label{font-size:24px;line-height:1}.absolute-voice-turn-quality__description,.absolute-voice-turn-quality__turn p,.absolute-voice-turn-quality__turn dt,.absolute-voice-turn-quality__empty{color:#5a4930}.absolute-voice-turn-quality__turns{display:grid;gap:12px;margin-top:14px}.absolute-voice-turn-quality__turn{background:#fff;border:1px solid #f0dfba;border-radius:16px;padding:14px}.absolute-voice-turn-quality__turn--pass{border-color:#86efac}.absolute-voice-turn-quality__turn--warn,.absolute-voice-turn-quality__turn--unknown{border-color:#fbbf24}.absolute-voice-turn-quality__turn--fail{border-color:#f2a7a7}.absolute-voice-turn-quality__turn p{margin:10px 0}.absolute-voice-turn-quality__turn dl{display:grid;gap:8px;grid-template-columns:repeat(2,minmax(0,1fr));margin:0}.absolute-voice-turn-quality__turn div{background:#fff9eb;border:1px solid #f0dfba;border-radius:12px;padding:8px}.absolute-voice-turn-quality__turn dt{font-size:12px}.absolute-voice-turn-quality__turn dd{font-weight:800;margin:4px 0 0}.absolute-voice-turn-quality__empty{margin:14px 0 0}.absolute-voice-turn-quality__error{color:#9f1239;font-weight:700}`;
|
|
@@ -8872,13 +9373,13 @@ var defineVoiceTurnQualityElement = (tagName = "absolute-voice-turn-quality") =>
|
|
|
8872
9373
|
};
|
|
8873
9374
|
|
|
8874
9375
|
// src/vue/useVoiceTurnQuality.ts
|
|
8875
|
-
import { onUnmounted as
|
|
9376
|
+
import { onUnmounted as onUnmounted16, shallowRef as shallowRef15 } from "vue";
|
|
8876
9377
|
function useVoiceTurnQuality(path = "/api/turn-quality", options = {}) {
|
|
8877
9378
|
const store = createVoiceTurnQualityStore(path, options);
|
|
8878
|
-
const error =
|
|
8879
|
-
const isLoading =
|
|
8880
|
-
const report =
|
|
8881
|
-
const updatedAt =
|
|
9379
|
+
const error = shallowRef15(null);
|
|
9380
|
+
const isLoading = shallowRef15(false);
|
|
9381
|
+
const report = shallowRef15();
|
|
9382
|
+
const updatedAt = shallowRef15(undefined);
|
|
8882
9383
|
const sync = () => {
|
|
8883
9384
|
const snapshot = store.getSnapshot();
|
|
8884
9385
|
error.value = snapshot.error;
|
|
@@ -8889,7 +9390,7 @@ function useVoiceTurnQuality(path = "/api/turn-quality", options = {}) {
|
|
|
8889
9390
|
const unsubscribe = store.subscribe(sync);
|
|
8890
9391
|
sync();
|
|
8891
9392
|
store.refresh().catch(() => {});
|
|
8892
|
-
|
|
9393
|
+
onUnmounted16(() => {
|
|
8893
9394
|
unsubscribe();
|
|
8894
9395
|
store.close();
|
|
8895
9396
|
});
|
|
@@ -8897,7 +9398,7 @@ function useVoiceTurnQuality(path = "/api/turn-quality", options = {}) {
|
|
|
8897
9398
|
}
|
|
8898
9399
|
|
|
8899
9400
|
// src/vue/VoiceTurnQuality.ts
|
|
8900
|
-
var VoiceTurnQuality =
|
|
9401
|
+
var VoiceTurnQuality = defineComponent16({
|
|
8901
9402
|
name: "VoiceTurnQuality",
|
|
8902
9403
|
props: {
|
|
8903
9404
|
class: { default: "", type: String },
|
|
@@ -8919,41 +9420,41 @@ var VoiceTurnQuality = defineComponent15({
|
|
|
8919
9420
|
report: quality.report.value,
|
|
8920
9421
|
updatedAt: quality.updatedAt.value
|
|
8921
9422
|
}, options));
|
|
8922
|
-
return () =>
|
|
9423
|
+
return () => h16("section", {
|
|
8923
9424
|
class: [
|
|
8924
9425
|
"absolute-voice-turn-quality",
|
|
8925
9426
|
`absolute-voice-turn-quality--${model.value.status}`,
|
|
8926
9427
|
props.class
|
|
8927
9428
|
]
|
|
8928
9429
|
}, [
|
|
8929
|
-
|
|
8930
|
-
|
|
8931
|
-
|
|
9430
|
+
h16("header", { class: "absolute-voice-turn-quality__header" }, [
|
|
9431
|
+
h16("span", { class: "absolute-voice-turn-quality__eyebrow" }, model.value.title),
|
|
9432
|
+
h16("strong", { class: "absolute-voice-turn-quality__label" }, model.value.label)
|
|
8932
9433
|
]),
|
|
8933
|
-
|
|
8934
|
-
model.value.turns.length ?
|
|
9434
|
+
h16("p", { class: "absolute-voice-turn-quality__description" }, model.value.description),
|
|
9435
|
+
model.value.turns.length ? h16("div", { class: "absolute-voice-turn-quality__turns" }, model.value.turns.map((turn) => h16("article", {
|
|
8935
9436
|
class: [
|
|
8936
9437
|
"absolute-voice-turn-quality__turn",
|
|
8937
9438
|
`absolute-voice-turn-quality__turn--${turn.status}`
|
|
8938
9439
|
],
|
|
8939
9440
|
key: `${turn.sessionId}:${turn.turnId}`
|
|
8940
9441
|
}, [
|
|
8941
|
-
|
|
8942
|
-
|
|
8943
|
-
|
|
9442
|
+
h16("header", [
|
|
9443
|
+
h16("strong", turn.label),
|
|
9444
|
+
h16("span", turn.status)
|
|
8944
9445
|
]),
|
|
8945
|
-
|
|
8946
|
-
|
|
8947
|
-
|
|
8948
|
-
|
|
9446
|
+
h16("p", turn.detail),
|
|
9447
|
+
h16("dl", turn.rows.map((row) => h16("div", { key: row.label }, [
|
|
9448
|
+
h16("dt", row.label),
|
|
9449
|
+
h16("dd", row.value)
|
|
8949
9450
|
])))
|
|
8950
|
-
]))) :
|
|
8951
|
-
model.value.error ?
|
|
9451
|
+
]))) : h16("p", { class: "absolute-voice-turn-quality__empty" }, "Complete a voice turn to see STT quality diagnostics."),
|
|
9452
|
+
model.value.error ? h16("p", { class: "absolute-voice-turn-quality__error" }, model.value.error) : null
|
|
8952
9453
|
]);
|
|
8953
9454
|
}
|
|
8954
9455
|
});
|
|
8955
9456
|
// src/vue/useVoiceProfileComparison.ts
|
|
8956
|
-
import { onUnmounted as
|
|
9457
|
+
import { onUnmounted as onUnmounted17, ref as ref12, shallowRef as shallowRef16 } from "vue";
|
|
8957
9458
|
|
|
8958
9459
|
// src/client/profileComparison.ts
|
|
8959
9460
|
var fetchVoiceProfileComparison = async (path = "/api/voice/real-call-profile-history", options = {}) => {
|
|
@@ -9033,10 +9534,10 @@ var createVoiceProfileComparisonStore = (path = "/api/voice/real-call-profile-hi
|
|
|
9033
9534
|
// src/vue/useVoiceProfileComparison.ts
|
|
9034
9535
|
function useVoiceProfileComparison(path = "/api/voice/real-call-profile-history", options = {}) {
|
|
9035
9536
|
const store = createVoiceProfileComparisonStore(path, options);
|
|
9036
|
-
const error =
|
|
9037
|
-
const isLoading =
|
|
9038
|
-
const report =
|
|
9039
|
-
const updatedAt =
|
|
9537
|
+
const error = ref12(null);
|
|
9538
|
+
const isLoading = ref12(false);
|
|
9539
|
+
const report = shallowRef16(undefined);
|
|
9540
|
+
const updatedAt = ref12(undefined);
|
|
9040
9541
|
const sync = () => {
|
|
9041
9542
|
const snapshot = store.getSnapshot();
|
|
9042
9543
|
error.value = snapshot.error;
|
|
@@ -9049,7 +9550,7 @@ function useVoiceProfileComparison(path = "/api/voice/real-call-profile-history"
|
|
|
9049
9550
|
if (typeof window !== "undefined") {
|
|
9050
9551
|
store.refresh().catch(() => {});
|
|
9051
9552
|
}
|
|
9052
|
-
|
|
9553
|
+
onUnmounted17(() => {
|
|
9053
9554
|
unsubscribe();
|
|
9054
9555
|
store.close();
|
|
9055
9556
|
});
|
|
@@ -9062,7 +9563,7 @@ function useVoiceProfileComparison(path = "/api/voice/real-call-profile-history"
|
|
|
9062
9563
|
};
|
|
9063
9564
|
}
|
|
9064
9565
|
// src/vue/useVoiceLiveOps.ts
|
|
9065
|
-
import { onUnmounted as
|
|
9566
|
+
import { onUnmounted as onUnmounted18, ref as ref13, shallowRef as shallowRef17 } from "vue";
|
|
9066
9567
|
|
|
9067
9568
|
// src/client/liveOps.ts
|
|
9068
9569
|
var postVoiceLiveOpsAction = async (input, options = {}) => {
|
|
@@ -9153,11 +9654,11 @@ var createVoiceLiveOpsStore = (options = {}) => {
|
|
|
9153
9654
|
// src/vue/useVoiceLiveOps.ts
|
|
9154
9655
|
function useVoiceLiveOps(options = {}) {
|
|
9155
9656
|
const store = createVoiceLiveOpsStore(options);
|
|
9156
|
-
const error =
|
|
9157
|
-
const isRunning =
|
|
9158
|
-
const lastResult =
|
|
9159
|
-
const runningAction =
|
|
9160
|
-
const updatedAt =
|
|
9657
|
+
const error = ref13(null);
|
|
9658
|
+
const isRunning = ref13(false);
|
|
9659
|
+
const lastResult = shallowRef17(undefined);
|
|
9660
|
+
const runningAction = ref13(undefined);
|
|
9661
|
+
const updatedAt = ref13(undefined);
|
|
9161
9662
|
const sync = () => {
|
|
9162
9663
|
const snapshot = store.getSnapshot();
|
|
9163
9664
|
error.value = snapshot.error;
|
|
@@ -9168,7 +9669,7 @@ function useVoiceLiveOps(options = {}) {
|
|
|
9168
9669
|
};
|
|
9169
9670
|
const unsubscribe = store.subscribe(sync);
|
|
9170
9671
|
sync();
|
|
9171
|
-
|
|
9672
|
+
onUnmounted18(() => {
|
|
9172
9673
|
unsubscribe();
|
|
9173
9674
|
store.close();
|
|
9174
9675
|
});
|
|
@@ -9182,7 +9683,7 @@ function useVoiceLiveOps(options = {}) {
|
|
|
9182
9683
|
};
|
|
9183
9684
|
}
|
|
9184
9685
|
// src/vue/useVoiceCampaignDialerProof.ts
|
|
9185
|
-
import { onUnmounted as
|
|
9686
|
+
import { onUnmounted as onUnmounted19, shallowRef as shallowRef18 } from "vue";
|
|
9186
9687
|
|
|
9187
9688
|
// src/client/campaignDialerProof.ts
|
|
9188
9689
|
var fetchVoiceCampaignDialerProofStatus = async (path = "/api/voice/campaigns/dialer-proof", options = {}) => {
|
|
@@ -9305,11 +9806,11 @@ var createVoiceCampaignDialerProofStore = (path = "/api/voice/campaigns/dialer-p
|
|
|
9305
9806
|
// src/vue/useVoiceCampaignDialerProof.ts
|
|
9306
9807
|
function useVoiceCampaignDialerProof(path = "/api/voice/campaigns/dialer-proof", options = {}) {
|
|
9307
9808
|
const store = createVoiceCampaignDialerProofStore(path, options);
|
|
9308
|
-
const error =
|
|
9309
|
-
const isLoading =
|
|
9310
|
-
const report =
|
|
9311
|
-
const status =
|
|
9312
|
-
const updatedAt =
|
|
9809
|
+
const error = shallowRef18(null);
|
|
9810
|
+
const isLoading = shallowRef18(false);
|
|
9811
|
+
const report = shallowRef18();
|
|
9812
|
+
const status = shallowRef18();
|
|
9813
|
+
const updatedAt = shallowRef18(undefined);
|
|
9313
9814
|
const sync = () => {
|
|
9314
9815
|
const snapshot = store.getSnapshot();
|
|
9315
9816
|
error.value = snapshot.error;
|
|
@@ -9323,7 +9824,7 @@ function useVoiceCampaignDialerProof(path = "/api/voice/campaigns/dialer-proof",
|
|
|
9323
9824
|
if (typeof window !== "undefined") {
|
|
9324
9825
|
store.refresh().catch(() => {});
|
|
9325
9826
|
}
|
|
9326
|
-
|
|
9827
|
+
onUnmounted19(() => {
|
|
9327
9828
|
unsubscribe();
|
|
9328
9829
|
store.close();
|
|
9329
9830
|
});
|
|
@@ -9338,7 +9839,7 @@ function useVoiceCampaignDialerProof(path = "/api/voice/campaigns/dialer-proof",
|
|
|
9338
9839
|
};
|
|
9339
9840
|
}
|
|
9340
9841
|
// src/vue/useVoiceStream.ts
|
|
9341
|
-
import { onUnmounted as
|
|
9842
|
+
import { onUnmounted as onUnmounted20, ref as ref14, shallowRef as shallowRef19 } from "vue";
|
|
9342
9843
|
|
|
9343
9844
|
// src/client/actions.ts
|
|
9344
9845
|
var normalizeErrorMessage = (value) => {
|
|
@@ -10743,17 +11244,17 @@ var createVoiceStream = (path, options = {}) => {
|
|
|
10743
11244
|
// src/vue/useVoiceStream.ts
|
|
10744
11245
|
function useVoiceStream(path, options = {}) {
|
|
10745
11246
|
const stream = createVoiceStream(path, options);
|
|
10746
|
-
const assistantAudio =
|
|
10747
|
-
const assistantTexts =
|
|
10748
|
-
const call =
|
|
10749
|
-
const error =
|
|
10750
|
-
const isConnected =
|
|
10751
|
-
const partial =
|
|
10752
|
-
const reconnect =
|
|
10753
|
-
const sessionId =
|
|
10754
|
-
const sessionMetadata =
|
|
10755
|
-
const status =
|
|
10756
|
-
const turns =
|
|
11247
|
+
const assistantAudio = shallowRef19([]);
|
|
11248
|
+
const assistantTexts = shallowRef19([]);
|
|
11249
|
+
const call = shallowRef19(null);
|
|
11250
|
+
const error = ref14(null);
|
|
11251
|
+
const isConnected = ref14(false);
|
|
11252
|
+
const partial = ref14("");
|
|
11253
|
+
const reconnect = shallowRef19(stream.reconnect);
|
|
11254
|
+
const sessionId = ref14(stream.sessionId);
|
|
11255
|
+
const sessionMetadata = shallowRef19(stream.sessionMetadata);
|
|
11256
|
+
const status = ref14(stream.status);
|
|
11257
|
+
const turns = shallowRef19([]);
|
|
10757
11258
|
const sync = () => {
|
|
10758
11259
|
assistantAudio.value = [...stream.assistantAudio];
|
|
10759
11260
|
assistantTexts.value = [...stream.assistantTexts];
|
|
@@ -10773,7 +11274,7 @@ function useVoiceStream(path, options = {}) {
|
|
|
10773
11274
|
unsubscribe();
|
|
10774
11275
|
stream.close();
|
|
10775
11276
|
};
|
|
10776
|
-
|
|
11277
|
+
onUnmounted20(destroy);
|
|
10777
11278
|
return {
|
|
10778
11279
|
assistantAudio,
|
|
10779
11280
|
assistantTexts,
|
|
@@ -10794,7 +11295,7 @@ function useVoiceStream(path, options = {}) {
|
|
|
10794
11295
|
};
|
|
10795
11296
|
}
|
|
10796
11297
|
// src/vue/useVoiceController.ts
|
|
10797
|
-
import { onUnmounted as
|
|
11298
|
+
import { onUnmounted as onUnmounted21, ref as ref15, shallowRef as shallowRef20 } from "vue";
|
|
10798
11299
|
|
|
10799
11300
|
// src/client/htmx.ts
|
|
10800
11301
|
var DEFAULT_EVENT_NAME = "voice-refresh";
|
|
@@ -11446,17 +11947,17 @@ var createVoiceController = (path, options = {}) => {
|
|
|
11446
11947
|
// src/vue/useVoiceController.ts
|
|
11447
11948
|
function useVoiceController(path, options = {}) {
|
|
11448
11949
|
const controller = createVoiceController(path, options);
|
|
11449
|
-
const assistantAudio =
|
|
11450
|
-
const assistantTexts =
|
|
11451
|
-
const error =
|
|
11452
|
-
const isConnected =
|
|
11453
|
-
const isRecording =
|
|
11454
|
-
const partial =
|
|
11455
|
-
const reconnect =
|
|
11456
|
-
const recordingError =
|
|
11457
|
-
const sessionId =
|
|
11458
|
-
const status =
|
|
11459
|
-
const turns =
|
|
11950
|
+
const assistantAudio = shallowRef20([]);
|
|
11951
|
+
const assistantTexts = shallowRef20([]);
|
|
11952
|
+
const error = ref15(null);
|
|
11953
|
+
const isConnected = ref15(false);
|
|
11954
|
+
const isRecording = ref15(false);
|
|
11955
|
+
const partial = ref15("");
|
|
11956
|
+
const reconnect = shallowRef20(controller.reconnect);
|
|
11957
|
+
const recordingError = ref15(null);
|
|
11958
|
+
const sessionId = ref15(controller.sessionId);
|
|
11959
|
+
const status = ref15(controller.status);
|
|
11960
|
+
const turns = shallowRef20([]);
|
|
11460
11961
|
const sync = () => {
|
|
11461
11962
|
assistantAudio.value = [...controller.assistantAudio];
|
|
11462
11963
|
assistantTexts.value = [...controller.assistantTexts];
|
|
@@ -11476,7 +11977,7 @@ function useVoiceController(path, options = {}) {
|
|
|
11476
11977
|
unsubscribe();
|
|
11477
11978
|
controller.close();
|
|
11478
11979
|
};
|
|
11479
|
-
|
|
11980
|
+
onUnmounted21(destroy);
|
|
11480
11981
|
return {
|
|
11481
11982
|
assistantAudio,
|
|
11482
11983
|
assistantTexts,
|
|
@@ -11500,13 +12001,13 @@ function useVoiceController(path, options = {}) {
|
|
|
11500
12001
|
};
|
|
11501
12002
|
}
|
|
11502
12003
|
// src/vue/useVoiceTraceTimeline.ts
|
|
11503
|
-
import { onUnmounted as
|
|
12004
|
+
import { onUnmounted as onUnmounted22, ref as ref16, shallowRef as shallowRef21 } from "vue";
|
|
11504
12005
|
function useVoiceTraceTimeline(path = "/api/voice-traces", options = {}) {
|
|
11505
12006
|
const store = createVoiceTraceTimelineStore(path, options);
|
|
11506
|
-
const error =
|
|
11507
|
-
const isLoading =
|
|
11508
|
-
const report =
|
|
11509
|
-
const updatedAt =
|
|
12007
|
+
const error = ref16(null);
|
|
12008
|
+
const isLoading = ref16(false);
|
|
12009
|
+
const report = shallowRef21(null);
|
|
12010
|
+
const updatedAt = ref16(undefined);
|
|
11510
12011
|
const sync = () => {
|
|
11511
12012
|
const snapshot = store.getSnapshot();
|
|
11512
12013
|
error.value = snapshot.error;
|
|
@@ -11517,7 +12018,7 @@ function useVoiceTraceTimeline(path = "/api/voice-traces", options = {}) {
|
|
|
11517
12018
|
const unsubscribe = store.subscribe(sync);
|
|
11518
12019
|
sync();
|
|
11519
12020
|
store.refresh().catch(() => {});
|
|
11520
|
-
|
|
12021
|
+
onUnmounted22(() => {
|
|
11521
12022
|
unsubscribe();
|
|
11522
12023
|
store.close();
|
|
11523
12024
|
});
|
|
@@ -11530,7 +12031,7 @@ function useVoiceTraceTimeline(path = "/api/voice-traces", options = {}) {
|
|
|
11530
12031
|
};
|
|
11531
12032
|
}
|
|
11532
12033
|
// src/vue/useVoiceWorkflowStatus.ts
|
|
11533
|
-
import { onUnmounted as
|
|
12034
|
+
import { onUnmounted as onUnmounted23, ref as ref17, shallowRef as shallowRef22 } from "vue";
|
|
11534
12035
|
|
|
11535
12036
|
// src/client/workflowStatus.ts
|
|
11536
12037
|
var fetchVoiceWorkflowStatus = async (path = "/evals/scenarios/json", options = {}) => {
|
|
@@ -11614,10 +12115,10 @@ var createVoiceWorkflowStatusStore = (path = "/evals/scenarios/json", options =
|
|
|
11614
12115
|
// src/vue/useVoiceWorkflowStatus.ts
|
|
11615
12116
|
function useVoiceWorkflowStatus(path = "/evals/scenarios/json", options = {}) {
|
|
11616
12117
|
const store = createVoiceWorkflowStatusStore(path, options);
|
|
11617
|
-
const error =
|
|
11618
|
-
const isLoading =
|
|
11619
|
-
const report =
|
|
11620
|
-
const updatedAt =
|
|
12118
|
+
const error = ref17(null);
|
|
12119
|
+
const isLoading = ref17(false);
|
|
12120
|
+
const report = shallowRef22(undefined);
|
|
12121
|
+
const updatedAt = ref17(undefined);
|
|
11621
12122
|
const sync = () => {
|
|
11622
12123
|
const snapshot = store.getSnapshot();
|
|
11623
12124
|
error.value = snapshot.error;
|
|
@@ -11630,7 +12131,7 @@ function useVoiceWorkflowStatus(path = "/evals/scenarios/json", options = {}) {
|
|
|
11630
12131
|
if (typeof window !== "undefined") {
|
|
11631
12132
|
store.refresh().catch(() => {});
|
|
11632
12133
|
}
|
|
11633
|
-
|
|
12134
|
+
onUnmounted23(() => {
|
|
11634
12135
|
unsubscribe();
|
|
11635
12136
|
store.close();
|
|
11636
12137
|
});
|
|
@@ -11650,6 +12151,7 @@ export {
|
|
|
11650
12151
|
useVoiceStream,
|
|
11651
12152
|
useVoiceSessionSnapshot,
|
|
11652
12153
|
useVoiceRoutingStatus,
|
|
12154
|
+
useVoiceReconnectProfileEvidence,
|
|
11653
12155
|
useVoiceReadinessFailures,
|
|
11654
12156
|
useVoiceProviderStatus,
|
|
11655
12157
|
useVoiceProviderSimulationControls,
|
|
@@ -11670,6 +12172,7 @@ export {
|
|
|
11670
12172
|
VoiceTurnLatency,
|
|
11671
12173
|
VoiceSessionSnapshot,
|
|
11672
12174
|
VoiceRoutingStatus,
|
|
12175
|
+
VoiceReconnectProfileEvidence,
|
|
11673
12176
|
VoiceReadinessFailures,
|
|
11674
12177
|
VoiceProviderStatus,
|
|
11675
12178
|
VoiceProviderSimulationControls,
|