mirror of
https://github.com/ruvnet/RuView
synced 2026-07-22 17:23:19 +00:00
6d3fb88677
Two gaps that only appear with a credential file written by an earlier build —
i.e. exactly the case a fresh-login test never exercises.
1. `whoami` printed "Scope: (not reported)" for an existing file. The previous
commit resolved scope from the token claim at WRITE time only, so files
written before it stayed blank forever. `effective_scope()` now falls back at
READ time, which fixes existing files and any client that stored only what
the token response carried. The token is authoritative either way; the stored
field is a convenience copy.
2. `whoami` said the token "will refresh on next use" — a promise nothing kept,
because no command called `ensure_fresh`. The refresh path was implemented
and unit-tested but never actually run. `--refresh` exercises it, and goes
through `Session::ensure_fresh` rather than reimplementing a second, subtly
different refresh, so it inherits the single-flight guarantee and the
persist-before-return ordering.
It is a flag, not silent behaviour: refreshing rotates the stored refresh
token — identity spends the old one — so it is a state change, not a read.
VERIFIED AGAINST PRODUCTION, end to end:
whoami on a pre-existing file -> Scope: sensing:read (was "not reported")
whoami --refresh -> both tokens rotated
refresh sha256[:12] 50cfa06b -> 2d37617a
access sha256[:12] 61eebe8d -> 14d8e8de
status: expired -> valid
refreshed token GET /api/v1/models -> 200
refreshed token POST /api/v1/train/start -> 401 (still read-scoped)
That exercises the rotating-refresh path against identity's real reuse
detection — the one place a bug costs the user their session rather than a
retry — and confirms the scope gate survives a refresh.
Tests: 82 with --features login, 44 default, 501 sensing-server.
Co-Authored-By: Ruflo & AQE