Skip to content

Add SLH-DSA-SHA2-128s (post-quantum) signature support to v2 - #142

Open
gregnazario wants to merge 1 commit into
mainfrom
greg/pq-slh-dsa-python-8a3c
Open

gregnazario wants to merge 1 commit into
mainfrom
greg/pq-slh-dsa-python-8a3c

Conversation

@gregnazario

Copy link
Copy Markdown
Contributor

Description

Adds SLH-DSA-SHA2-128s (post-quantum, AIP-137) signature support to the v2 SDK (aptos_sdk_v2, mirrored to aptos_sdk/v2), mirroring aptos-ts-sdk#802:

  • New crypto/slh_dsa_sha2_128s.py — SlhDsaSha2128sPrivateKey (48-byte three-seeds value, as in the TS SDK), SlhDsaSha2128sPublicKey (32 bytes), SlhDsaSha2128sSignature (7,856 bytes), with BCS (de)serialization, generate(), from_str/from_hex, and TS-compatible from_derivation_path / from_derivation_path_inner.
  • Wire formats match TS/on-chain exactly — AnyPublicKey variant 5, AnySignature variant 4 (new AnySignatureVariant, also fixing AnySignature previously reusing AnyPublicKeyVariant), AIP-80 prefix slh-dsa-sha2-128s-priv- (including a fix to parse_hex_input so multi-hyphen prefixes parse), SingleKey authentication scheme (0x02) for address derivation.
  • Accounts & transactions — Account.generate_slh_dsa_sha2_128s(), Account.from_mnemonic(..., slh_dsa_sha2_128s=True), derive_slh_dsa_sha2_128s_private_key() (custom SLIP-0010 "SLH-DSA-SHA2-128s seed" HMAC derivation, hardened-only), simulated signing support. Single-sender, multi-agent, and fee-payer flows work unchanged through SingleKeyAuthenticator.
  • Dependency choice — signing/verification use the optional pqcrypto package (PQClean C bindings, abi3 wheels for Linux/macOS/Windows): pip install "aptos-sdk-v2[slh-dsa-sha2-128s]" (also declared on the root package for the aptos_sdk.v2 mirror). This mirrors the TS SDK's optional @noble/post-quantum. Public-key derivation from the 48-byte seed (XMSS root, FIPS 205 SHA2 instantiation) is standard-library only, so key handling, BCS, and address derivation work without the optional dependency; sign/verify raise an actionable ImportError when it is missing. Alternatives considered: slh-dsa (pure-Python/mypyc; ~1.7s per signature and no seeded key generation) — used here as an independent cross-check implementation instead; cryptography/PyNaCl do not expose SLH-DSA.
  • The legacy v1 API (aptos_sdk.ed25519 etc.) is intentionally unchanged; CHANGELOG, v2 README, and the different_key_types example are updated.

Test Plan

  • cd v2 && uv run pytest tests/unit -q — 457 passed (39 new in tests/unit/test_slh_dsa_sha2_128s.py), including:
    • HD-derivation vectors ported verbatim from aptos-ts-sdk PR #802 (hdKey.test.ts)
    • a fixed-seed public-key/signature vector cross-verified against two independent FIPS 205 implementations (pqcrypto/PQClean and the pure-Python slh-dsa): their signature verifies here and ours verifies there
    • BCS layout/round-trips, AIP-80 strings, SingleKey variant indices, account/address derivation, single-sender + multi-agent + fee-payer signed-transaction verification, missing-backend error
  • cd v2 && uv run ruff check src/ tests/ and uv run mypy src/ — clean; new modules at 99–100% coverage
  • Root make lint and make test (unittest + behave, 248 scenarios) — pass; .github/scripts/check_v2_sync.sh — OK
  • Not run: on-chain e2e (requires a node built with aptos-core#18300, same caveat as the TS PR) and the devnet example update

Related Links

Open in Web Open in Cursor 

Mirror aptos-ts-sdk PR #802 (AIP-137): 32-byte public keys, 48-byte
three-seeds private keys, 7,856-byte signatures, AnyPublicKey variant 5 /
AnySignature variant 4, AIP-80 slh-dsa-sha2-128s-priv- strings,
SingleKey address derivation, hardened SLIP-0010-style HD derivation,
Account.generate_slh_dsa_sha2_128s and mnemonic derivation.

Signing/verification use the optional pqcrypto dependency
(pip install "aptos-sdk-v2[slh-dsa-sha2-128s]"); public-key derivation
from the seed value is standard-library only, so key handling and BCS
work without it. Mirrored to aptos_sdk/v2 per the sync check.

Co-authored-by: greg <greg@gnazar.io>
@gregnazario
gregnazario requested a review from a team as a code owner October 29, 2026 17:53
@codecov

codecov Bot commented Oct 29, 2026 •

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 99.16318% with 2 lines in your changes missing coverage. Please review.
✅ Project coverage is 93.34%. Comparing base (39d59de) to head (198a630).

Files with missing lines Patch % Lines
v2/src/aptos_sdk_v2/crypto/mnemonic.py 88.23% 2 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main     #142      +/-   ##
==========================================
+ Coverage   93.07%   93.34%   +0.27%     
==========================================
  Files          56       57       +1     
  Lines        5239     5468     +229     
==========================================
+ Hits         4876     5104     +228     
- Misses        363      364       +1     
Flag Coverage Δ
v1-sdk 90.17% <ø> (ø)
v2-sdk 97.25% <99.16%> (+0.23%) ⬆️
Files with missing lines Coverage Δ
v2/src/aptos_sdk_v2/account/account.py 100.00% <100.00%> (ø)
v2/src/aptos_sdk_v2/crypto/__init__.py 100.00% <100.00%> (ø)
v2/src/aptos_sdk_v2/crypto/authentication_key.py 100.00% <100.00%> (+3.70%) ⬆️
v2/src/aptos_sdk_v2/crypto/keys.py 100.00% <100.00%> (ø)
v2/src/aptos_sdk_v2/crypto/single_key.py 100.00% <100.00%> (ø)
v2/src/aptos_sdk_v2/crypto/slh_dsa_sha2_128s.py 100.00% <100.00%> (ø)
...2/src/aptos_sdk_v2/transactions/raw_transaction.py 100.00% <100.00%> (ø)
v2/src/aptos_sdk_v2/crypto/mnemonic.py 95.71% <88.23%> (-2.40%) ⬇️
🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

This branch has not been deployed

No deployments
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