hermes-agent/apps/desktop/e2e
张豪杰 1535c114c9 test(desktop): cover connection.json owner-only mode end to end
The helpers were tested; nothing proved main.ts called them. Reverting both
call sites and both imports in readDesktopConnectionConfig /
writeDesktopConnectionConfig left the whole suite green (947 passed / 2
skipped, tsc 0, eslint clean, e2e 1 passed 1 skipped) while connection.json
went back to 0644 — the user-visible fix this PR promises was untested.

The e2e spec could not catch it by construction: it asserts the ENCRYPTION
contract with a raw-bytes scan, and safeStorage keeps the token opaque
regardless of the file's mode, so a 0644 file passes that scan every time.
There was no mode assertion anywhere in e2e/.

Adds the missing third contract — unreadable by other local accounts — on all
three paths that can produce the file:

- write: assert the mode of the artifact test 1 already proves the app wrote.
- read, valid file: seed the app's own encrypted connection.json back to 0644
  and assert launch tightens it. Scoped to the MODE only, so it is independent
  of the still-deferred plaintext migration — the fixture's token is already
  ciphertext, so nothing re-encrypts, no #62319 opt-in marker is involved, and
  no rotation guidance is owed.
- read, corrupt file: a truncated file still holds the token bytes and throws
  into the swallowing catch, so it would be the one file never tightened. This
  is the only test that distinguishes the chmod's placement relative to the
  parse.

Also moves the tighten above JSON.parse for exactly that reason, and pins the
cache invariant the placement depends on: the tighten must be a chmod, not a
rewrite, because it sits inside the function whose cache keys on mtimeMs.

Asserted as `mode & 0o077 === 0` rather than `=== 0o600` to avoid a
change-detector, and skipped on win32, where chmod maps to the read-only bit
and the fix deliberately no-ops (ACLs are PR #77527).

Every assertion was mutation-tested: reverting the full wiring fails all three;
reverting only the write path fails only the write test; deleting only the
tighten-on-read fails only the two read tests; moving the tighten below the
parse fails only the corrupt test; making the tighten a rewrite instead of a
chmod fails the mtime assertions. Bundle greps confirmed each mutation reached
dist/electron-main.mjs before the run.

(cherry picked from commit 99cfc16e7c)
2026-08-12 22:38:17 -07:00
..
at-rest-connection-token.spec.ts
boot-failure.spec.ts
boot.spec.ts
chat.spec.ts
correction-session-switch.spec.ts
fix-electron-tracing.ts
fixtures.ts
hidden-history-messages.spec.ts
image-attachment-resume.spec.ts
interim-messages.spec.ts
large-session-resume.spec.ts
launch-packaged-app.spec.ts
mock-backend-setup.spec.ts
mock-server.ts
onboarding.spec.ts
queue-turn-boundary.spec.ts
real-session-builder.ts
right-pane.spec.ts
session-compression-and-queue-stop.spec.ts
sidebar-states.spec.ts
submit-drift.spec.ts
test.ts
tile-unread-bug.spec.ts
visual-snapshot.ts
warm-resume-jitter.spec.ts
worktree-branch-status.spec.ts