Which signature schemes does Sui support?
November 3, 2026
Sui user accounts can sign with three key schemes: Ed25519, ECDSA Secp256k1 and ECDSA Secp256r1. Sui also has three more ways to authorize a transaction: multisig, zkLogin (OAuth login backed by a zero-knowledge proof) and passkeys (WebAuthn). Each scheme has a 1-byte flag. The flag goes into the address hash, so the same public key gives a different address under a different scheme.
The flags
| Flag | Scheme | Notes |
|---|---|---|
0x00 |
Ed25519 | The most common choice for wallets and the CLI |
0x01 |
ECDSA Secp256k1 | The same curve as Bitcoin and Ethereum |
0x02 |
ECDSA Secp256r1 | NIST P-256; secure enclaves and HSMs |
0x03 |
MultiSig | k-of-n over weighted member keys |
0x04 |
BLS12-381 | Validators only; not allowed for user addresses |
0x05 |
zkLogin | OAuth (OpenID) login with a Groth16 proof |
0x06 |
Passkey | WebAuthn, secp256r1 inside |
0x07 |
ML-DSA-65 | Post-quantum; enabled on devnet only |
These values come from SignatureScheme::flag() in crates/sui-types/src/crypto.rs. An address is BLAKE2b-256(flag || public_key). See How are Sui addresses derived from keys?.
What a signature looks like
For the three key schemes, a serialized user signature is flag || signature || public_key, Base64-encoded. What gets signed is the BLAKE2b-256 hash of the intent message: a 3-byte intent prefix ([0, 0, 0] for transactions) followed by the BCS transaction data. Intent prefixes prevent a transaction signature from being reused as a personal-message signature, and the reverse.
You can parse any of these signatures in TypeScript:
import { parseSerializedSignature } from '@mysten/sui/cryptography'
const parsed = parseSerializedSignature(signatureBase64)
console.log(parsed.signatureScheme) // 'ED25519' | 'Secp256k1' | 'Secp256r1' | 'MultiSig' | 'ZkLogin' | 'Passkey' | ...Choosing a scheme
- Ed25519: fast, deterministic and the most widely used. It's the right choice unless you have a reason to pick another.
- Secp256k1: useful when the key lives in a signer that only supports secp256k1, such as some custody systems or hardware.
- Secp256r1: supported by Apple Secure Enclave, Android Keystore, cloud KMS and HSMs.
- Multisig: for treasuries and for holding admin caps such as
UpgradeCap. Members can mix the schemes above, and on mainnet they can also be zkLogin and passkey signers. See How do multisig accounts work on Sui?. - zkLogin: lets users sign in with Google, Apple and other OpenID providers, with no seed phrase. See What is zkLogin?.
- Passkey: lets users sign with Face ID, Touch ID or a security key through WebAuthn. See How do passkeys work on Sui?.
About ML-DSA-65
ML-DSA-65 is the FIPS 204 post-quantum signature scheme. The Sui codebase supports it as flag 0x07, and @mysten/sui has a keypairs/mldsa65 module. The protocol config enables it (feature flag mldsa65_auth) only on chains other than mainnet and testnet, which means devnet and local networks. As of epoch 1291 (2026-10-25), mainnet runs protocol version 139 and doesn't accept ML-DSA-65 signatures. Check the current state with GraphQL:
{ epoch { epochId protocolConfigs { protocolVersion featureFlag(key: "mldsa65_auth") { value } } } }If featureFlag returns null or false, the scheme isn't enabled.
Verifying signatures inside Move
Move contracts can verify more schemes than accounts can sign with. The sui::ed25519, sui::ecdsa_k1, sui::ecdsa_r1 and sui::bls12381 modules verify signatures over arbitrary messages, which is useful for oracles or off-chain attestations. That is separate from transaction authorization.
Sources
- Keys and addresses, Sui documentation
- Offline signing, Sui documentation
- Signature verification in Move, Sui documentation
crates/sui-types/src/crypto.rs, MystenLabs/suicrates/sui-protocol-config/src/lib.rs, MystenLabs/sui