mirror of
https://github.com/stablyai/orca.git
synced 2026-10-23 16:03:49 +00:00
fix(terminal): bound bold glitch diagnostics
This commit is contained in:
File diff suppressed because one or more lines are too long
@@ -17,11 +17,11 @@ describe('Electron runtime package contract', () => {
|
||||
'utf8'
|
||||
)
|
||||
|
||||
expect(patch).toContain('diff --git a/src/Types.ts b/src/Types.ts')
|
||||
expect(patch).toContain('readonly clearModelGeneration: number')
|
||||
expect(patch).toContain('const generation = this._atlas.clearModelGeneration')
|
||||
expect(patch).toContain('this.clearModelGeneration++')
|
||||
expect(patch).toContain('this._atlas._clearModelGeneration||0')
|
||||
expect(patch.match(/\^\(\?:\[1-8\]\\d\{2\}\|900\)\$/g)).toHaveLength(3)
|
||||
})
|
||||
|
||||
it('keeps root postinstall as the single Electron binary install owner', () => {
|
||||
|
||||
Generated
+3
-3
@@ -18,7 +18,7 @@ patchedDependencies:
|
||||
hash: af3b156143ed2ee9903b753145b63dd4a2ee72cadd7ef333ab0f4d5d3ebfc32c
|
||||
path: config/patches/@xterm__addon-serialize@0.15.0-beta.287.patch
|
||||
'@xterm/addon-webgl@0.20.0-beta.286':
|
||||
hash: cad3f24983886675ce45b67bc169545b9a2f3f9e05f3b0ffac0911d974ca6c54
|
||||
hash: 335427c05eef212851ba4e2fc19623c65af82898c5243c6b7f308c97b1d6a174
|
||||
path: config/patches/@xterm__addon-webgl@0.20.0-beta.286.patch
|
||||
'@xterm/xterm@6.1.0-beta.287':
|
||||
hash: 46796c152f3b73e28238f44499eaf5a867a863809bc7b470b159526a41e354f7
|
||||
@@ -229,7 +229,7 @@ importers:
|
||||
version: 0.13.0-beta.287(@xterm/xterm@6.1.0-beta.287(patch_hash=46796c152f3b73e28238f44499eaf5a867a863809bc7b470b159526a41e354f7))
|
||||
'@xterm/addon-webgl':
|
||||
specifier: 0.20.0-beta.286
|
||||
version: 0.20.0-beta.286(patch_hash=cad3f24983886675ce45b67bc169545b9a2f3f9e05f3b0ffac0911d974ca6c54)(@xterm/xterm@6.1.0-beta.287(patch_hash=46796c152f3b73e28238f44499eaf5a867a863809bc7b470b159526a41e354f7))
|
||||
version: 0.20.0-beta.286(patch_hash=335427c05eef212851ba4e2fc19623c65af82898c5243c6b7f308c97b1d6a174)(@xterm/xterm@6.1.0-beta.287(patch_hash=46796c152f3b73e28238f44499eaf5a867a863809bc7b470b159526a41e354f7))
|
||||
'@xterm/xterm':
|
||||
specifier: 6.1.0-beta.287
|
||||
version: 6.1.0-beta.287(patch_hash=46796c152f3b73e28238f44499eaf5a867a863809bc7b470b159526a41e354f7)
|
||||
@@ -9638,7 +9638,7 @@ snapshots:
|
||||
dependencies:
|
||||
'@xterm/xterm': 6.1.0-beta.287(patch_hash=46796c152f3b73e28238f44499eaf5a867a863809bc7b470b159526a41e354f7)
|
||||
|
||||
'@xterm/addon-webgl@0.20.0-beta.286(patch_hash=cad3f24983886675ce45b67bc169545b9a2f3f9e05f3b0ffac0911d974ca6c54)(@xterm/xterm@6.1.0-beta.287(patch_hash=46796c152f3b73e28238f44499eaf5a867a863809bc7b470b159526a41e354f7))':
|
||||
'@xterm/addon-webgl@0.20.0-beta.286(patch_hash=335427c05eef212851ba4e2fc19623c65af82898c5243c6b7f308c97b1d6a174)(@xterm/xterm@6.1.0-beta.287(patch_hash=46796c152f3b73e28238f44499eaf5a867a863809bc7b470b159526a41e354f7))':
|
||||
dependencies:
|
||||
'@xterm/xterm': 6.1.0-beta.287(patch_hash=46796c152f3b73e28238f44499eaf5a867a863809bc7b470b159526a41e354f7)
|
||||
|
||||
|
||||
@@ -15,6 +15,10 @@ import {
|
||||
import { maybeStartTerminalRenderDesyncSentinel } from './terminal-render-desync-trigger'
|
||||
|
||||
const rendererDeliveryBreadcrumbs = createPtyDeliveryBreadcrumbRing()
|
||||
const ATLAS_FONT_PROBE_MISMATCH = 'atlas-font-probe-mismatch'
|
||||
const ATLAS_CRASH_MIRROR_INTERVAL_MS = 30_000
|
||||
let lastAtlasCrashMirrorAt = Number.NEGATIVE_INFINITY
|
||||
let suppressedAtlasCrashMirrors = 0
|
||||
|
||||
export function recordTerminalFreezeBreadcrumb(
|
||||
kind: string,
|
||||
@@ -35,9 +39,26 @@ export function recordTerminalFreezeBreadcrumb(
|
||||
// instrumentation, not absence of the event.
|
||||
setTerminalWebglDiagnosticRecorder((kind, detail) => {
|
||||
rendererDeliveryBreadcrumbs.record(kind, detail)
|
||||
if (kind === ATLAS_FONT_PROBE_MISMATCH) {
|
||||
const now = Date.now()
|
||||
if (now - lastAtlasCrashMirrorAt < ATLAS_CRASH_MIRROR_INTERVAL_MS) {
|
||||
suppressedAtlasCrashMirrors++
|
||||
return
|
||||
}
|
||||
lastAtlasCrashMirrorAt = now
|
||||
}
|
||||
// `kind` last: it is the coalescing discriminator, so a detail field of the
|
||||
// same name must not be able to shadow it.
|
||||
recordRendererCrashBreadcrumb(TERMINAL_WEBGL_DIAGNOSTIC_BREADCRUMB, { ...detail, kind })
|
||||
recordRendererCrashBreadcrumb(TERMINAL_WEBGL_DIAGNOSTIC_BREADCRUMB, {
|
||||
...detail,
|
||||
...(kind === ATLAS_FONT_PROBE_MISMATCH && suppressedAtlasCrashMirrors > 0
|
||||
? { rendererSuppressedSinceLast: suppressedAtlasCrashMirrors }
|
||||
: {}),
|
||||
kind
|
||||
})
|
||||
if (kind === ATLAS_FONT_PROBE_MISMATCH) {
|
||||
suppressedAtlasCrashMirrors = 0
|
||||
}
|
||||
})
|
||||
|
||||
// Why: the sentinel is a field-diagnostic that must be armable on production
|
||||
@@ -53,7 +74,7 @@ type AtlasFontProbeMismatch = { desired?: string; actual?: string }
|
||||
;(globalThis as { __orcaAtlasFontProbe?: (mismatch: AtlasFontProbeMismatch) => void })[
|
||||
'__orcaAtlasFontProbe'
|
||||
] = (mismatch) => {
|
||||
recordTerminalWebglDiagnostic('atlas-font-probe-mismatch', {
|
||||
recordTerminalWebglDiagnostic(ATLAS_FONT_PROBE_MISMATCH, {
|
||||
desired: mismatch?.desired ?? null,
|
||||
actual: mismatch?.actual ?? null
|
||||
})
|
||||
@@ -65,4 +86,6 @@ export function getTerminalFreezeBreadcrumbs(): PtyDeliveryBreadcrumb[] {
|
||||
|
||||
export function resetTerminalFreezeBreadcrumbsForTesting(): void {
|
||||
rendererDeliveryBreadcrumbs.reset()
|
||||
lastAtlasCrashMirrorAt = Number.NEGATIVE_INFINITY
|
||||
suppressedAtlasCrashMirrors = 0
|
||||
}
|
||||
|
||||
@@ -186,6 +186,20 @@ describe('terminal-render-desync-sentinel', () => {
|
||||
expect(getRenderDesyncEvidence()).toHaveLength(4)
|
||||
})
|
||||
|
||||
it('does not spend the capture budget on failed persistence attempts', async () => {
|
||||
writeTerminalRenderDesyncEvidence.mockRejectedValue(new Error('disk unavailable'))
|
||||
|
||||
for (let pane = 1; pane <= 5; pane++) {
|
||||
sampleWith(divergenceOf(manyCells(0)), false, `m1:p${pane}`)
|
||||
sampleWith(divergenceOf(manyCells(0)), false, `m1:p${pane}`)
|
||||
await vi.waitFor(() => expect(writeTerminalRenderDesyncEvidence).toHaveBeenCalledTimes(pane))
|
||||
await vi.waitFor(() => expect(getRenderDesyncEvidence()).toHaveLength(0))
|
||||
}
|
||||
|
||||
expect(getRenderDesyncEvidence()).toHaveLength(0)
|
||||
expect(resetAndRefreshAllTerminalWebglAtlases).not.toHaveBeenCalled()
|
||||
})
|
||||
|
||||
it('resets tracking for paused panes instead of sampling them', () => {
|
||||
const cells = manyCells(0)
|
||||
sampleWith(divergenceOf(cells))
|
||||
|
||||
@@ -233,6 +233,10 @@ async function persistEntry(
|
||||
if (directory == null) {
|
||||
// Why: a failed write must leave the bad pixels intact; recovering here
|
||||
// would destroy the only evidence without producing a durable capture.
|
||||
const entryIndex = evidence.indexOf(entry)
|
||||
if (entryIndex !== -1) {
|
||||
evidence.splice(entryIndex, 1)
|
||||
}
|
||||
pendingPaneKeys.delete(entry.paneKey)
|
||||
return
|
||||
}
|
||||
|
||||
+29
@@ -53,4 +53,33 @@ describe('WebGL diagnostics → freeze breadcrumb ring', () => {
|
||||
kind: 'webgl-context-restore'
|
||||
})
|
||||
})
|
||||
|
||||
it('bounds atlas mismatch storm IPC while retaining the local occurrence count', () => {
|
||||
vi.useFakeTimers()
|
||||
try {
|
||||
for (let mismatch = 0; mismatch < 10_000; mismatch++) {
|
||||
recordTerminalWebglDiagnostic('atlas-font-probe-mismatch', {
|
||||
desired: '550',
|
||||
actual: '700 14px Menlo'
|
||||
})
|
||||
}
|
||||
|
||||
expect(recordRendererCrashBreadcrumb).toHaveBeenCalledTimes(1)
|
||||
expect(getTerminalFreezeBreadcrumbs()).toEqual([
|
||||
expect.objectContaining({ kind: 'atlas-font-probe-mismatch', repeats: 10_000 })
|
||||
])
|
||||
|
||||
vi.advanceTimersByTime(30_000)
|
||||
recordTerminalWebglDiagnostic('atlas-font-probe-mismatch', {
|
||||
desired: '550',
|
||||
actual: '700 14px Menlo'
|
||||
})
|
||||
expect(recordRendererCrashBreadcrumb).toHaveBeenLastCalledWith(
|
||||
'terminal_webgl_diagnostic',
|
||||
expect.objectContaining({ rendererSuppressedSinceLast: 9_999 })
|
||||
)
|
||||
} finally {
|
||||
vi.useRealTimers()
|
||||
}
|
||||
})
|
||||
})
|
||||
|
||||
Reference in New Issue
Block a user