Skip to content

feat: verify Sr25519 wallet login signatures (ADR-014 §3 follow-up) - #84

Merged
flo2517 merged 1 commit into
mainfrom
feat/issue-76-sr25519-wallet-login
Aug 7, 2026
Merged

feat: verify Sr25519 wallet login signatures (ADR-014 §3 follow-up)#84
flo2517 merged 1 commit into
mainfrom
feat/issue-76-sr25519-wallet-login

Conversation

@flo2517

@flo2517 flo2517 commented Aug 7, 2026

Copy link
Copy Markdown
Owner

Closes the Sr25519 gap ADR-014 explicitly flagged as a tracked follow-up: most real Polkadot.js-generated accounts default to Sr25519, not Ed25519, so wallet login was only verifiable for a minority of real accounts until now. This is part of #76 — leaves the rest of #76's scope (wallet-extension client integration, operator/validator dashboard views, RBAC, pagination, accessibility, E2E tests) open.

internal/walletlogin/sr25519.go

verifySr25519 checks a signature via github.com/ChainSafe/go-schnorrkel, using Substrate's own standard signing context (signing_context(b"substrate") — the same constant sr25519::Pair::sign and every wallet built on that stack, including Polkadot.js's extension signRaw, already use for raw message signing). Not an OpenInfra-specific choice — must match what a real wallet already produces.

Login now accepts both SchemeEd25519 and SchemeSr25519; a genuinely unrecognized scheme value still returns ErrSchemeNotSupported.

Tests

sr25519_test.go proves round-trip correctness against go-schnorrkel's own sign/verify. walletlogin_test.go and internal/dashboard/auth_test.go both gain full happy-path tests with a real Schnorrkel-signed challenge, at the service and HTTP layers respectively. The previous "unsupported scheme" HTTP test (which used to test Sr25519 specifically) now uses a genuinely unrecognized scheme value.

Verified

gofmt -l .; go build ./...; go vet ./...; go test ./... -count=1 — full workspace green against live Postgres/Redis.

Known gap (disclosed in ADR-014's implementation note)

The signing-context constant is Substrate's well-established public convention, proven correct against go-schnorrkel's own round trip, but not cross-checked against a signature from a real wallet extension — none reachable in this sandbox. The browser UI doesn't offer Sr25519 login yet either way (only the Ed25519 local-key fallback) — that needs wallet-extension integration, still open.

🤖 Generated with Claude Code

Co-Authored-By: Claude Sonnet 5 noreply@anthropic.com

Closes the Sr25519 gap ADR-014 explicitly flagged as a tracked
follow-up: most real Polkadot.js-generated accounts default to
Sr25519, not Ed25519, so wallet login was only verifiable for a
minority of real accounts until now.

internal/walletlogin/sr25519.go: verifySr25519 checks a signature via
github.com/ChainSafe/go-schnorrkel, using Substrate's own standard
signing context (signing_context(b"substrate") -- the same constant
sr25519::Pair::sign and every wallet built on that stack, Polkadot.js's
extension signRaw included, already use for raw message signing, as
opposed to extrinsic signing which uses a different transcript). This
is not an OpenInfra-specific choice: it must match what a real wallet
already produces.

Login now accepts both SchemeEd25519 and SchemeSr25519, dispatching to
the scheme-appropriate verifier; a scheme value that is neither still
returns ErrSchemeNotSupported, unchanged for that genuinely-unknown
case.

Tests: sr25519_test.go proves round-trip correctness against
go-schnorrkel's own sign/verify (accepts a genuine signature, rejects
a wrong key, a tampered message, and malformed/undersized input).
walletlogin_test.go gains a full Login() happy-path test with a real
Schnorrkel-signed challenge. internal/dashboard/auth_test.go gains the
same at the HTTP layer (challenge -> Sr25519-signed login -> session
key), and its previous "unsupported scheme" test (which used to test
Sr25519 specifically) now uses a genuinely unrecognized scheme value
instead, since Sr25519 is no longer the unsupported case.

Verified (control-plane/): gofmt -l .; go build ./...; go vet ./...;
go test ./... -count=1 -- full workspace green against live Postgres/
Redis.

Known gap, disclosed explicitly in ADR-014's implementation note: the
signing-context constant is Substrate's well-established public
convention and has been proven correct against go-schnorrkel's own
round trip, but has not been cross-checked against a signature
produced by a real wallet extension in this sandbox -- no such
extension is reachable here. The browser UI doesn't offer Sr25519
login yet either way (it only has the Ed25519 local-key fallback);
that needs wallet-extension integration, a separate, still-open piece
of #76.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
@flo2517
flo2517 merged commit 7420d60 into main Aug 7, 2026
4 checks passed
@flo2517
flo2517 deleted the feat/issue-76-sr25519-wallet-login branch August 7, 2026 09:36
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.

2 participants