Status
PASS
882 executed tests
Passed
882
100.0% pass rate
Failed
0
 
Duration
7.4s
1.5s vitest + 5.9s android
TS Line Coverage
28.6%
3,700/12,939 TypeScript lines
Total Tests
882
Pass Rate
100.0%
Line Coverage
28.6%

Vitest

PASS
Pass 793 Fail 0 29 files Coverage + JSON report

Android

PASS
Pass 82 Fail 0 4 files JUnit + Robolectric on ubuntu

Apple (XCTest)

NOT RUN
Not executed in Pages workflow (requires macOS runner)

Robot Framework

PASS
Pass 7Fail 0Skip 0
Terminal Output Parsing PASS
Claude Code와 Codex CLI의 터미널 출력을 정확히 해석하는가?
236 passed 0 failed 3 files 319ms
output-parser.test.ts
197 / 197 259ms
OutputParser 197 / 197
basic option parsing › parses clean numbered options with newlines
16.079480999999987ms
basic option parsing › detects (recommended) marker
4.119742999999971ms
basic option parsing › detects ✔ selected marker
1.537083999999993ms
basic option parsing › handles both recommended and selected on different options
1.4363160000000335ms
basic option parsing › parses full Claude model selector with labels and middle dot
1.8601660000000493ms
ANSI-stripped options › parses concatenated text with · delimiter
1.1656920000000355ms
ANSI-stripped options › extracts version numbers from · delimited labels
0.6652700000000777ms
chunked input debounce › does NOT emit immediately on first chunk
0.6587680000000091ms
chunked input debounce › batches multiple chunks into single emission
1.418894000000023ms
chunked input debounce › resets debounce timer when new chunk with options arrives
1.4292130000000043ms
chunked input debounce › simulates real /model flow: split across chunks
1.3741099999999733ms
model ID date rejection › does NOT parse 20251001 from model ID as option number
1.1550529999999526ms
model ID date rejection › rejects large numbers that look like dates
1.0718980000000329ms
version number rejection › does NOT parse version "4.6" followed by digit as option
1.3606959999999617ms
version number rejection › does NOT parse "6)" from "4.6)" as option 6
1.9575069999999641ms
stale buffer overwrite › newer options overwrite older ones with same index
1.4319880000000467ms
permission prompts › detects Yes/No/Always pattern
2.1683309999999665ms
permission prompts › detects (Y)es/(N)o pattern
1.400961000000052ms
permission prompts › emits immediately with no debounce
0.840596000000005ms
permission prompts › sets yes_no_always prompt type
0.750046999999995ms
permission prompts › sets yes_no prompt type
0.7553980000000138ms
permission prompts › suppresses false idle from user prompt echo after permission (interactive cooldown)
1.2658989999999903ms
permission prompts › allows real idle after interactive cooldown expires
0.8219920000000229ms
diff prompts › detects (V)iew/(A)pply/(D)eny pattern
4.7885219999999435ms
diff prompts › detects lowercase (a)pply/(d)eny/(v)iew pattern
1.5278470000000652ms
diff prompts › emits immediately with no debounce
0.7919550000000299ms
diff prompts › suppresses false idle from user prompt echo after diff (interactive cooldown)
1.0694729999999026ms
various option counts › handles 1 option
0.7752150000000029ms
various option counts › handles 2 options
0.7379449999999679ms
various option counts › handles 5+ options
0.8275820000000067ms
various option counts › handles bullet-style options
0.9460619999999835ms
option updates › emits new options when data changes after first emission
1.2306430000001ms
spinner cancels option timer › spinner cancels pending option debounce
0.8693200000000161ms
idle vs option debounce › idle prompt is ignored when option debounce is pending
0.9473550000000159ms
idle vs option debounce › idle prompt fires normally when no option debounce is pending
0.6254159999999729ms
interactive prompt during spinner › stops spinner when permission prompt arrives
1.355015000000094ms
interactive prompt during spinner › stops spinner when diff prompt arrives
0.9426869999999781ms
interactive prompt during spinner › stops spinner when option prompt arrives
0.9564120000000003ms
interactive prompt during spinner › stops spinner when idle prompt arrives in small chunk
1.0967540000000326ms
interactive prompt during spinner › ignores idle prompt in large chunk during spinner (screen redraw)
0.7193500000000768ms
cleanOptionLabel (via parseOptions) › deduplicates exact CamelCase matches
0.9379079999999931ms
cleanOptionLabel (via parseOptions) › preserves labels without · delimiter
0.5795399999999518ms
cleanOptionLabel (via parseOptions) › removes (recommended) from label text
1.0052630000000136ms
cleanOptionLabel (via parseOptions) › removes ✔ from label text
0.7130890000000818ms
cleanOptionLabel (via parseOptions) › extracts version from identity before middle dot
0.6310959999999568ms
metadata events › emits project_name from startup banner
0.5856009999999969ms
metadata events › emits project_name only once (caches)
0.5882569999999987ms
metadata events › parses absolute path for project_name
0.6025529999999435ms
metadata events › emits model_info with model and plan
0.6522449999999935ms
metadata events › emits model_info without plan
0.7001450000000204ms
metadata events › emits model_info only once for same model (caches)
0.6215479999999616ms
metadata events › re-emits model_info when model changes
0.6177309999999352ms
metadata events › parses ANSI-stripped model_info
0.6057579999999234ms
metadata events › detects API billing plan
0.7427940000000035ms
metadata events › emits status_line with duration and tokens
0.7594550000000027ms
metadata events › parses zero-minute status line
0.7003949999999577ms
metadata events › emits tool_action from ⏺ pattern
0.5360089999999218ms
metadata events › extracts various tool names
0.5690499999999474ms
user prompt › emits user_prompt after first idle has been seen
0.685758000000078ms
user prompt › does NOT emit user_prompt before first idle
0.53268300000002ms
user prompt › filters out mode banner text
0.6689269999999397ms
user prompt › filters out numbered option lines
0.6914689999999837ms
user prompt › filters out keyboard hint text
0.6970589999999675ms
user prompt › filters out "esc to interrupt" text
0.6474459999999453ms
user prompt › filters out autocomplete suggestions
1.8011960000000045ms
user prompt › filters out box-drawing decorative lines
0.6677139999999326ms
usage info › parses usage percentage
0.8065730000000713ms
usage info › parses usage cost
1.7173309999999447ms
usage info › parses session percentage with hour limit
0.5839580000000524ms
usage info › parses reset time with timezone
0.6360949999999548ms
usage info › parses time remaining
0.6104870000000346ms
spinner lifecycle › emits spinner_start on spinner char (after idle seen)
0.6464240000000245ms
spinner lifecycle › does NOT emit spinner_start before first idle
0.5319109999999228ms
spinner lifecycle › emits spinner_stop after debounce (2000ms)
0.926977000000079ms
spinner lifecycle › does NOT emit duplicate spinner_start on repeated chars
0.6653999999999769ms
spinner lifecycle › resets spinner debounce timer on repeated chars
2.765282999999954ms
spinner lifecycle › ignores spinner chars in large text blocks (>80 non-ws)
0.7161040000000867ms
spinner lifecycle › recognizes all spinner characters
1.660474000000022ms
idle detection › emits idle after IDLE_DEBOUNCE_MS (300ms)
0.7311819999999898ms
idle detection › sets seenFirstIdle on first idle prompt
0.7913849999999911ms
idle detection › cancels idle timer when spinner starts
0.9146240000000034ms
idle detection › recognizes > as idle prompt char
0.7477539999999863ms
mode detection › detects plan mode
0.7132690000000821ms
mode detection › detects accept edits mode
0.6513830000000098ms
mode detection › detects default mode after Shift+Tab
0.7864960000000565ms
mode detection › detects default mode via idle prompt after Shift+Tab
0.8838670000000093ms
mode detection › emits default mode on Shift+Tab timeout (2s)
0.7654370000000199ms
mode detection › detects ANSI-stripped plan mode text
0.7038609999999608ms
mode detection › detects ANSI-stripped accept edits text
0.6452219999999897ms
mode detection › clears pending mode switch when mode banner is detected
0.7741630000000441ms
reset › clears cached project name and model name
0.8819440000000895ms
reset › disables spinner detection (clears seenFirstIdle)
0.5995369999999411ms
reset › allows re-detection after new idle prompt post-reset
0.7269049999999879ms
reset › allows re-detection of project name after reset
0.5742099999999937ms
reset › allows re-detection of model info after reset
0.6096850000000131ms
buffer management › truncates buffer when exceeding 8192 chars
1.3941580000000613ms
buffer management › keeps the last 4096 chars after truncation
1.302878000000078ms
option navigation › cursor movement during option selection does NOT trigger idle
1.1126429999999345ms
option navigation › cursor movement does NOT trigger user_prompt
0.8993859999999358ms
option navigation › normal cursor movement between options emits no idle or user_prompt
0.9703480000000582ms
option navigation › real idle prompt still works after option navigation
1.0356089999999085ms
option navigation › effort/hint text during navigation does not trigger events
1.0379140000000007ms
option navigation › IDLE_PROMPT requires space/tab/NBSP after ❯ (not newline)
0.7642539999999372ms
option navigation › USER_PROMPT requires space/tab after ❯ (not newline)
0.9704079999999067ms
permission reclassification › reclassifies numbered Yes/No options as permission_prompt
3.2823459999999614ms
permission reclassification › does NOT reclassify regular options as permission
0.849503000000027ms
permission reclassification › does NOT reclassify cursor-selection UI with "Enter to confirm" as permission
0.8925530000000208ms
permission reclassification › detects cursor-selection UI even when ANSI stripping removes spaces
0.9086329999998952ms
permission reclassification › includes navigable and cursorIndex in reclassified permission_prompt
0.7860150000000203ms
permission reclassification › infers shortcuts for reclassified permission options
1.131338000000028ms
permission reclassification › infers shortcut "a" for "don't ask again" labels
0.9418150000000196ms
permission reclassification › infers shortcut "a" for "allow all sessions" labels
0.8864320000000134ms
ghost text suggestion › detects SGR 90 (bright black) ghost text on prompt line
2.1696530000000394ms
ghost text suggestion › detects ghost text via Strategy 1 (Try "..." in clean text)
0.7684520000000248ms
ghost text suggestion › unwraps Try "..." wrapper with smart quotes
1.0741009999999278ms
ghost text suggestion › unwraps Try "..." wrapper with straight quotes
1.5319539999999279ms
ghost text suggestion › detects ghost text on first idle (❯ and suggestion in same chunk)
1.4054889999999887ms
ghost text suggestion › clears suggestion on spinner start
1.7107170000000451ms
ghost text suggestion › debounces rapid updates
1.679679999999962ms
ghost text suggestion › ignores dim (SGR 2) text without ❯ prompt context
0.7567000000000235ms
ghost text suggestion › detects dim (SGR 2) ghost text on ❯ prompt line
0.7779490000000351ms
ghost text suggestion › detects ghost text with cursor-forward spacing (Strategy 1)
0.7999700000000303ms
ghost text suggestion › filters UI chrome fragments
1.4365869999999177ms
ghost text suggestion › filters box-drawing lines as UI chrome
0.9414350000000695ms
ghost text suggestion › filters file paths (false positive from screen redraws)
1.038644999999974ms
ghost text suggestion › detects 256-color gray ghost text
0.8388629999999466ms
ghost text suggestion › handles multi-segment ghost text on prompt line
4.1352549999999155ms
ghost text suggestion › ignores ghost text on non-prompt lines
0.6769910000000436ms
ghost text suggestion › detects 24-bit RGB gray ghost text
0.821790999999962ms
ghost text suggestion › ignores 24-bit RGB non-gray colors (e.g. blue prompt char)
12.810018999999897ms
ghost text suggestion › filters out short gray text like prompt char itself
0.8944270000000643ms
ghost text suggestion › suppresses ghost text detection during spinner (processing)
0.7432149999999638ms
ghost text suggestion › rejects digit+operator fragments like diff markers "96 +"
0.6811089999999922ms
ghost text UI chrome filtering › filters out "Tip:" segments on prompt line
9.102484000000004ms
ghost text UI chrome filtering › filters out "(ctrl+...)" shortcut hints on prompt line
0.7202419999999847ms
ghost text UI chrome filtering › filters concatenated UI chrome even in scheduleSuggestion
0.6623539999999366ms
ghost text UI chrome filtering › keeps ghost text when UI chrome is also present on the line
3.840045000000032ms
filters out extended thinking indicators › rejects "(thought for 1s)" as ghost text via isUiChrome
0.6644380000000183ms
filters out extended thinking indicators › rejects "(thought for 1s)>" via scheduleSuggestion
0.7774080000000367ms
filters out extended thinking indicators › rejects longer thinking durations like "(thought for 15s)"
2.186824999999999ms
filters out extended thinking indicators › rejects "(thought for 1m 30s)" multipart duration
0.6754779999999982ms
filters out extended thinking indicators › rejects "✻ Cooked for 1m 26s" sparkle indicator
0.6866899999999987ms
filters out extended thinking indicators › rejects "✻ Cooked for 5s" short duration variant
0.5795000000000528ms
filters out extended thinking indicators › rejects "Cooked for 10s" without sparkle (cross-chunk)
0.7802540000000135ms
parenthesized placeholder filtering › rejects "(no content)" via SGR 2 (dim)
0.6621739999999363ms
parenthesized placeholder filtering › rejects "(no content)" via SGR 90 (bright black)
0.601921999999945ms
parenthesized placeholder filtering › rejects "(loading...)"
0.6007090000000517ms
parenthesized placeholder filtering › rejects "(empty)"
0.596390999999926ms
parenthesized placeholder filtering › rejects "(waiting for response)"
1.1643200000000888ms
parenthesized placeholder filtering › allows "fix the broken (auth) module" — parens in middle
0.7738120000000208ms
parenthesized placeholder filtering › allows "(optional) refactor the code" — paren prefix with text after
0.77394199999992ms
stacked ANSI + cross-chunk ghost text › detects ghost text with stacked ANSI escapes (gray + italic)
0.7932580000000371ms
stacked ANSI + cross-chunk ghost text › detects ghost text with combined SGR params (2;90 = dim+bright-black)
0.7708860000000186ms
stacked ANSI + cross-chunk ghost text › detects cross-chunk ghost text (❯ and gray text in separate feeds)
1.2265859999999975ms
stacked ANSI + cross-chunk ghost text › does NOT cross-chunk detect when chunk contains ⎿ output fence
0.7397490000000744ms
stacked ANSI + cross-chunk ghost text › does NOT cross-chunk detect when new chunk has \n (different line)
0.7584429999999429ms
ghost option from stale buffer › excludes stale numbered list items before actual option prompt
1.3707240000001093ms
ghost option from stale buffer › bypasses chunk size guard when ❯ cursor is present in large chunk
1.0390260000000353ms
ghost option from stale buffer › still works with scrambled TUI order after backward scan
0.8673860000000104ms
ghost option from stale buffer › excludes file path fragments from Read() tool in permission prompt
1.1179730000000063ms
option index ordering › returns options sorted by index even when TUI lines arrive out of order
1.0846609999999828ms
split ANSI sequence buffering › handles ANSI SGR codes split across chunks
4.195137000000045ms
split ANSI sequence buffering › handles bare ESC at end of chunk
4.106131000000005ms
split ANSI sequence buffering › does not buffer complete ANSI sequences
0.8173520000000281ms
large chunk guard for option detection › does NOT detect numbered items in large response chunks as options
3.8787869999999884ms
large chunk guard for option detection › still detects real options in small TUI chunks
0.9118690000000242ms
CUP-positioned options › parses options using CUP (\x1b[row;colH) instead of newlines
1.1564949999999499ms
CUP-positioned options › parses options using CUD (\x1b[B) for vertical movement
1.8864650000000438ms
trailing TUI chrome stripping › strips "Esc to cancel" from last option label
1.086445000000026ms
trailing TUI chrome stripping › strips "Enter to confirm" from last option label
0.8779560000000401ms
trailing TUI chrome stripping › does NOT strip "Esc" when it appears within legitimate label text
0.6933719999999539ms
CJK suggestion detection › accepts ghost text containing CJK characters
2.2253560000000334ms
CJK suggestion detection › accepts ghost text that is purely CJK (no ASCII words)
1.1709020000000692ms
AskUserQuestion with separators and descriptions › handles AskUserQuestion with separator and descriptions
1.0903509999999415ms
AskUserQuestion with separators and descriptions › handles options starting from non-zero index (buffer truncation)
1.0189090000000078ms
permission scroll does not trigger idle (Bug 1) › scroll chunk with ❯ option text does NOT cause idle when navigable
1.0992680000000519ms
permission scroll does not trigger idle (Bug 1) › /model combined chunk: confirmation + idle prompt clears options
1.602386000000024ms
permission scroll does not trigger idle (Bug 1) › /model separate chunks: ANSI reposition timer does not block idle
1.081865999999991ms
permission scroll does not trigger idle (Bug 1) › cursor move chunk with option text does NOT falsely trigger idle
1.0545150000000376ms
permission scroll does not trigger idle (Bug 1) › genuine idle prompt exits navigable state and emits idle
1.0050730000000385ms
TUI cursor-overwrite label correction (Bug 2) › fixes contaminated permission option label using correction line
1.522846999999956ms
TUI cursor-overwrite label correction (Bug 2) › leaves labels unchanged when no correction line is present
0.9401619999999866ms
genuine idle detection (semantic) › "❯ \n" is genuine idle — only prompt character, no label text
0.8267309999999952ms
genuine idle detection (semantic) › "❯ Beta" is NOT idle — has label text after prompt char
0.8497830000000022ms
genuine idle detection (semantic) › "❯ A" is NOT idle — single-char label still counts
1.230953999999997ms
genuine idle detection (semantic) › ">" also treated as idle prompt character
0.673385000000053ms
effort level parsing › detects "High effort" selection pattern
0.665520000000015ms
effort level parsing › detects "Medium effort" selection pattern
0.6502419999999347ms
effort level parsing › detects "Low effort" selection pattern
0.5983839999998963ms
effort level parsing › detects "with high effort" confirmation line
0.6384400000000596ms
effort level parsing › detects effort in model info line
0.625585000000001ms
effort level parsing › caches effort level — no re-emit on same value
0.5399760000000242ms
effort level parsing › emits on effort level change
0.9108580000000757ms
effort level parsing › resets effort level on reset()
4.206258000000048ms
effort level parsing › does not match "effort" in unrelated context
0.6182410000000118ms
effort level parsing › does not match effort inside numbered option lines
0.7727290000000266ms
effort level parsing › getter returns current effort level
0.49797799999998915ms
codex-output-parser.test.ts
24 / 24 32ms
CodexOutputParser 24 / 24
idle detection › emits idle on ❯ prompt
6.882593999999983ms
idle detection › emits idle on > prompt
1.119987000000009ms
idle detection › debounces rapid idle signals
0.6259859999999833ms
spinner detection › emits spinner_start on braille spinner chars after first idle
1.2717800000000068ms
spinner detection › does not emit spinner_start before first idle
0.6944540000000075ms
spinner detection › emits spinner_stop + idle on timeout
0.6461030000000108ms
spinner detection › emits spinner_stop when idle prompt appears
0.5057529999999986ms
spinner detection › detects "Thinking" text as processing
0.4821579999999983ms
permission prompt detection › emits permission_prompt on Allow/Deny pattern
1.8765259999999842ms
permission prompt detection › emits permission_prompt on y/n pattern
1.0679489999999987ms
permission prompt detection › stops spinner when approval detected
0.7625409999999988ms
permission prompt detection › extracts Allow once / Always allow options
0.9250739999999951ms
tool action detection › detects Running: command pattern
4.016524000000004ms
tool action detection › detects file operation patterns
0.8753199999999879ms
tool action detection › detects Editing file pattern
2.7072989999999777ms
model info detection › detects gpt model name
0.8705420000000004ms
model info detection › detects o-series model
0.6879319999999893ms
model info detection › does not re-emit same model
0.5687999999999818ms
project name detection › detects working directory
0.999762000000004ms
project name detection › detects project from path
0.6552910000000054ms
project name detection › only detects project name once
0.6289629999999988ms
buffer management › truncates buffer at 8192 chars
0.6531969999999774ms
buffer management › handles incomplete ANSI sequences
0.5763039999999933ms
getProjectName › returns null when no project detected
0.5295869999999923ms
cursor-sync.test.ts
15 / 15 28ms
Cursor Synchronization 15 / 15
terminal keyboard cursor tracking › emits cursor_update when full option redraw arrives with ❯ at new position
14.792743999999999ms
terminal keyboard cursor tracking › triggers buffer re-parse on small non-❯ chunk during navigable state
2.0012979999999914ms
terminal keyboard cursor tracking › does not emit cursor_update when cursor position unchanged
0.8472989999999925ms
genuine idle distinction › treats "❯ \n" as genuine idle (clears navigable state)
0.8432809999999904ms
genuine idle distinction › does NOT treat "❯ Beta" as idle (cursor on option label)
1.0197610000000168ms
genuine idle distinction › does NOT treat "❯ Allow once" as idle (permission cursor move)
1.2790030000000172ms
cursor authority in StateMachine › accepts optimistic update immediately
1.3402479999999741ms
cursor authority in StateMachine › suppresses stale PTY value within 200ms of optimistic update
0.4939099999999996ms
cursor authority in StateMachine › accepts PTY value after 200ms grace period
0.44769399999998427ms
cursor authority in StateMachine › always accepts PTY when no recent optimistic update
0.5176449999999875ms
cursor authority in StateMachine › resets authority on state transition out of AWAITING
0.9462230000000034ms
cursor authority in StateMachine › default source parameter is pty
0.5496440000000007ms
select_option proportional delay › delay scales with step count
0.627079000000009ms
option re-emission with cursorIndex › AWAITING_OPTION update triggers state_changed with options
0.7241489999999828ms
option re-emission with cursorIndex › updateCursorIndex emits snapshot with new cursor value
0.5462280000000135ms
State Machine & Adapters PASS
에이전트의 상태 전이와 타입별 명령 라우팅이 정확한가?
167 passed 0 failed 3 files 166ms
state-machine.test.ts
50 / 50 53ms
StateMachine 50 / 50
basic transitions › starts in DISCONNECTED
6.139218999999912ms
basic transitions › SessionStart → IDLE
1.3239370000000008ms
basic transitions › UserPromptSubmit → PROCESSING
1.236242999999945ms
basic transitions › Stop → IDLE from PROCESSING
0.9124100000000226ms
basic transitions › SessionEnd → DISCONNECTED from any state
0.7733500000000504ms
permission flow › permission_prompt → AWAITING_PERMISSION
0.8939559999998892ms
permission flow › user respond → PROCESSING from AWAITING_PERMISSION
0.9775409999999738ms
option flow › option_prompt → AWAITING_OPTION
0.8047900000000254ms
option flow › select_option → PROCESSING from AWAITING_OPTION
0.793818999999985ms
diff flow › diff_prompt → AWAITING_DIFF
0.7693940000000339ms
diff flow › respond → PROCESSING from AWAITING_DIFF
0.774742999999944ms
interrupt › interrupt → IDLE from PROCESSING
0.6888430000000199ms
interrupt › interrupt → IDLE from AWAITING_PERMISSION
0.7444169999999986ms
strict transitions › allows IDLE → AWAITING_PERMISSION (prompt without spinner)
0.6701689999999871ms
strict transitions › blocks invalid transition: DISCONNECTED → PROCESSING
0.510360999999989ms
strict transitions › allows wildcard session_end from any state
0.8025250000000597ms
stuck timeout › PROCESSING for >5min → auto-recovery to IDLE
1.3642820000000029ms
stuck timeout › AWAITING_PERMISSION does NOT timeout (waits for user)
0.84418299999993ms
stuck timeout › AWAITING_OPTION does NOT timeout (waits for user)
0.7344590000000153ms
stuck timeout › AWAITING_DIFF does NOT timeout (waits for user)
0.7719779999999901ms
stuck timeout › timer resets on state change before timeout
0.8716940000000477ms
stuck timeout › no timeout in IDLE state
0.7414619999999559ms
parser events › spinner_start → PROCESSING from IDLE
0.794571000000019ms
parser events › spinner_stop → IDLE from PROCESSING
0.5706030000000055ms
parser events › idle → IDLE from PROCESSING
0.5747609999999668ms
parser events › mode_change updates permission mode
0.5801609999999755ms
snapshot › emits state_changed on transitions
0.6013000000000375ms
snapshot › includes tool info in snapshot
0.6696780000000899ms
snapshot › clears tool info on PostToolUse
5.878854000000047ms
snapshot › includes project name and model
0.7373739999999316ms
billingType detection › defaults to unknown
0.6390010000000075ms
billingType detection › detects subscription from "Claude Max" plan
0.7009959999999182ms
billingType detection › detects subscription from "Max" (case-insensitive)
2.1614170000000286ms
billingType detection › detects api from "api.anthropic.com"
0.5087579999999434ms
billingType detection › detects api (case-insensitive)
0.46751100000005863ms
billingType detection › stays unknown for unrecognized plan
0.44395699999995486ms
billingType detection › stays unknown when plan is absent
0.5838380000000143ms
billingType detection › persists billingType across subsequent model_info without plan
0.4903439999999364ms
billingType detection › emits state_changed when billingType is set
0.4847139999999399ms
spinner_start recovery from awaiting states › spinner_start transitions from AWAITING_OPTION to PROCESSING
0.6175210000000106ms
spinner_start recovery from awaiting states › spinner_start transitions from AWAITING_PERMISSION to PROCESSING
0.7073979999998983ms
spinner_start recovery from awaiting states › spinner_start transitions from AWAITING_DIFF to PROCESSING
0.7470019999999522ms
spinner_start recovery from awaiting states › clears options and navigable state on spinner_start from AWAITING_OPTION
2.584795999999983ms
spinner_start recovery from awaiting states › stores navigable and cursorIndex from permission_prompt
0.7634630000000016ms
spinner_start recovery from awaiting states › cursor index tracking via updateCursorIndex
0.7642639999999119ms
cursor authority (optimistic vs pty) › optimistic source updates cursor immediately
0.6278300000000172ms
cursor authority (optimistic vs pty) › suppresses stale PTY within 200ms of optimistic
0.7171369999999797ms
cursor authority (optimistic vs pty) › accepts PTY after 200ms grace period
0.6826919999999745ms
cursor authority (optimistic vs pty) › emits state_changed on optimistic update
0.8453250000000025ms
cursor authority (optimistic vs pty) › does NOT emit state_changed when stale PTY is suppressed
0.7352099999999382ms
adapter.test.ts
93 / 93 83ms
createAdapter factory 5 / 5
creates ClaudeCodeAdapter for "claude-code"
2.8501509999999826ms
creates OpenClawAdapter for "openclaw"
0.4865670000000364ms
passes gatewayUrl to OpenClawAdapter
0.15282400000000962ms
creates CodexCliAdapter for "codex-cli"
0.4961049999999432ms
throws for unknown agent type
0.982731000000058ms
ClaudeCodeAdapter 17 / 17
capabilities › reports all Claude Code capabilities as true
0.7929070000000138ms
handleCommand routing › handles respond → returns true
0.5764239999999745ms
handleCommand routing › handles switch_mode → returns true
0.3441010000000233ms
handleCommand routing › handles interrupt → returns true
0.4427850000000717ms
handleCommand routing › handles escape → returns true
0.43872699999997167ms
handleCommand routing › defers select_option to bridge → returns false
0.3848570000000109ms
handleCommand routing › defers navigate_option to bridge → returns false
0.4063780000000179ms
handleCommand routing › defers send_prompt to bridge → returns false
0.5534390000000258ms
handleCommand routing › defers voice to bridge → returns false
0.4050250000000233ms
handleCommand routing › defers query_usage to bridge → returns false
0.29887700000006134ms
switch_mode debounce › debounces rapid switch_mode calls (< 100ms apart)
1.054595000000063ms
lifecycle › isAlive returns false before start
0.41533400000002985ms
lifecycle › getTtyPath returns undefined before start
0.42687499999999545ms
lifecycle › getProjectName returns null before start
1.7425770000000966ms
lifecycle › getHttpServer returns an object
0.4180790000000343ms
onRawData callback › can register callback without error
0.44081200000005083ms
onDiag handler › can register handler without error
0.3401339999999209ms
OpenClawAdapter 17 / 17
capabilities › reports OpenClaw capabilities correctly
0.40489500000001044ms
handleCommand routing › handles respond → returns true (RPC)
0.461879999999951ms
handleCommand routing › handles select_option → returns true (RPC)
0.23380500000007487ms
handleCommand routing › handles navigate_option → returns true (no-op)
0.22050100000001294ms
handleCommand routing › handles send_prompt → returns false without session key
0.26252899999997226ms
handleCommand routing › handles interrupt → returns true (RPC)
0.16767299999992247ms
handleCommand routing › handles escape → returns true (RPC)
0.1362139999999954ms
handleCommand routing › defers switch_mode → returns false (not supported)
0.12934100000006765ms
handleCommand routing › defers voice to bridge → returns false
0.1296710000000303ms
handleCommand routing › defers query_usage to bridge → returns false
0.16944599999999355ms
lifecycle › isAlive returns false before start
0.14066200000002027ms
lifecycle › getTtyPath returns undefined (no PTY)
0.15165300000001025ms
lifecycle › getProjectName returns null before start
0.1296109999999544ms
lifecycle › getHttpServer returns an object
0.1298509999999169ms
lifecycle › attachTerminal is a no-op
0.3945450000001074ms
onRawData callback › can register callback without error
0.35853800000006686ms
onDiag handler › can register handler without error
0.3410559999999805ms
OpenClawAdapter gateway protocol 13 / 13
sends connect request with correct format on connect.challenge
4.293509999999969ms
becomes alive after hello-ok response
9.476991999999996ms
emits spinner_start on chat delta event
1.1263989999999922ms
emits idle on chat final event
1.0287160000000313ms
emits idle on chat aborted event
0.8053409999999985ms
emits idle on chat error event
0.5843290000000252ms
emits permission_prompt on exec.approval.requested
0.8636090000001104ms
sends exec.approval.resolve on respond after approval request
1.1879440000000159ms
sends exec.approval.resolve with deny on respond "n"
0.8194770000000062ms
sends chat.send on send_prompt with active session
1.613615999999979ms
sends chat.abort on interrupt with active session and runId
4.440162999999984ms
emits SessionEnd on shutdown event
0.7056949999999915ms
clears pendingApprovalId on exec.approval.resolved
0.7123370000000477ms
CodexCliAdapter 16 / 16
capabilities › reports Codex CLI capabilities correctly
0.6846860000000561ms
handleCommand routing › handles respond → returns true
0.31171999999992295ms
handleCommand routing › handles interrupt → returns true
0.3367079999999305ms
handleCommand routing › handles escape → returns true
0.33827000000007956ms
handleCommand routing › does not handle switch_mode → returns false
0.46271200000001045ms
handleCommand routing › defers select_option to bridge → returns false
0.3100680000000011ms
handleCommand routing › defers navigate_option to bridge → returns false
1.124461999999994ms
handleCommand routing › defers send_prompt to bridge → returns false
0.3861289999999826ms
handleCommand routing › defers voice to bridge → returns false
0.32419400000003407ms
handleCommand routing › defers query_usage to bridge → returns false
0.33156799999994746ms
lifecycle › isAlive returns false before start
0.35561299999994844ms
lifecycle › getTtyPath returns undefined before start
0.31246199999998225ms
lifecycle › getProjectName returns null before start
0.3166599999999562ms
lifecycle › getHttpServer returns an object
0.28047300000002906ms
onRawData callback › can register callback without error
0.39335300000004736ms
onDiag handler › can register handler without error
0.5574480000000221ms
CodexCliAdapter start lifecycle 2 / 2
emits SessionStart and connected on start
4.621651000000043ms
feeds PTY data to output parser and emits activity
3.08720500000004ms
MonitorAdapter 18 / 18
capabilities › reports monitor capabilities correctly
0.8558940000000348ms
handleCommand routing › rejects respond (no PTY)
0.38286300000004303ms
handleCommand routing › rejects interrupt (no PTY)
0.319515000000024ms
handleCommand routing › rejects escape (no PTY)
0.34104600000000573ms
handleCommand routing › rejects switch_mode (no PTY)
0.3115900000000238ms
handleCommand routing › rejects select_option (no PTY)
0.2914130000000341ms
handleCommand routing › rejects send_prompt (no PTY)
0.29601199999990513ms
handleCommand routing › defers voice to bridge
0.3154269999999997ms
handleCommand routing › defers query_usage to bridge
0.29048199999999724ms
lifecycle › isAlive always returns true
0.30623000000002776ms
lifecycle › getTtyPath returns undefined (no PTY)
0.3377490000000307ms
lifecycle › getProjectName returns null
0.3274099999999862ms
lifecycle › getHttpServer returns an object
0.3049679999999171ms
lifecycle › writeInput is a no-op (no PTY)
0.49510299999997187ms
lifecycle › attachTerminal is a no-op
2.3978200000000243ms
lifecycle › onRawData is a no-op
0.477359999999976ms
start and event emission › emits connected event on start
0.5608549999999468ms
start and event emission › exposes hook server for external wiring
0.36807599999997365ms
ClaudeCodeAdapter start lifecycle 5 / 5
emits SessionStart and connected on start
1.761622999999986ms
uses claude as default command
1.2821390000000292ms
feeds PTY data to output parser and emits activity
4.378838999999971ms
emits SessionEnd and disconnected on PTY exit
2.365056999999979ms
registers rawData callback without error
1.4138040000000274ms
protocol-contract.test.ts
24 / 24 29ms
Protocol Contract — StateUpdateEvent 5 / 5
minimal state_update has required fields
4.375326000000001ms
full state_update has all optional fields as correct types
1.7192540000000065ms
state_update serializes to valid JSON
0.3691880000000083ms
state enum values are lowercase strings
0.5960509999999886ms
promptType values match known set
0.26497399999999516ms
Protocol Contract — UsageEvent 3 / 3
has all required numeric fields
0.46835300000000757ms
rate limit fields are present when available
1.7061089999999979ms
tokenStatus matches known values
0.3167399999999816ms
Protocol Contract — SessionsListEvent 2 / 2
sessions have required fields
0.5599129999999946ms
agentType is optional string
0.23377499999998008ms
Protocol Contract — ButtonStateEvent 1 / 1
buttons have required fields
0.9331280000000106ms
Protocol Contract — EncoderStateEvent 1 / 1
encoders have required fields
0.842378999999994ms
Protocol Contract — TimelineEventMsg 1 / 1
entry has required fields
0.43859700000001567ms
Protocol Contract — ConnectionEvent 1 / 1
has required fields
0.35678400000000465ms
Protocol Contract — DisplayStateEvent 1 / 1
has boolean displayOn
0.2679989999999748ms
Protocol Contract — PluginCommand shapes 5 / 5
respond command has value
0.2554359999999747ms
select_option has numeric index
0.19306000000000267ms
navigate_option has direction
0.24006699999995362ms
send_prompt has text
0.18752000000000635ms
utility command has action
0.2978039999999851ms
Protocol Contract — BridgeEvent discriminated union 2 / 2
all event types in union have type field
3.1824060000000145ms
SERIAL_FORWARDED_EVENTS covers expected types
8.586139000000003ms
Protocol Contract — Backward Compatibility 2 / 2
state_update can be parsed with only required fields (old client)
0.5543329999999855ms
usage_update required fields are sufficient for display
0.4024400000000128ms
Timeline Pipeline PASS
이벤트 타임라인의 저장, 중복 제거, 세션 간 릴레이가 올바른가?
80 passed 0 failed 3 files 1.3s
timeline.test.ts
54 / 54 16ms
cleanDetailText 12 / 12
returns empty/falsy input unchanged
1.5987590000000012ms
strips markdown bold
0.39920399999999745ms
strips markdown headings
0.2710450000000151ms
strips code fences
0.12677700000000414ms
strips inline backticks
0.11168899999998416ms
strips markdown links
0.11099699999999757ms
strips blockquotes
0.10947400000000584ms
strips list markers
0.11438300000000368ms
collapses multiple blank lines
0.115916000000027ms
filters system JSON blobs (connectionId)
0.15605000000002178ms
extracts error from JSON blob
0.12462199999998802ms
compacts other JSON
0.1398200000000145ms
cleanRawText 2 / 2
strips bold, headings, links, backticks
0.17596799999998325ms
returns empty/falsy unchanged
0.12542400000000953ms
cleanNopMarkers 3 / 3
removes NOP markers
0.3032750000000135ms
collapses resulting blank lines
0.12302999999999997ms
returns empty/falsy unchanged
0.11249999999998295ms
extractSemanticCore 4 / 4
strips duration suffix for chat_end
0.15685199999998645ms
keeps full text for chat_end without separator
0.12141600000001063ms
keeps full text for non-chat_end types
0.13653399999998328ms
trims whitespace
0.11273900000000481ms
isRepetitiveEntry 11 / 11
detects exact duplicate chat_end entries
0.4236799999999903ms
detects keyword-similar entries
0.5674869999999999ms
returns -1 for non-matching entries
0.23943699999998103ms
ignores entries outside window
0.19712699999999472ms
only applies to chat_end, chat_start, and error types
0.1780509999999822ms
dedupes repeated error entries within 1h window
0.24330299999999738ms
matches chat_start entries
0.15434799999999882ms
dedupes automated entries regardless of content
0.15349600000001828ms
does not dedup automated vs non-automated
0.17042699999998945ms
uses 8h window for automated entries
0.14819600000001287ms
expires automated dedup after 8h
0.15284499999998502ms
parseLogLine 22 / 22
returns null for null/undefined/non-object
0.5689900000000137ms
returns null for empty message
0.14983999999998332ms
returns null for model start/complete (suppressed)
0.218135999999987ms
parses memory/recall (legacy structured)
0.41242900000000304ms
parses tool execution (legacy structured)
0.24767099999999687ms
filters gateway/ws subsystem
0.14561100000000238ms
filters infrastructure noise
0.4736519999999871ms
filters channel infra reconnect noise
0.8846780000000081ms
filters connection status JSON blobs
0.437736000000001ms
filters transient fetch timeouts
0.27102500000000873ms
filters edit mismatch errors (agent retries)
0.16169099999999048ms
filters failover cascade noise
0.2586019999999962ms
parses genuine errors
0.6778639999999996ms
parses error from message pattern (not level)
0.5285449999999798ms
filters model/inference patterns (suppressed)
0.5127750000000049ms
parses memory patterns from message text
0.34446200000002136ms
parses tool patterns from message text
0.2673680000000047ms
parses ISO timestamp correctly
0.23995700000000397ms
falls back to Date.now() for invalid timestamp
0.280493000000007ms
truncates long tool raw to 500 chars
0.27673599999999965ms
does NOT filter user-facing whatsapp tool messages (non-infra subsystem)
0.18710799999999495ms
filters whatsapp noise only from channel infra subsystem
0.30137099999998895ms
timeline-integration.test.ts
21 / 21 16ms
BridgeTimelineStore 10 / 10
adds and retrieves entries
4.744551000000001ms
filters history by timestamp
0.39785100000000284ms
calls listeners on new entries
0.37577000000001703ms
upsert updates existing entry with same ts+type
0.9958860000000129ms
upsert adds new entry when no match exists
0.25649799999999345ms
updateEntryStatus updates approval status
0.2818049999999914ms
getLastEntry returns most recent of given type
0.3477980000000116ms
getLastEntry returns null when type not found
0.16824399999998718ms
removeListener stops notifications
0.3158780000000263ms
enforces MAX_ENTRIES (200) with FIFO
3.5517380000000003ms
deduplicateEntry pipeline 3 / 3
exact duplicate within 5s → skip
0.28824699999998415ms
same type, different content → add
0.22506900000001906ms
different type, same raw → add
0.21551099999999224ms
Timeline → WS broadcast pipeline 4 / 4
store entries trigger broadcast via listener
0.48969200000001933ms
upsert entries broadcast with upsert flag
0.4146329999999807ms
exact duplicate within 5s is skipped by store
0.30157199999999307ms
different content within 5s is NOT deduped
0.3112700000000075ms
TimelineEntry types 4 / 4
common entry types have expected shape
1.384680000000003ms
entries with status field
0.24287200000000553ms
entries with detail field
0.31452600000000075ms
entries with automated flag
0.1907250000000147ms
session-timeline-relay.test.ts
5 / 5 1.2s
SessionTimelineRelay 5 / 5
connects to sibling and relays timeline_event
310.8948479999999ms
relays timeline_history entries
301.95796299999995ms
removes subscription when session disappears
201.8820619999999ms
ignores daemon sessions
0.3696789999999055ms
handles upsert timeline events
402.03546499999993ms
Daemon & Infrastructure PASS
데몬 싱글톤, 세션 레지스트리, 사용량 릴레이가 안정적인가?
60 passed 0 failed 4 files 1.3s
daemon-lifecycle.test.ts
19 / 19 51ms
daemon.json lifecycle 6 / 6
writeDaemonInfo creates daemon.json with correct content
6.447904999999992ms
readDaemonInfo returns info when PID is alive
1.3958109999999806ms
readDaemonInfo returns null and removes file when PID is dead
1.1489009999999666ms
readDaemonInfo returns null when file does not exist
0.5666349999999625ms
removeDaemonInfo deletes daemon.json
0.8290250000000015ms
removeDaemonInfo is safe when file already gone
1.616581999999994ms
session registry with real files 7 / 7
register creates sessions.json
2.3274860000000217ms
register replaces existing entry with same id
1.5778300000000058ms
deregister removes session by id
1.5562400000000025ms
listActive prunes dead PIDs
1.3861630000000105ms
multiple sessions coexist
1.1079949999999599ms
findExistingDaemon returns daemon session
0.9020909999999844ms
findExistingDaemon returns null when no daemon
0.5556149999999889ms
findDaemonPort 4 / 4
returns port from daemon.json (priority 1)
0.7557780000000207ms
falls back to sessions.json daemon entry
0.6610919999999965ms
returns null when no daemon anywhere
0.3669940000000338ms
daemon.json takes precedence over sessions.json
0.7994199999999978ms
probeDaemonHealth 2 / 2
returns health JSON from running server
23.422112999999968ms
returns null for closed port
3.112549999999999ms
session-registry.test.ts
10 / 10 10ms
Session Registry Logic 10 / 10
pruneDeadSessions › keeps alive sessions
2.8952549999999917ms
pruneDeadSessions › removes sessions with dead PIDs
0.46155099999998583ms
pruneDeadSessions › keeps old sessions if PID is alive
0.29477900000000545ms
pruneDeadSessions › handles mix of alive and dead sessions
1.0332159999999817ms
port allocation logic › returns base port when no ports are used
0.27894000000000574ms
port allocation logic › returns next port when base is taken
0.13985999999999876ms
port allocation logic › skips used ports
0.12622600000000261ms
port allocation logic › finds gaps in used ports
0.13911899999999378ms
port allocation logic › throws when all ports are taken
0.8165010000000166ms
atomic write › write-then-rename produces valid JSON
2.7206290000000024ms
usage-relay.test.ts
12 / 12 625ms
Usage relay — HTTP (Tier 1) 3 / 3
fetches usage from sibling GET /usage
68.21826199999998ms
returns null usage when sibling has no data
9.728497000000004ms
rejects stale data (>5 min old)
3.9891230000000064ms
Usage relay — WebSocket (Tier 2) 2 / 2
receives usage_update from sibling WS on connect
261.911125ms
does not send usage_update when sibling has no data
252.30680899999993ms
HookServer GET /usage (relay source) 2 / 2
returns cached usage via onApiUsage getter
7.428352000000018ms
returns fresh usage after update
6.664760999999999ms
429 prevention — relay-first strategy 2 / 2
sibling with data prevents direct API call
3.105425999999966ms
multiple siblings — first with data wins
10.326020999999969ms
ApiUsageData shape 3 / 3
has all required fields
0.4047640000000001ms
serializes to valid JSON and back
0.29486899999994876ms
handles null optional fields
0.2886680000000297ms
bridge-core.test.ts
19 / 19 584ms
BridgeCore Orchestration 19 / 19
buildStateEvent › builds state_update with IDLE state
20.655975999999953ms
buildStateEvent › includes cached ollamaStatus and gatewayAvailable
5.461997999999994ms
buildStateEvent › computes promptType for permission options
4.164980999999955ms
buildStateEvent › computes promptType yes_no_always for 3+ permission options
3.41153700000001ms
usage management › updateApiUsage caches and broadcasts
24.142669000000012ms
usage management › buildUsage includes API usage data
6.792168000000061ms
usage management › buildUsage works without API data
4.99029900000005ms
usage management › inferredBillingType propagates to StateMachine
5.450956999999903ms
sendInitialState › sends state_update, usage_update, connection, display_state on connect
23.22701900000004ms
sendInitialState › includes timeline_history when entries exist
17.689384999999902ms
state change broadcast › state_changed emits to WS clients when wired by caller
7.345890000000054ms
wireTimeline › timeline entries broadcast as timeline_event
58.423558999999955ms
hasClients guard › wsServer.getClientCount reflects connected clients
257.162238ms
hasClients guard › external client count provider extends hasClients
6.158846999999923ms
voice assistant state › updateVoiceAssistantState caches and triggers state broadcast
58.70784900000001ms
voice assistant state › disabled voice assistant state is not included in event
5.302780999999982ms
session registry › registerSession writes to sessions.json
6.454316000000063ms
session registry › deregisterSession removes from sessions.json
5.554038999999989ms
broadcast coordination › broadcast sends to WS and SSE callback
60.82565899999997ms
Integration Tests PASS
전체 파이프라인이 실제 서버 환경에서 동작하는가?
29 passed 0 failed 2 files 942ms
server-integration.test.ts
15 / 15 640ms
Server Integration 15 / 15
SessionStart hook → IDLE state broadcast
100.98373700000002ms
full session lifecycle: SessionStart → UserPromptSubmit → Stop
17.635991000000047ms
PreToolUse → PostToolUse cycle broadcasts tool info
19.975450000000023ms
SessionEnd → DISCONNECTED
10.109758ms
GET /health returns valid JSON
10.527987999999937ms
GET /usage returns data when getter is set
7.237184999999954ms
GET /usage returns null when no getter
5.510058000000072ms
GET /devices returns empty when no getter
5.503164999999967ms
POST to unknown route returns 404
6.852559000000042ms
hook endpoint responds immediately
6.98007599999994ms
SSE client receives state_update events
77.68440800000008ms
broadcasts to multiple WS clients
8.269121000000041ms
WS command from client triggers callback
104.57280099999991ms
rapid hook events do not corrupt state
246.7010069999999ms
token counts accumulate through hook events
10.522286000000008ms
tier3-integration.test.ts
14 / 14 302ms
mDNS crash recovery 3 / 3
invalidateMdnsInstance does not throw when no instance exists
2.883713ms
EADDRNOTAVAIL pattern matches expected error messages
0.3882239999999797ms
non-mDNS errors are NOT matched by recovery pattern
0.23561900000004243ms
Display sleep/wake broadcast 5 / 5
DisplayMonitor initial state is ON
0.2616869999999949ms
display_state event has correct shape
0.22176300000000992ms
display_state broadcasts to WS clients
77.42405600000001ms
display_state broadcasts to multiple clients
56.397366000000034ms
SSE also receives display_state
112.175973ms
Voice transcription endpoint 4 / 4
returns 503 when no voice manager is set
20.84686499999998ms
returns 400 for empty audio data
6.883675999999923ms
returns transcription from voice manager
11.474199999999996ms
returns 500 when voice manager throws
5.274587999999994ms
WsServer broadcast hooks (serial relay) 2 / 2
onBroadcast hook receives all broadcast events
1.8000549999999294ms
broadcast hook errors do not crash server
1.2710480000000643ms
Stream Deck Plugin UI PASS
플러그인의 연결 관리, 옵션 레이아웃, 렌더링이 정확한가?
107 passed 0 failed 5 files 1.8s
connection-manager.test.ts
15 / 15 11ms
ConnectionManager 15 / 15
starts disconnected
2.670055000000019ms
start() begins bridge connection
2.283143999999993ms
emits connected when bridge connects
0.9167580000000157ms
emits disconnected when bridge disconnects
0.3879530000000102ms
forwards state_update from bridge
0.8154899999999827ms
send() delegates to bridge
0.7367429999999899ms
send() drops command when not connected
0.3348839999999882ms
reconnectBridgeTo delegates to bridge
0.3245040000000188ms
getBridgePort returns bridge port
0.23640100000000075ms
scanLatestPort setter delegates to bridge
0.2873459999999852ms
switchToOpenClaw() › sends switch_agent command to bridge
0.9096859999999936ms
switchToClaude() › sends switch_agent command to bridge
0.32275099999998247ms
isGatewayAvailable() › returns false by default
0.22174300000000358ms
isGatewayAvailable() › returns true when bridge reports gateway available
0.2786389999999983ms
isGatewayAvailable() › returns false when bridge reports gateway unavailable
0.2006539999999859ms
connection-integration.test.ts
6 / 6 1.7s
ConnectionManager Integration — Real WebSocket 6 / 6
client connects and receives broadcast events
229.422348ms
multiple clients receive same broadcast
205.882293ms
client sends command to server
152.59363799999994ms
handles rapid connect/disconnect without crashes
415.068169ms
server detects client disconnect
254.45556299999998ms
bridge → gateway priority: second server takes over on disconnect
407.42334000000005ms
option-scenario.test.ts
15 / 15 8ms
6-option SELECT scenario 9 / 9
Quick Action slots: 3 options + MORE (6 options)
3.1512209999999925ms
STOP slot is always preserved (getStopSlotOverride returns null)
0.20214699999999652ms
3 options: all shown in Quick Action slots, 4th slot DIM
0.44635099999999284ms
4 options: all 4 shown, no MORE
0.3850480000000118ms
5 options: 3 options + MORE
0.3181629999999984ms
E2 Focus panel renders with adaptive font
0.5979640000000188ms
E3 List panel renders 4 visible rows with 14px font
0.6220799999999826ms
E4 Detail panel shows word-wrapped label (12px, left-aligned)
0.5054820000000007ms
PERMISSION without shortcut: diffButtons uses label first char
0.5945280000000253ms
colorForOption — "don't ask again" / "allow all sessions" 6 / 6
returns blue for "Yes, and don't ask again for: tail:*"
0.1786730000000034ms
returns blue for "Yes, and don’t ask again" (smart quote)
0.23029900000000225ms
returns blue for "Yes, allow all sessions in project"
0.16804400000000896ms
returns green for plain "Yes" (shortcut y)
0.12387099999997986ms
returns green for "Apply" (shortcut a, but no "don't ask" pattern)
0.1144130000000132ms
returns blue for "Always allow"
0.11335099999999443ms
renderer-snapshots.test.ts
52 / 52 59ms
voice-renderer snapshots 12 / 12
renderVoiceReady
5.024222000000009ms
renderVoiceRecording frame 0
0.745439000000033ms
renderVoiceRecording frame 30 (>1min)
0.3752190000000155ms
renderVoiceTranscribing frame 0
0.4372139999999831ms
renderVoiceTranscribing frame 10 (different dot phase)
0.3135350000000017ms
renderVoiceError with message
0.4797940000000267ms
renderVoiceError default
0.3110699999999724ms
renderVoiceDisabled
0.38129000000003543ms
renderVoiceAssistantListening frame 0
0.4144319999999766ms
renderVoiceAssistantProcessing frame 5
0.4388680000000136ms
renderVoiceAssistantSpeaking frame 0
0.510360999999989ms
renderWideVoiceText returns correct panel count
2.9907029999999963ms
utility-renderer snapshots 4 / 4
renderSetupUtility
3.0743380000000116ms
renderUtilityGeneric with icon
0.6723430000000121ms
renderUtilityGeneric text-only (no icon)
0.4670300000000225ms
renderUtilityMedia
0.5638599999999769ms
iterm-renderer snapshots 4 / 4
renderItermReady
0.46313300000002755ms
renderItermPanel short name
0.7750839999999926ms
renderItermPanel long name wrapping
0.42355900000001157ms
renderItermDisabled
0.36589099999997643ms
response-renderer snapshots 7 / 7
renderResponseIdle
0.645922999999982ms
renderResponseProcessing
0.4223569999999768ms
renderResponseDisconnected
0.3688769999999977ms
renderResponseDisabled
0.30928599999998596ms
renderResponseSuggestion
0.5813640000000078ms
renderResponseInteractive
0.3057590000000232ms
renderSetupPrompt
0.26281000000000176ms
option-renderer snapshots 7 / 7
renderContextPanel permission
0.795031999999992ms
renderContextPanel diff
0.3850570000000175ms
renderFocusPanel with recommended option
0.7969149999999559ms
renderListPanel 3 options
0.6490089999999782ms
renderListPanel 6 options (scroll indicator)
0.40522500000008677ms
renderDetailPanel
0.5318009999999731ms
renderWideOptionList returns correct panel count
0.7739720000000716ms
button-renderer snapshots 7 / 7
basic text button
0.9677629999999908ms
button with subtitle
0.41863999999998214ms
disabled button
0.3042769999999564ms
loading button
0.41558500000007825ms
long text that needs abbreviation
0.31255300000009356ms
svgToDataUrl returns data URI
0.7155830000000378ms
labelNeedsHaiku detects long labels
1.5710569999999962ms
timeline-renderer snapshots 5 / 5
empty timeline
0.7085109999999304ms
single entry
1.5704859999999599ms
multiple entries fisheye
0.57802700000002ms
detail mode
0.595499000000018ms
with session status
0.4218549999999368ms
qr-renderer snapshots 3 / 3
extractUrlLabel extracts host:port
0.5976640000000089ms
qrPathData deterministic
14.933195000000069ms
renderQrButtonSvg
6.417961999999989ms
agent-logos snapshots 3 / 3
claude-code watermark
0.344141000000036ms
openclaw watermark
0.2576999999999998ms
CLAUDE_LOGO_PATH is defined
0.38490699999999833ms
text-utils-and-labels.test.ts
19 / 19 11ms
text-utils: CJK width measurement 4 / 4
Latin text is ~0.55em per char
2.3681430000000034ms
Korean text is 1em per char (double-width)
0.5733380000000068ms
mixed text measures correctly
0.21252599999999688ms
isWide detects Hangul, CJK, fullwidth
0.37313499999999067ms
text-utils: wrapTextByWidth 3 / 3
short text returns single line
1.221777000000003ms
long Latin text wraps to multiple lines
0.5970129999999756ms
Korean text wraps at correct pixel width
0.3457439999999963ms
button-renderer: abbreviation 10 / 10
short label renders without abbreviation indicator
1.3226149999999848ms
"Yes, I trust this folder" fits with wrapping (no abbreviation needed)
0.29007000000001426ms
"Yes, allow and don't ask again" wraps into 3 lines
0.22695300000000884ms
very long label triggers abbreviation with ~ indicator
0.872444999999999ms
short permission labels like "No" render unchanged
0.21993000000000507ms
labelNeedsHaiku returns false for short labels
0.23576900000000478ms
labelNeedsHaiku returns false when heuristic abbreviation fits
0.14620299999998565ms
labelNeedsHaiku returns true for very long unknown labels
0.403160999999983ms
labelNeedsHaiku returns false when Haiku cache has result
0.2890279999999734ms
BUTTON_MAX_CHARS is reasonable
0.23071999999999093ms
button-renderer: CJK labels 2 / 2
Korean label does not overflow (produces valid SVG)
0.249715000000009ms
mixed CJK/Latin label renders
0.15683299999997757ms
TUI Dashboard PASS
터미널 대시보드의 상태 렌더링과 테라리움 애니메이션이 올바른가?
49 passed 0 failed 3 files 42ms
tui-dashboard.test.ts
8 / 8 8ms
TUI dashboard models 8 / 8
stores modelCatalog from state_update
2.302990999999963ms
renders OAuth catalog and Ollama models in wide layout
2.4396859999999947ms
renders disconnected OAuth state
0.9560919999999555ms
shows current session summary and control hints
0.3617840000000001ms
renders agent list secondary line as model dash compact state
0.28651400000001104ms
renders sibling models in session bridge mode and omits uptime label
0.569390999999996ms
renders help overlay when helpVisible is on
0.43252599999999575ms
shows numbered session badges
0.4228479999999877ms
tui-renderer-snapshots.test.ts
29 / 29 14ms
blockGauge snapshots 7 / 7
0% — all empty, green
3.968344000000002ms
50% — half filled, green
0.43492999999998005ms
75% — yellow threshold
0.25891300000000683ms
95% — red threshold
0.25153899999997975ms
100% — all filled, red
0.2573989999999924ms
clamps negative to 0
0.21952000000001703ms
clamps above 100
0.21565100000000825ms
resetTimeStr 5 / 5
returns empty for undefined
0.48872999999997546ms
returns ↻now for past time
0.39117899999999395ms
formats minutes
0.49201700000000415ms
formats hours and minutes
0.22854599999999436ms
formats days and hours
0.22346699999999942ms
formatUptime 3 / 3
seconds
0.295771000000002ms
minutes
0.19464300000001344ms
hours and minutes
0.19098600000000943ms
formatTokens 3 / 3
below 1000 unchanged
0.23290399999999067ms
1k-10k with decimal
0.26047499999998536ms
10k+ rounded
0.2285359999999912ms
activityDensityBar 3 / 3
empty timestamps — all dim
0.36804499999999507ms
recent burst — bright right side
0.3034460000000081ms
spread timestamps — distributed density
0.30237399999998615ms
getLayout 3 / 3
wide for 120+ cols
0.25825100000000134ms
standard for 80-119 cols
0.2960019999999872ms
narrow for <80 cols
0.2591730000000041ms
shouldShowTerrarium 3 / 3
true for adequate size
0.23849500000000035ms
false for too narrow
0.17947399999999902ms
false for too short
0.1761290000000031ms
spinner 2 / 2
returns braille characters at different frames
2.0159260000000074ms
spinner cycles through 10 frames
0.2811240000000055ms
tui-terrarium-snapshots.test.ts
12 / 12 20ms
TUI terrarium snapshots 12 / 12
initTerrarium creates context with expected structure
4.480458999999996ms
setOctopi configures octopus instances
0.8847090000000151ms
setCrayfish configures crayfish state
0.3975409999999897ms
setJellyfish configures jellyfish instances
0.6178219999999897ms
renderTerrariumFrame empty terrarium (small)
4.002467999999993ms
renderTerrariumFrame empty terrarium (large)
1.1440220000000068ms
renderTerrariumFrame with idle octopus
2.9299900000000036ms
renderTerrariumFrame with processing octopus
1.0423219999999844ms
renderTerrariumFrame with routing crayfish
1.4731850000000009ms
renderTerrariumFrame with sick crayfish
1.2692750000000217ms
renderTerrariumFrame too small returns empty
0.39240099999997824ms
updateTerrarium advances bubble positions
0.6017010000000198ms
Serial Protocol PASS
ESP32와의 시리얼 바이트스트림이 정확히 프레이밍되는가?
22 passed 0 failed 1 files 16ms
esp32-serial-node.test.ts
22 / 22 16ms
SERIAL_FORWARDED_EVENTS 4 / 4
includes all display events
2.5518349999999828ms
includes timeline events (unique to serial)
0.34138599999999997ms
does NOT include plugin-only events
0.530557999999985ms
required serial events are present
0.47248100000001614ms
ESP32 port detection patterns 5 / 5
matches CH340 ports (86 Box)
0.631385999999992ms
matches native USB JTAG ports (IPS 3.5", Round AMOLED)
0.3275000000000148ms
matches Linux serial ports
0.3653109999999913ms
excludes Bluetooth and WLAN
0.24110899999999447ms
excludes non-ESP32 ports
0.2944789999999955ms
handleSerialLine (source) 4 / 4
parses device_info message and updates deviceInfo
0.7320840000000146ms
skips debug lines (non-JSON)
0.20564300000000912ms
recovers from malformed JSON
0.4375659999999755ms
ignores JSON without type field
0.22422800000001075ms
prepareForSerial (source) 5 / 5
strips agentCapabilities from state_update
0.5830369999999903ms
strips billingType and remoteUrl from state_update
0.34815900000000966ms
preserves essential state_update fields
1.8756349999999884ms
strips legacy usage fields from usage_update
1.0114550000000122ms
passes through other events unchanged
1.0119760000000042ms
WiFi provision protocol 1 / 1
provision message has all required fields
0.522673999999995ms
serial buffer management 3 / 3
line splitting handles multiple lines in one chunk
0.3709920000000011ms
handles partial message across chunks
0.5304090000000201ms
truncates buffer when exceeding 8KB limit
0.18777000000000044ms
Display Rendering PASS
외부 디스플레이에 전송할 이미지 데이터가 올바른가?
3 passed 0 failed 1 files 3ms
pixoo-sprites.test.ts
3 / 3 3ms
getOctopusPaletteForSession 3 / 3
keeps the first additional session near the original terracotta tone
2.273947000000021ms
darkens later sessions while preserving channel ordering
0.4181989999999871ms
clamps very large session indices to the darkest supported tone
0.27036300000000324ms
Hook Installation PASS
Claude Code hook의 설치, 제거, 마이그레이션이 안전한가?
18 passed 0 failed 1 files 13ms
install.test.ts
18 / 18 13ms
Hook Installer 18 / 18
buildHookEntry › creates matcher-group format with AGENTDECK_PORT env var
2.8099049999999863ms
buildHookEntry › includes fallback port 9120 in command
0.1852660000000128ms
applyHooks › installs hooks to empty settings in matcher-group format
3.4370639999999923ms
applyHooks › preserves non-AgentDeck hooks
0.5023669999999925ms
applyHooks › replaces old flat-format hooks
0.31971599999999967ms
applyHooks › replaces old matcher-format hooks
0.26550399999999286ms
applyHooks › is idempotent — running twice produces same result
0.8222219999999822ms
applyHooks › preserves existing non-hook settings
1.0946390000000008ms
removeHooks › removes all AgentDeck hooks (new format)
0.34095599999997717ms
removeHooks › removes old flat-format AgentDeck hooks
0.16522800000001325ms
removeHooks › preserves non-AgentDeck hooks
0.3110900000000072ms
removeHooks › handles empty settings gracefully
0.13995099999999638ms
migrateHooks › migrates old hardcoded port to env var
0.3678859999999986ms
migrateHooks › migrates flat format to matcher-group format
0.2235070000000121ms
migrateHooks › skips already-migrated hooks (new format)
0.20141499999999724ms
migrateHooks › skips non-AgentDeck hooks
0.15064100000000735ms
migrateHooks › migrates multiple events at once
0.5402569999999969ms
migrateHooks › migrates hardcoded port inside matcher-group
0.3014220000000023ms
Other Tests
Uncategorized test files
22 passed 0 failed 3 files
bridge-core-sessions.test.ts
2 / 2 77ms
BridgeCore sessions_list 2 / 2
broadcastSessionsList enriches sessions before broadcast
15.817834000000005ms
sendInitialState sends enriched sessions_list to the connecting client
60.989855999999975ms
session-aggregator.test.ts
4 / 4 13ms
session-aggregator 4 / 4
uses ownState for the current session without fetching /health
5.439536000000004ms
fetches sibling /health and merges state and modelName
4.07585499999999ms
falls back to base session info when sibling /health fails
0.920375000000007ms
buildEnrichedSessionsList excludes daemon and own session before enrichment
1.781720000000007ms
format-utils.test.ts
16 / 16 6ms
adjustUsagePercent 9 / 9
returns undefined when percent is null
2.107797000000005ms
returns undefined when percent is undefined
0.24548699999999712ms
returns percent unchanged when resetsAt is null
0.36050199999999677ms
returns percent unchanged when resetsAt is undefined
0.18284099999999626ms
returns percent unchanged when resetsAt is in the future
0.5148189999999886ms
returns 0 when resetsAt is in the past (window expired)
0.20730600000001687ms
returns 0 when resetsAt equals now (edge case)
0.20119500000001267ms
handles invalid date string gracefully (returns percent)
0.13375000000002046ms
handles empty string resetsAt (returns percent)
0.11761899999999059ms
formatResetTime 7 / 7
returns "now" when resetsAt is in the past
0.2328239999999937ms
returns undefined for null input
0.1204050000000052ms
returns minutes-only for < 1h remaining
0.22311600000000453ms
returns hours and minutes for < 24h remaining
0.22983800000000087ms
returns days and hours for >= 24h remaining
0.26982300000000237ms
omits minutes when exactly on the hour
0.1859359999999981ms
passes through pre-formatted strings (no T)
0.1288199999999904ms
Android PASS
JUnit + Robolectric · 4 files · 82 tests
net.ProtocolTest
32 / 32 5.8s
parse state_update with all permission modes
4807ms
parse connection connected with sessionId
39ms
parse sessions_list
55ms
PluginCommands selectOption generates valid JSON
47ms
parse button_state
56ms
PluginCommands utility with and without value
44ms
parse invalid json returns null
39ms
parse timeline_history
35ms
parse timeline_event upsert
31ms
parse state_update with processing state and tool info
33ms
PluginCommands respond escapes special characters
43ms
PluginCommands respond generates valid JSON
39ms
parse state_update with permission options
31ms
parse connection disconnected
27ms
parse missing type returns null
29ms
parse deck_slot_map
50ms
parse usage_update with extra usage
29ms
parse state_update with ollama status
29ms
PluginCommands navigateOption
26ms
parse state_update with agent capabilities
27ms
parse unknown type returns null
25ms
parse user_prompt
30ms
BridgeTimelineEntry converts to TimelineEntry
41ms
parse state_update with model catalog
40ms
parse state_update ignores unknown fields
25ms
parse state_update with idle state
22ms
parse display_state sleep and wake
27ms
parse voice_state
25ms
parse encoder_state
27ms
PluginCommands interrupt and escape
24ms
parse usage_update with rate limits
19ms
parse timeline_event
19ms
state.SessionMetricsTest
8 / 8 8ms
reset clears all metrics
5ms
onMessageReceived updates lastMessageAt
onConnected sets connectedSince
onDisconnected clears connectedSince
clean reconnect after disconnect does not increment
initial state has no connection
reconnect increments reconnectCount when still connected
1ms
onMessageReceived increments count
state.TimelineStoreTest
22 / 22 19ms
addEntry allows same type+summary after 5s
2ms
clear empties the store
1ms
upsertEntry updates existing entry within 1s tolerance
groupConsecutive empty list returns empty
upsertEntry adds new entry if no match
addEntry stores entry
1ms
groupConsecutive groups same summary within 60s
updateLastOfType modifies the last matching entry
1ms
addEntries merges and deduplicates
3ms
upsertEntry preserves existing detail if new detail is null
groupConsecutive splits tool_request after 10s gap
addEntries sorts by timestamp
groupConsecutive splits different types
addEntry allows different type within 5s
groupConsecutive single entry
1ms
addEntry deduplicates within 5s window
addEntry allows different summary within 5s
groupConsecutive groups chat_end by type only within 60s
1ms
addEntry caps at MAX_ENTRIES
6ms
groupConsecutive requires same summary for other types
updateLastOfType no-op if type not found
2ms
groupConsecutive groups tool_request within 10s
util.TimeFormatUtilsTest
20 / 20 19ms
gaugeBar clamps below 0
2ms
formatCount thousands show K
2ms
formatBytes kilobytes
formatDurationCompact seconds
formatDurationCompact exact minutes no seconds
formatDurationCompact sub-second
1ms
formatCount int overload works
gaugeBar clamps above 100
formatBytes small values
1ms
formatCount small numbers unchanged
gaugeBar 50 percent is half filled
gaugeBar 0 percent is all empty
formatBytes megabytes
formatResetTime returns original on parse failure
10ms
gaugeBar custom width
formatBytes gigabytes
formatUptime zero returns 0 colon 00
formatCount millions show M
1ms
formatDurationCompact minutes
1ms
gaugeBar 100 percent is all filled
Robot Framework PASS
ESP32 Hardware Tests · 1 suites · 4 scenarios · 7 tests · 4 boards
BoardBuildFlash+BootBoot TimeFW SizeBoot HeapLatency
86Box20.2s
IPS 3.5"16.2s
Round16.2s
TC00116.1s
01_build.robot no-hwquicksmoke
7 / 7
Build And Verify 4 boards 4 / 4
Given the "${board}" firmware is built
Then the firmware binary should exist for "${board}"
And the firmware size should be sane for "${board}"
And the partitions binary should exist for "${board}"
✓ 86Box✓ IPS 3.5"✓ Round✓ TC001
Box 86 Build And Verify
20.2s
IPS 3.5 Build And Verify
16.2s
Round AMOLED Build And Verify
16.2s
Ulanzi TC001 Build And Verify
16.1s
Boot Test Environment Builds Successfully
1.5s
Source Files Are Present
PlatformIO Configuration Parses Cleanly
704ms
Scenario Coverage
User scenario mapping against actual test results
6 covered 4 partial/missing 10 with identified gaps
Score Scenario Priority Unit Integ. Platform E2E
6/8
Session Lifecycle
Start session -> processing -> idle -> stop. Core state machine transitions that drive all UI.
  • No end-to-end test with real Claude PTY process
  • No Android UI test for state transitions
critical 4/41/21/2
3/5
Permission Flow
Agent requests permission -> user sees options -> approves/denies -> state transitions back.
  • No multi-option navigation end-to-end test
  • No encoder dial interaction test for option scrolling
critical 2/20/21/1
7/7
Multi-agent Monitoring
Daemon hub orchestrates multiple session bridges, unified dashboard for all agents.
  • No daemon + session bridge coordinated test
  • No multi-agent state aggregation test
high 3/34/4
7/7
Device Connection
mDNS discovery -> auth token validation -> WebSocket/serial state sync with dashboard clients.
  • No real mDNS discovery test
  • No ADB reverse tunnel test
  • No auth token rejection test
high 3/33/31/1
4/5
Timeline Aggregation
Events from multiple sessions -> daemon relay -> dedup -> unified timeline for all clients.
  • No daemon-to-client relay end-to-end test
  • No LLM summary enrichment test
high 2/21/11/2
1/1
Voice Recording & Transcription
Audio capture -> whisper transcription -> text delivery to Claude PTY or clipboard.
  • No audio recording unit test
  • No recording -> transcription -> paste end-to-end
  • No Android voice recording test
  • No silence detection unit test
medium 1/1
3/3
Encoder & Button Interaction
Dial rotate -> option scroll -> push select. Button press -> action trigger. Label rendering.
  • No encoder rotate/push integration test
  • No wide canvas takeover test
  • No Android Deck gesture test
medium 3/3
4/5
Usage Tracking & Rate Limits
API usage fetch -> rate limit gauge -> sibling relay (429 prevention) -> dashboard display.
  • No real API rate limit response test
  • No usage_update WS relay end-to-end
medium 0/12/22/2
2/2
Daemon Singleton Guard
PID check -> port probe -> prevent double daemon. Auto-fallback on port conflict.
  • No port conflict auto-fallback test
  • No LaunchAgent KeepAlive loop prevention test
medium 1/11/1
1/1
Hook Installation & Migration
Install Claude Code hooks -> migrate v2.0 flat format to v2.1 matcher groups -> port injection.
  • No real settings.local.json file test
  • No hook execution verification test
medium 1/1
Coverage
v8 provider · 12,939 lines tracked
Lines ≥17%: 28.6%
Functions ≥15%: 24.8%
Branches ≥14%: 23.8%
Statements ≥16%: 27.4%
bridge
33% Lines
32% Stmts
30% Funcs
28% Branch
2708/8137 lines covered
plugin
17% Lines
16% Stmts
15% Funcs
12% Branch
747/4390 lines covered
shared
58% Lines
54% Stmts
56% Funcs
56% Branch
191/328 lines covered
hooks
64% Lines
62% Stmts
73% Funcs
71% Branch
54/84 lines covered
File Stmts Branch Funcs Lines
bridge/src/adb-reverse.ts 0% 0% 0% 0%
bridge/src/check-deps.ts 0% 0% 0% 0%
bridge/src/cli.ts 0% 0% 0% 0%
bridge/src/daemon-server.ts 0% 0% 0% 0%
bridge/src/daemon.ts 0% 0% 0% 0%
bridge/src/diag-analyzer.ts 0% 0% 0% 0%
bridge/src/event-journal.ts 0% 0% 0% 0%
bridge/src/index.ts 0% 0% 0% 0%
bridge/src/log-stream.ts 0% 0% 0% 0%
bridge/src/pty-ringbuffer.ts 0% 0% 0% 0%
bridge/src/terminal-status.ts 0% 0% 0% 0%
bridge/src/tts.ts 0% 0% 0% 0%
bridge/src/types.ts 0% 0% 0% 0%
bridge/src/utility-proxy.ts 0% 0% 0% 0%
bridge/src/version-check.ts 0% 0% 0% 0%
bridge/src/voice-assistant.ts 0% 0% 0% 0%
bridge/src/voice.ts 0% 0% 0% 0%
bridge/src/wake-word.ts 0% 0% 0% 0%
bridge/src/whisper-server-manager.ts 0% 0% 0% 0%
bridge/src/wifi-config.ts 0% 0% 0% 0%
bridge/src/modules/adb-module.ts 0% 0% 0% 0%
bridge/src/modules/index.ts 0% 0% 0% 0%
bridge/src/modules/mdns-module.ts 0% 100% 0% 0%
bridge/src/modules/pixoo-module.ts 0% 0% 0% 0%
bridge/src/modules/serial-module.ts 0% 0% 0% 0%
bridge/src/modules/types.ts 0% 0% 0% 0%
bridge/src/pixoo/pixoo-font.ts 0% 0% 0% 0%
bridge/src/pixoo/pixoo-settings.ts 0% 0% 0% 0%
bridge/src/tui/screen.ts 0% 0% 0% 0%
bridge/src/types/picovoice.d.ts 0% 0% 0% 0%
bridge/src/mdns.ts 4% 4% 11% 5%
bridge/src/ollama-probe.ts 5% 0% 0% 5%
bridge/src/tui/dashboard.ts 6% 12% 3% 6%
bridge/src/pixoo/pixoo-camera.ts 6% 0% 0% 7%
bridge/src/pixoo/pixoo-renderer.ts 6% 0% 0% 8%
bridge/src/timeline-summarizer.ts 7% 0% 0% 8%
bridge/src/pixoo/pixoo-sprites.ts 9% 0% 9% 10%
bridge/src/pixoo/pixoo-client.ts 11% 0% 0% 11%
bridge/src/pixoo/pixoo-bridge.ts 12% 0% 0% 14%
bridge/src/esp32-serial.ts 13% 12% 5% 14%
bridge/src/logger.ts 18% 10% 17% 15%
bridge/src/gateway-probe.ts 12% 0% 0% 16%
bridge/src/display-monitor.ts 20% 9% 18% 22%
bridge/src/usage-api.ts 26% 11% 55% 29%
bridge/src/bridge-core.ts 40% 38% 29% 43%
bridge/src/usage-tracker.ts 44% 55% 23% 44%
bridge/src/model-catalog.ts 42% 20% 40% 48%
bridge/src/pty-manager.ts 54% 31% 53% 55%
bridge/src/hook-server.ts 53% 29% 53% 55%
bridge/src/ws-server.ts 61% 31% 61% 60%
bridge/src/auth.ts 59% 37% 75% 63%
bridge/src/adapters/openclaw.ts 63% 44% 56% 65%
bridge/src/tui/renderer.ts 67% 51% 92% 67%
bridge/src/tui/terrarium.ts 70% 56% 76% 72%
bridge/src/adapters/claude-code.ts 73% 40% 50% 73%
bridge/src/tui/ansi.ts 75% 49% 83% 75%
bridge/src/state-machine.ts 76% 58% 81% 76%
bridge/src/session-registry.ts 75% 58% 74% 79%
bridge/src/adapters/monitor.ts 81% 60% 87% 81%
bridge/src/timeline-store.ts 83% 71% 100% 82%
bridge/src/adapters/pty-adapter.ts 82% 81% 65% 82%
bridge/src/session-timeline-relay.ts 78% 58% 67% 83%
bridge/src/adapters/codex-cli.ts 83% 100% 75% 83%
bridge/src/adapters/index.ts 83% 80% 100% 83%
bridge/src/output-parser.ts 89% 83% 100% 93%
bridge/src/codex-output-parser.ts 90% 83% 92% 94%
bridge/src/session-aggregator.ts 100% 100% 100% 100%
bridge/src/usage-event.ts 100% 100% 100% 100%
bridge/src/tui/gauge.ts 98% 96% 100% 100%
hooks/src/install.ts 62% 71% 73% 64%
plugin/src/agent-link.ts 0% 0% 0% 0%
plugin/src/bridge-client.ts 0% 0% 0% 0%
plugin/src/encoder-registry.ts 0% 0% 0% 0%
plugin/src/encoder-takeover.ts 0% 0% 0% 0%
plugin/src/expanded-actions.ts 0% 0% 0% 0%
plugin/src/label-summarizer.ts 0% 0% 0% 0%
plugin/src/log.ts 0% 0% 0% 0%
plugin/src/plugin.ts 0% 0% 0% 0%
plugin/src/project-picker.ts 0% 0% 0% 0%
plugin/src/project-scanner.ts 0% 0% 0% 0%
plugin/src/timeline-store.ts 0% 0% 0% 0%
plugin/src/voice-local.ts 0% 0% 0% 0%
plugin/src/actions/iterm-dial.ts 0% 0% 0% 0%
plugin/src/actions/mode-button.ts 0% 0% 0% 0%
plugin/src/actions/option-dial.ts 0% 0% 0% 0%
plugin/src/actions/response-button.ts 0% 0% 0% 0%
plugin/src/actions/session-button.ts 0% 0% 0% 0%
plugin/src/actions/stop-button.ts 0% 0% 0% 0%
plugin/src/actions/usage-button.ts 0% 0% 0% 0%
plugin/src/actions/utility-dial.ts 0% 0% 0% 0%
plugin/src/actions/voice-dial.ts 0% 0% 0% 0%
plugin/src/utility-modes/brightness.ts 0% 0% 0% 0%
plugin/src/utility-modes/darkmode.ts 0% 0% 0% 0%
plugin/src/utility-modes/diag.ts 0% 0% 0% 0%
plugin/src/utility-modes/index.ts 0% 0% 0% 0%
plugin/src/utility-modes/macos.ts 0% 0% 0% 0%
plugin/src/utility-modes/media.ts 0% 0% 0% 0%
plugin/src/utility-modes/mic.ts 0% 0% 0% 0%
plugin/src/utility-modes/timer.ts 0% 0% 0% 0%
plugin/src/utility-modes/types.ts 0% 0% 0% 0%
plugin/src/utility-modes/volume.ts 0% 0% 0% 0%
plugin/src/layout-manager.ts 65% 64% 62% 66%
plugin/src/renderers/timeline-renderer.ts 62% 37% 79% 67%
plugin/src/renderers/button-renderer.ts 82% 72% 100% 82%
plugin/src/renderers/response-renderer.ts 85% 40% 92% 87%
plugin/src/renderers/voice-renderer.ts 88% 57% 87% 90%
plugin/src/renderers/option-renderer.ts 92% 69% 100% 93%
plugin/src/connection-manager.ts 90% 70% 94% 94%
plugin/src/renderers/iterm-renderer.ts 95% 72% 100% 97%
plugin/src/renderers/utility-renderer.ts 98% 57% 100% 98%
plugin/src/renderers/qr-renderer.ts 98% 90% 80% 98%
plugin/src/renderers/agent-logos.ts 100% 100% 100% 100%
plugin/src/renderers/text-utils.ts 92% 81% 100% 100%
shared/src/adapter.ts 0% 100% 100% 0%
shared/src/index.ts 0% 0% 0% 0%
shared/src/net-utils.ts 0% 0% 0% 0%
shared/src/timeline-summarizer.ts 0% 0% 0% 0%
shared/src/voice-paths.ts 0% 0% 0% 0%
shared/src/format-utils.ts 39% 39% 29% 39%
shared/src/timeline.ts 70% 68% 93% 76%
shared/src/protocol.ts 100% 100% 100% 100%
shared/src/states.ts 100% 100% 100% 100%