Skip to content

fix(state): report real counts in state show - #2520

Open
Bella-rab wants to merge 2 commits into
vercel-labs:mainfrom
Bella-rab:fix/state-show-summary-contract
Open

Bella-rab wants to merge 2 commits into
vercel-labs:mainfrom
Bella-rab:fix/state-show-summary-contract

Conversation

@Bella-rab

@Bella-rab Bella-rab commented Nov 10, 2026 •

Copy link
Copy Markdown

Summary

state show reports the wrong summary in both output modes.

The daemon built summary as a preformatted string ("12 cookies, 3 origins"), but the CLI read summary.cookies and summary.origins as numbers. Those lookups always returned None, so every state file printed Cookies: 0 and Origins with localStorage: 0 regardless of its contents.

While verifying, the text path turned out to be wrong for a second reason. A state-show payload carries filename and path, and the download formatter claims any payload with those fields. It runs earlier in print_primary_response, so state show printed a completed-download line and never reached the summary at all:

$ agent-browser state show my-session-default.json
✓ Downloaded to /home/user/.agent-browser/sessions/my-session-default.json (my-session-default.json)

Changes

  • cli/src/native/state.rs: summary is now an object with cookies and origins counts. That matches the shape doctor already uses and what the CLI was written to read.
  • cli/src/output.rs: the summary is extracted into format_state_show_text, and the state_show branch moves ahead of the generic path/filename branches. A preformatted string summary is still rendered, so a CLI pointed at an older daemon keeps working.

Verification

Built the binary and ran it against a fixture holding 2 cookies and 1 origin.

Before:

✓ Downloaded to ...\fixture.json (fixture.json)

After:

State file summary:
  Cookies: 2
  Origins with localStorage: 1

--json now returns "summary":{"cookies":2,"origins":1}.

Tests:

  • cargo test --bin agent-browser format_state_show (5 passed), covering count rendering, the encrypted marker, a legacy string summary, the non-state payload, and the payload that used to match the download branch.
  • cargo test --bin agent-browser state:: (19 passed), including a new daemon-side test that keeps summary structured.
  • cargo test --bin agent-browser: 1918 passed, 4 failed. The 4 failures are pre-existing on Windows and unrelated to this change: install::tests::download_bytes_connection_refused_includes_details and session_settings::tests::* assert a localized error string and /path separators, and native::tab_binding::tests::test_pinned_owner_dead_or_missing_pid_is_free shells out to ps. The same 4 failed before this change.
  • cargo fmt -- --check is clean.

Why the contract changed on the daemon side

Fixing only the CLI would have left --json consumers reading a sentence where they expect counts. The object shape is the one the CLI already assumed and the one doctor returns, so the daemon is the side that drifted.

Note

I did not find an open issue for this specific report. #2455 is a different state list problem (a blank modification date) and is already claimed by #2457.

Follow-up commit

74c31ee moves the new daemon-side test onto tempfile::tempdir(), matching the other tests in that module. process::id() is constant within the test binary, so the previous fixed filename could collide between tests and survive a panic.

state_show returned a preformatted summary string while the CLI read summary.cookies and summary.origins as numbers, so every file reported 0 cookies and 0 origins. Return the counts as an object instead, matching the summary shape doctor already uses.

The same payload also carries filename and path, which the download formatter claims first, so state show printed a completed-download line instead of the summary. Render the summary before the generic path branches and keep the preformatted string working for older daemons.
@vercel

vercel Bot commented Nov 10, 2026

Copy link
Copy Markdown
Contributor

@Bella-rab is attempting to deploy a commit to the Vercel Labs Team on Vercel.

A member of the Team first needs to authorize it.

Other tests in this module build fixtures under tempfile::tempdir(). process::id() is constant within the test binary, so the previous name could collide between tests and leave the file behind on failure.

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant