Skip to content

Commit 4726535

Browse files
authored
docs: add docs for starknet-signers (#638)
1 parent 3a5537a commit 4726535

File tree

5 files changed

+53
-1
lines changed

5 files changed

+53
-1
lines changed

starknet-signers/src/key_pair.rs

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,23 +6,29 @@ use starknet_core::{
66
};
77
use starknet_crypto::get_public_key;
88

9+
/// A ECDSA signing (private) key on the STARK curve.
910
#[derive(Debug, Clone)]
1011
pub struct SigningKey {
1112
secret_scalar: Felt,
1213
}
1314

15+
/// A ECDSA verifying (public) key on the STARK curve.
1416
#[derive(Debug, Clone)]
1517
pub struct VerifyingKey {
1618
scalar: Felt,
1719
}
1820

21+
/// Errors using an encrypted JSON keystore.
1922
#[cfg(not(target_arch = "wasm32"))]
2023
#[derive(Debug, thiserror::Error)]
2124
pub enum KeystoreError {
25+
/// The file path is invalid.
2226
#[error("invalid path")]
2327
InvalidPath,
28+
/// The decrypted secret scalar is not a valid private key.
2429
#[error("invalid decrypted secret scalar")]
2530
InvalidScalar,
31+
/// Upstream `eth-keystore` error propagated.
2632
#[error(transparent)]
2733
Inner(eth_keystore::KeystoreError),
2834
}
@@ -47,6 +53,7 @@ impl SigningKey {
4753
Self { secret_scalar }
4854
}
4955

56+
/// Constructs [`SigningKey`] directly from a secret scalar.
5057
pub const fn from_secret_scalar(secret_scalar: Felt) -> Self {
5158
Self { secret_scalar }
5259
}
@@ -92,28 +99,35 @@ impl SigningKey {
9299
Ok(())
93100
}
94101

102+
/// Gets the secret scalar in the signing key.
95103
pub const fn secret_scalar(&self) -> Felt {
96104
self.secret_scalar
97105
}
98106

107+
/// Derives the verifying (public) key that corresponds to the signing key.
99108
pub fn verifying_key(&self) -> VerifyingKey {
100109
VerifyingKey::from_scalar(get_public_key(&self.secret_scalar))
101110
}
102111

112+
/// Signs a raw hash using ECDSA for a signature.
103113
pub fn sign(&self, hash: &Felt) -> Result<Signature, EcdsaSignError> {
104114
ecdsa_sign(&self.secret_scalar, hash).map(|sig| sig.into())
105115
}
106116
}
107117

108118
impl VerifyingKey {
119+
/// Constructs [`VerifyingKey`] directly from a scalar.
109120
pub const fn from_scalar(scalar: Felt) -> Self {
110121
Self { scalar }
111122
}
112123

124+
/// Gets the scalar in the verifying key.
113125
pub const fn scalar(&self) -> Felt {
114126
self.scalar
115127
}
116128

129+
/// Verifies that an ECDSA signature is valid for the verifying key against a certain message
130+
/// hash.
117131
pub fn verify(&self, hash: &Felt, signature: &Signature) -> Result<bool, EcdsaVerifyError> {
118132
ecdsa_verify(&self.scalar, hash, signature)
119133
}

starknet-signers/src/ledger.rs

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,18 +37,29 @@ pub struct LedgerStarknetApp {
3737
transport: Ledger,
3838
}
3939

40+
/// Errors using the Ledger hardware wallet.
4041
#[derive(Debug, thiserror::Error)]
4142
pub enum LedgerError {
43+
/// The HD wallet derivation path is malformed or does not conform to EIP-2645.
4244
#[error("derivation path is empty, not prefixed with m/2645', or is not 6-level long")]
4345
InvalidDerivationPath,
46+
/// Error communicating with the Ledger hardware device.
4447
#[error(transparent)]
4548
TransportError(coins_ledger::LedgerError),
49+
/// An unknown response code is returned from the device.
4650
#[error("unknown response code from Ledger: {0}")]
4751
UnknownResponseCode(u16),
52+
/// The response code returned from the device does not indicate success.
4853
#[error("failed Ledger request: {0}")]
4954
UnsuccessfulRequest(APDUResponseCodes),
55+
/// The response has an unexpected size.
5056
#[error("unexpected response length - expected: {expected}; actual: {actual}")]
51-
UnexpectedResponseLength { expected: usize, actual: usize },
57+
UnexpectedResponseLength {
58+
/// The expected response size.
59+
expected: usize,
60+
/// The actual response size.
61+
actual: usize,
62+
},
5263
}
5364

5465
/// The `GetPubKey` Ledger command.

starknet-signers/src/lib.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,7 @@
1+
//! Starknet signer interface and common implementations.
2+
3+
#![deny(missing_docs)]
4+
15
mod key_pair;
26
pub use key_pair::{SigningKey, VerifyingKey};
37

@@ -7,13 +11,17 @@ pub use key_pair::KeystoreError;
711
mod signer;
812
pub use signer::Signer;
913

14+
/// Module containing types related to the use of a simple in-memory signer.
1015
pub mod local_wallet;
1116
pub use local_wallet::LocalWallet;
1217

18+
/// Module containing types related to the Ledger hardware wallet.
1319
#[cfg(feature = "ledger")]
1420
pub mod ledger;
1521
#[cfg(feature = "ledger")]
1622
pub use ledger::{DerivationPath, LedgerError, LedgerSigner};
1723

24+
/// An error type that indicates an error cannot possibly occur. Used as placeholder where
25+
/// [`Result`] is expected.
1826
#[derive(Debug, thiserror::Error)]
1927
pub enum Infallible {}

starknet-signers/src/local_wallet.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,18 +6,23 @@ use starknet_core::{
66
types::Felt,
77
};
88

9+
/// A signer that simply holds the signing (private) key in memory for performing cryptographic
10+
/// operations. It's recommended to use hardware-based signers for use cases involving real value.
911
#[derive(Debug, Clone)]
1012
pub struct LocalWallet {
1113
private_key: SigningKey,
1214
}
1315

16+
/// Errors using [`LocalWallet`].
1417
#[derive(Debug, thiserror::Error)]
1518
pub enum SignError {
19+
/// ECDSA signature error.
1620
#[error(transparent)]
1721
EcdsaSignError(EcdsaSignError),
1822
}
1923

2024
impl LocalWallet {
25+
/// Constructs [`LocalWallet`] from a [`SigningKey`].
2126
pub fn from_signing_key(key: SigningKey) -> Self {
2227
key.into()
2328
}

starknet-signers/src/signer.rs

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,15 +5,29 @@ use auto_impl::auto_impl;
55
use starknet_core::{crypto::Signature, types::Felt};
66
use std::error::Error;
77

8+
/// Any signer that can provide a public key as [`Felt`], and sign a raw hash for a signature
9+
/// encoded as [`Vec<Felt>`].
810
#[cfg_attr(not(target_arch = "wasm32"), async_trait)]
911
#[cfg_attr(target_arch = "wasm32", async_trait(?Send))]
1012
#[auto_impl(&, Box, Arc)]
1113
pub trait Signer {
14+
/// Possible errors for calling [`get_public_key`](fn.get_public_key).
1215
type GetPublicKeyError: Error + Send + Sync;
16+
/// Possible errors for calling [`sign`](fn.sign).
1317
type SignError: Error + Send + Sync;
1418

19+
/// Retrieves the verifying (public) key from the signer.
1520
async fn get_public_key(&self) -> Result<VerifyingKey, Self::GetPublicKeyError>;
1621

22+
/// Requests an ECDSA signature for a message hash.
23+
///
24+
/// Signing a raw hash is known as "blind signing". For interactive signers (e.g. hardware
25+
/// wallets) that can theoretically provide better security properties via "clear signing",
26+
/// using blind signing is bad practice.
27+
///
28+
/// However, as of this writing, no actual interactive signer implementation offers clear
29+
/// signing. When this changes in the future, this trait shall be altered to allow such clear
30+
/// signing capabilities.
1731
async fn sign_hash(&self, hash: &Felt) -> Result<Signature, Self::SignError>;
1832

1933
/// Whether the underlying signer implementation is interactive, such as a hardware wallet.

0 commit comments

Comments
 (0)