Skip to content

Refresh an issuer value when the issuer orders it - #46

Merged
czpython merged 1 commit into
mainfrom
dru-481-refresh-order
Sep 7, 2026
Merged

Refresh an issuer value when the issuer orders it#46
czpython merged 1 commit into
mainfrom
dru-481-refresh-order

Conversation

@czpython

@czpython czpython commented Sep 7, 2026

Copy link
Copy Markdown
Owner

What changes

  • POST /refresh/{host_id}/{service} on the exchange. An issuer that ends a value before its expiry, as an OAuth provider does when it revokes the previous token at a refresh, orders a refresh. The exchange forgets the held value, fetches now, and on a provider that holds the value pushes at once.
  • Secrets.refresh replaces the entry's RefreshableSecret with a fresh one and runs the existing push or refresh on it, so the retry wait and the push bookkeeping stay the code they are. It raises IssuerUnavailableError when nothing valid came back.
  • Answers: 200 after the refresh and the push. 503 with Retry-After: 5 when the issuer gave nothing usable or the push failed, and the entry then waits as after any failed fetch. 404 for an unknown host or service. 409 for a static entry. The route logs the host and the service, never a value.
  • Tests: a proxy entry serves the new value on the next /authorize with no wait, an sbx entry gets the new value pushed at once and the timer finds it fresh afterwards, a failed fetch answers 503 and the next request waits out the retry delay, a failed push answers 503 and logs no value, an unknown host or service, and a static entry.
  • docs/api.md lists the exchange's endpoints. docs/security.md states the order's trust: no value, no token, one fetch at most. docs/architecture.md describes the flow.

Where this differs from the ticket

  • Nothing. Secrets.current and the push timer are unchanged.

Names

Secrets.refresh, beside current and push. The route is refresh, the word the exchange already uses for the act.

Gates

uv run ruff check, uv run ruff format --check, uv run pyright, and uv run pytest are green, 680 tests.

Review

Pending.

🤖 Generated with Claude Code

An issuer can end a value before its expiry, as an OAuth provider does when
it revokes the previous token at a refresh. POST /refresh/<host id>/<service>
makes the exchange forget the held value, fetch now, and push at once where
the provider holds the value. 503 with Retry-After when the issuer gives
nothing usable, 404 for an unknown entry, 409 for a static one.

The exchange's current, push, and refresh take the host row and resolve the
provider from host.provider, the way the hosts service does.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
@czpython
czpython force-pushed the dru-481-refresh-order branch from 5546671 to 70d00ec Compare September 7, 2026 13:22
@czpython
czpython merged commit 574332d into main Sep 7, 2026
11 of 12 checks passed
@czpython
czpython deleted the dru-481-refresh-order branch September 7, 2026 13:25
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