Skip to main content
Package: monaco.api.auth Source: protos/api/auth.proto Use AuthService to create wallet challenges, verify wallet signatures, refresh sessions, and revoke sessions.

Notes

  • Challenge binds the ed25519 session public key into the wallet-signed message. The challenge is single-use and authorizes exactly one keypair, once. It lives 5 minutes, or 30 minutes on a deployment where contract-signature login is enabled, because a multisig has to collect owner approvals before it can answer — that window is uniform for every address rather than eligibility-specific, so this unauthenticated RPC cannot be used to probe which addresses hold a BuilderCodes payout bucket. Read expires_at rather than assuming either value.
  • Verify opens the signed session. There is no access token — the session is the registered public key. signature carries whatever the wallet produced and is bounded at 8192 decoded bytes: anything longer is refused as UNAUTHENTICATED rather than forwarded to the chain. The bound is far above any realistic owner set, and EOA signatures never approach it.
  • VerifyResponse carries two signup signals alongside expires_at and user. Both are scoped per (wallet, application) — identity is created per application, so a wallet already registered on another application still sees them on its first sign-in to a new one. is_new_user is true when this verify created the user row (the wallet’s first sign-in to this application). referral_applied is true when a PitPass referral relationship was recorded on this verify — a valid, non-self TraderCode presented on that first sign-in resolved to a known referrer. Both are false on every returning verify for the application. Use is_new_user to gate first-time UX and referral_applied to confirm a referral landed.
  • Challenge and Verify share one rate budget per client address — 60 requests/min sustained, burst 120 by default, on public ingress — and return RESOURCE_EXHAUSTED over it once enforcement is on. Enforcement is gated by auth_rate_limit_enforced, which defaults off; until it flips, an over-budget request is admitted with a warn log rather than rejected. Both figures are deployment defaults, overridden by AUTH_RATE_LIMIT_PER_MINUTE / AUTH_RATE_LIMIT_BURST, so treat the environment’s own budget as authoritative. The check runs before the signature, so a throttled request is never an authentication failure.
  • Verify returns ALREADY_EXISTS (“resource already exists”) when the session public key it is asked to bind is already registered — the key is stored under a unique constraint, and the violation maps to that status. Do not retry with the same keypair: generate a fresh session keypair and start a new challenge. The high-level login() flow generates one per call, so this only reaches callers driving Challenge / Verify themselves.
  • Both RPCs also return INVALID_ARGUMENT for invalid request parameters (on Verify, that includes a nonce already used or expired), PERMISSION_DENIED when the origin is not allowed for this application, NOT_FOUND for an invalid client_id or nonce, and INTERNAL for a server-side failure.
  • Verify returns UNAVAILABLE when contract-signature (EIP-1271) verification of an eligible address could not be completed: the chain did not answer, did not answer within the deadline, or the server was at its concurrent-verification capacity and declined to ask. It is retryable and is not a verdict on the signature — a rejected signature is UNAUTHENTICATED, and so is a wallet contract that rejects by reverting. An eligible address can see it even when it turns out to be an EOA, because the code lookup precedes the choice of verification path; addresses that are not eligible never reach the chain. A fourth trigger is unrelated to contract wallets: Verify reads private-beta feature-flag state before anything else, and a read that cannot be served surfaces as the same retryable UNAVAILABLE, for any address, ahead of any signature or eligibility work.
  • Authenticated RPCs are signed per request over the prost-encoded body. See authenticated gRPC for the metadata names, canonical signing string, session expiry/refresh, and a runnable signed example, or TypeScript authentication for the same session-key model in the SDK.