Browse Source

Merge pull request #62 from Relayz-io/silvestr/improve-keypair

Improve keypair API
develop
Predko Silvestr 3 years ago
parent
commit
e1d86bb6c8
No account linked to committer's email address

+ 26
- 12
.github/workflows/ci.yml View File

3
 env:
3
 env:
4
   CARGO_TERM_COLOR: always
4
   CARGO_TERM_COLOR: always
5
 
5
 
6
-on: 
6
+on:
7
   push:
7
   push:
8
     branches:
8
     branches:
9
       - main
9
       - main
23
       - name: Install Rust Toolchain
23
       - name: Install Rust Toolchain
24
         uses: actions-rs/toolchain@v1
24
         uses: actions-rs/toolchain@v1
25
         with:
25
         with:
26
-            toolchain: nightly
27
-            components: rustfmt
26
+          toolchain: nightly
27
+          components: rustfmt
28
       - name: cargo fmt
28
       - name: cargo fmt
29
         run: cargo +nightly fmt -- --check
29
         run: cargo +nightly fmt -- --check
30
   clippy:
30
   clippy:
36
       - name: Install Rust Toolchain
36
       - name: Install Rust Toolchain
37
         uses: actions-rs/toolchain@v1
37
         uses: actions-rs/toolchain@v1
38
         with:
38
         with:
39
-            toolchain: nightly
40
-            components: clippy
39
+          toolchain: nightly
40
+          components: clippy
41
       - name: cargo clippy
41
       - name: cargo clippy
42
-        run: cargo +nightly clippy --all --tests -- -D warnings
42
+        run: cargo +nightly clippy --workspace --tests -- -D warnings
43
       - name: Install wasm32-unknown-unknown
43
       - name: Install wasm32-unknown-unknown
44
         run: rustup +nightly target add wasm32-unknown-unknown
44
         run: rustup +nightly target add wasm32-unknown-unknown
45
       - name: cargo clippy for wasm32-unknown-unknown
45
       - name: cargo clippy for wasm32-unknown-unknown
46
-        run: cargo +nightly clippy --all --target wasm32-unknown-unknown -- -D warnings
46
+        run: cargo +nightly clippy --workspace --target wasm32-unknown-unknown -- -D warnings
47
   build:
47
   build:
48
     name: build
48
     name: build
49
     needs: [clippy, fmt]
49
     needs: [clippy, fmt]
53
       - name: Install Rust Toolchain
53
       - name: Install Rust Toolchain
54
         uses: actions-rs/toolchain@v1
54
         uses: actions-rs/toolchain@v1
55
         with:
55
         with:
56
-            toolchain: stable
56
+          toolchain: stable
57
       - name: Install wasm32-unknown-unknown
57
       - name: Install wasm32-unknown-unknown
58
         run: rustup target add wasm32-unknown-unknown
58
         run: rustup target add wasm32-unknown-unknown
59
-      - name: cargo build [wasm-client, near-client] for wasm
60
-        run: cargo build --all --target wasm32-unknown-unknown --release
61
-      - name: cargo build [near-client]
62
-        run: cargo build --all --release
59
+      - name: cargo build [web-client, near-client, common-api] for wasm
60
+        run: cargo build -p web-client -p near-client -p common-api --target wasm32-unknown-unknown --release
61
+      - name: cargo build [near-client, common-api]
62
+        run: cargo build -p near-client -p common-api --tests --release
63
+  tests:
64
+    name: tests
65
+    needs: [clippy, fmt]
66
+    runs-on: ubuntu-latest
67
+    steps:
68
+      - uses: actions/checkout@v3
69
+      - name: Install Rust Toolchain
70
+        uses: actions-rs/toolchain@v1
71
+        with:
72
+          toolchain: stable
73
+      - name: Run unit-tests for [common-api]
74
+        run: cargo test -p common-api crypto
75
+      - name: Run integration-tests for [common-api]
76
+        run: cargo test -p common-api --test crypto

+ 0
- 16
.github/workflows/issue-link.yml View File

1
-name: 'Issue Links'
2
-on:
3
-  pull_request:
4
-    types: [opened]
5
-
6
-jobs:
7
-  issue-links:
8
-    runs-on: ubuntu-latest
9
-    steps:
10
-      - uses: actions/checkout@v3
11
-      - uses: tkt-actions/add-issue-links@v1.8.0
12
-        with:
13
-          header: '### Issue'
14
-          repo-token: '${{ secrets.GITHUB_TOKEN }}'
15
-          resolve: 'true'
16
-          branch-prefix: '/'

+ 0
- 1
common-api/Cargo.toml View File

20
 x25519-dalek = { version = "1", features = ["serde"] }
20
 x25519-dalek = { version = "1", features = ["serde"] }
21
 
21
 
22
 [dev-dependencies]
22
 [dev-dependencies]
23
-anyhow = "1"
24
 rand = "0.8.5"
23
 rand = "0.8.5"
25
 rand_chacha = "0.3"
24
 rand_chacha = "0.3"

+ 58
- 6
common-api/src/crypto/ed25519.rs View File

10
     fmt::Display,
10
     fmt::Display,
11
     hash::{Hash, Hasher},
11
     hash::{Hash, Hasher},
12
     io::{Error as IoError, ErrorKind},
12
     io::{Error as IoError, ErrorKind},
13
+    str::FromStr,
13
 };
14
 };
14
 
15
 
15
 use super::{split_encoded_str, Error, Key, Result, ED25519};
16
 use super::{split_encoded_str, Error, Key, Result, ED25519};
16
 
17
 
17
 pub use ed25519_dalek::{
18
 pub use ed25519_dalek::{
18
-    PUBLIC_KEY_LENGTH as ED25519_PUBLIC_KEY_LENGTH, SECRET_KEY_LENGTH as ED25519_SECRET_KEY_LENGTH,
19
-    SIGNATURE_LENGTH as ED25519_SIGNATURE_LENGTH,
19
+    KEYPAIR_LENGTH as ED25519_KEYPAIR_LENGTH, PUBLIC_KEY_LENGTH as ED25519_PUBLIC_KEY_LENGTH,
20
+    SECRET_KEY_LENGTH as ED25519_SECRET_KEY_LENGTH, SIGNATURE_LENGTH as ED25519_SIGNATURE_LENGTH,
20
 };
21
 };
21
 
22
 
22
-#[derive(Copy, Clone, Default, Eq, PartialEq)]
23
+#[derive(Copy, Clone, Debug, Default, Eq, PartialEq)]
23
 pub struct Ed25519PublicKey(PublicKey);
24
 pub struct Ed25519PublicKey(PublicKey);
24
 
25
 
25
 impl Ed25519PublicKey {
26
 impl Ed25519PublicKey {
27
+    /// Verifies the signature of a signed data
26
     pub fn verify(&self, data: &[u8], signature: &Ed25519Signature) -> Result<()> {
28
     pub fn verify(&self, data: &[u8], signature: &Ed25519Signature) -> Result<()> {
27
         self.0
29
         self.0
28
             .verify(data, &signature.0)
30
             .verify(data, &signature.0)
95
 pub struct Ed25519SecretKey(SecretKey);
97
 pub struct Ed25519SecretKey(SecretKey);
96
 
98
 
97
 impl Ed25519SecretKey {
99
 impl Ed25519SecretKey {
100
+    /// Sign a `data` with a private key
98
     pub fn sign(&self, data: &[u8], public_key: &Ed25519PublicKey) -> Ed25519Signature {
101
     pub fn sign(&self, data: &[u8], public_key: &Ed25519PublicKey) -> Ed25519Signature {
99
         let expanded_key = ExpandedSecretKey::from(&self.0);
102
         let expanded_key = ExpandedSecretKey::from(&self.0);
100
         Ed25519Signature(expanded_key.sign(data, &public_key.0))
103
         Ed25519Signature(expanded_key.sign(data, &public_key.0))
156
     }
159
     }
157
 }
160
 }
158
 
161
 
159
-#[derive(Copy, Clone, Eq, PartialEq)]
162
+#[derive(Copy, Clone, Debug, Eq, PartialEq)]
160
 pub struct Ed25519Signature(Signature);
163
 pub struct Ed25519Signature(Signature);
161
 
164
 
162
 impl Key<ED25519_SIGNATURE_LENGTH> for Ed25519Signature {
165
 impl Key<ED25519_SIGNATURE_LENGTH> for Ed25519Signature {
207
     }
210
     }
208
 }
211
 }
209
 
212
 
213
+/// Contains public and secret user keys
210
 #[derive(Serialize, Deserialize)]
214
 #[derive(Serialize, Deserialize)]
211
 pub struct Keypair {
215
 pub struct Keypair {
212
     public_key: Ed25519PublicKey,
216
     public_key: Ed25519PublicKey,
222
         }
226
         }
223
     }
227
     }
224
 
228
 
225
-    pub fn from_encoded(encoded: &str) -> Result<Self> {
226
-        let secret_key = Ed25519SecretKey::from_expanded(encoded)?;
229
+    pub fn from_expanded_secret(expanded: &str) -> Result<Self> {
230
+        let secret_key = Ed25519SecretKey::from_expanded(expanded)?;
227
         let public_key = Ed25519PublicKey::from(&secret_key);
231
         let public_key = Ed25519PublicKey::from(&secret_key);
228
         Ok(Self {
232
         Ok(Self {
229
             public_key,
233
             public_key,
248
     }
252
     }
249
 }
253
 }
250
 
254
 
255
+impl ToString for Keypair {
256
+    fn to_string(&self) -> String {
257
+        let keypair_bytes = self
258
+            .secret_key()
259
+            .as_bytes()
260
+            .iter()
261
+            .chain(self.public_key().as_bytes().iter())
262
+            .copied()
263
+            .collect_vec();
264
+
265
+        format!("{ED25519}:{}", bs58::encode(keypair_bytes).into_string())
266
+    }
267
+}
268
+
269
+impl FromStr for Keypair {
270
+    type Err = Error;
271
+
272
+    fn from_str(s: &str) -> Result<Self> {
273
+        let (key_type, data) = split_encoded_str(s)?;
274
+
275
+        if key_type != ED25519 {
276
+            return Err(Error::WrongKeyType {
277
+                key_type: key_type.to_owned(),
278
+                expected_key_type: ED25519,
279
+            });
280
+        }
281
+
282
+        let byte_data = bs58::decode(data)
283
+            .into_vec()
284
+            .map_err(|err| Error::from_string::<Keypair>(data.to_owned(), err.to_string()))?;
285
+
286
+        if byte_data.len() != ED25519_KEYPAIR_LENGTH {
287
+            return Err(Error::from_bytes::<Keypair>(
288
+                &byte_data,
289
+                format!(
290
+                    "Keypair byte array length doesn't equal\
291
+                     to requested length {ED25519_KEYPAIR_LENGTH}"
292
+                ),
293
+            ));
294
+        }
295
+
296
+        Ok(Self {
297
+            secret_key: Ed25519SecretKey::try_from_bytes(&byte_data[..ED25519_SECRET_KEY_LENGTH])?,
298
+            public_key: Ed25519PublicKey::try_from_bytes(&byte_data[ED25519_SECRET_KEY_LENGTH..])?,
299
+        })
300
+    }
301
+}
302
+
251
 serde_impl!(Ed25519PublicKey);
303
 serde_impl!(Ed25519PublicKey);
252
 serde_impl!(Ed25519SecretKey);
304
 serde_impl!(Ed25519SecretKey);
253
 serde_impl!(Ed25519Signature);
305
 serde_impl!(Ed25519Signature);

+ 1
- 2
common-api/src/crypto/mod.rs View File

167
     use super::{split_encoded_str, Error, ED25519, X25519};
167
     use super::{split_encoded_str, Error, ED25519, X25519};
168
 
168
 
169
     #[test]
169
     #[test]
170
-    fn split_encoded() -> anyhow::Result<()> {
170
+    fn split_encoded() {
171
         let bs58_str = bs58::encode(vec![0, 0, 0]).into_string();
171
         let bs58_str = bs58::encode(vec![0, 0, 0]).into_string();
172
         assert!(matches!(
172
         assert!(matches!(
173
                 split_encoded_str(&format!("ed25519:{}", bs58_str)),
173
                 split_encoded_str(&format!("ed25519:{}", bs58_str)),
179
             split_encoded_str(&bs58_str),
179
             split_encoded_str(&bs58_str),
180
             Err(Error::UnknownKeyType(..))
180
             Err(Error::UnknownKeyType(..))
181
         ));
181
         ));
182
-        Ok(())
183
     }
182
     }
184
 }
183
 }

+ 84
- 70
common-api/tests/crypto.rs View File

1
+use std::str::FromStr;
2
+
1
 use borsh::BorshDeserialize;
3
 use borsh::BorshDeserialize;
2
 use common_api::crypto::prelude::*;
4
 use common_api::crypto::prelude::*;
3
 use ed25519_dalek::{ExpandedSecretKey, SecretKey as DalekSecretKey};
5
 use ed25519_dalek::{ExpandedSecretKey, SecretKey as DalekSecretKey};
5
 use rand_chacha::ChaChaRng;
7
 use rand_chacha::ChaChaRng;
6
 
8
 
7
 #[test]
9
 #[test]
8
-fn try_from_bytes_ed25519() -> anyhow::Result<()> {
9
-    let sk = Ed25519SecretKey::try_from_bytes(&random_bits())?;
10
+fn try_from_bytes_ed25519() {
11
+    let sk = Ed25519SecretKey::try_from_bytes(&random_bits()).unwrap();
10
     let pk = Ed25519PublicKey::from(&sk);
12
     let pk = Ed25519PublicKey::from(&sk);
11
-    let _ = Ed25519PublicKey::try_from_bytes(pk.as_bytes())?;
13
+    let _ = Ed25519PublicKey::try_from_bytes(pk.as_bytes()).unwrap();
12
 
14
 
13
     assert!(matches!(
15
     assert!(matches!(
14
         Ed25519PublicKey::try_from_bytes(&[0, 0, 0]),
16
         Ed25519PublicKey::try_from_bytes(&[0, 0, 0]),
19
         Ed25519SecretKey::try_from_bytes(&[0, 0, 0]),
21
         Ed25519SecretKey::try_from_bytes(&[0, 0, 0]),
20
         Err(Error::ConvertFromBytes { .. })
22
         Err(Error::ConvertFromBytes { .. })
21
     ));
23
     ));
22
-
23
-    Ok(())
24
 }
24
 }
25
 
25
 
26
 #[test]
26
 #[test]
27
-fn to_string_ed25519() -> anyhow::Result<()> {
28
-    let sk = Ed25519SecretKey::try_from_bytes(&random_bits())?;
27
+fn to_string_ed25519() {
28
+    let sk = Ed25519SecretKey::try_from_bytes(&random_bits()).unwrap();
29
     let pk = Ed25519PublicKey::from(&sk);
29
     let pk = Ed25519PublicKey::from(&sk);
30
 
30
 
31
     assert_eq!(
31
     assert_eq!(
36
         format!("ed25519:{}", bs58::encode(pk.as_bytes()).into_string()),
36
         format!("ed25519:{}", bs58::encode(pk.as_bytes()).into_string()),
37
         pk.string()
37
         pk.string()
38
     );
38
     );
39
-
40
-    Ok(())
41
 }
39
 }
42
 
40
 
43
 #[test]
41
 #[test]
44
-fn from_string_ed25519() -> anyhow::Result<()> {
45
-    let sk = Ed25519SecretKey::try_from_bytes(&random_bits())?;
42
+fn from_string_ed25519() {
43
+    let sk = Ed25519SecretKey::try_from_bytes(&random_bits()).unwrap();
46
     let pk = Ed25519PublicKey::from(&sk);
44
     let pk = Ed25519PublicKey::from(&sk);
47
 
45
 
48
     let _ = Ed25519SecretKey::from_string(
46
     let _ = Ed25519SecretKey::from_string(
49
         format!("ed25519:{}", bs58::encode(sk.as_bytes()).into_string()).as_str(),
47
         format!("ed25519:{}", bs58::encode(sk.as_bytes()).into_string()).as_str(),
50
-    )?;
48
+    )
49
+    .unwrap();
51
 
50
 
52
     let _ = Ed25519PublicKey::from_string(
51
     let _ = Ed25519PublicKey::from_string(
53
         format!("ed25519:{}", bs58::encode(pk.as_bytes()).into_string()).as_str(),
52
         format!("ed25519:{}", bs58::encode(pk.as_bytes()).into_string()).as_str(),
54
-    )?;
53
+    )
54
+    .unwrap();
55
 
55
 
56
     assert!(matches!(
56
     assert!(matches!(
57
         Ed25519PublicKey::from_string(
57
         Ed25519PublicKey::from_string(
83
         Ed25519PublicKey::from_string(format!("ed25519:{}", "==1234%#").as_str(),),
83
         Ed25519PublicKey::from_string(format!("ed25519:{}", "==1234%#").as_str(),),
84
         Err(Error::ConvertFromString { .. })
84
         Err(Error::ConvertFromString { .. })
85
     ));
85
     ));
86
-
87
-    Ok(())
88
 }
86
 }
89
 
87
 
90
 #[test]
88
 #[test]
91
-fn from_expanded() -> anyhow::Result<()> {
92
-    let dalek_sk = ExpandedSecretKey::from(&DalekSecretKey::from_bytes(&random_bits())?);
89
+fn from_expanded() {
90
+    let dalek_sk = ExpandedSecretKey::from(&DalekSecretKey::from_bytes(&random_bits()).unwrap());
93
     let exp_str = format!(
91
     let exp_str = format!(
94
         "ed25519:{}",
92
         "ed25519:{}",
95
         bs58::encode(dalek_sk.to_bytes()).into_string()
93
         bs58::encode(dalek_sk.to_bytes()).into_string()
96
     );
94
     );
97
-    let sk = Ed25519SecretKey::from_expanded(&exp_str)?;
95
+    let sk = Ed25519SecretKey::from_expanded(&exp_str).unwrap();
98
 
96
 
99
     assert_eq!(sk.as_bytes(), &dalek_sk.to_bytes()[..32]);
97
     assert_eq!(sk.as_bytes(), &dalek_sk.to_bytes()[..32]);
100
-    Ok(())
101
 }
98
 }
102
 
99
 
103
 #[test]
100
 #[test]
104
-fn from_expanded_fail() -> anyhow::Result<()> {
105
-    let dalek_sk = ExpandedSecretKey::from(&DalekSecretKey::from_bytes(&random_bits())?);
101
+fn from_expanded_fail() {
102
+    let dalek_sk = ExpandedSecretKey::from(&DalekSecretKey::from_bytes(&random_bits()).unwrap());
106
 
103
 
107
     let exp_str = bs58::encode(dalek_sk.to_bytes()).into_string();
104
     let exp_str = bs58::encode(dalek_sk.to_bytes()).into_string();
108
     assert!(matches!(
105
     assert!(matches!(
121
         Ed25519SecretKey::from_expanded(&exp_str),
118
         Ed25519SecretKey::from_expanded(&exp_str),
122
         Err(Error::ConvertFromString { .. })
119
         Err(Error::ConvertFromString { .. })
123
     ));
120
     ));
124
-
125
-    Ok(())
126
 }
121
 }
127
 
122
 
128
 #[test]
123
 #[test]
129
-fn try_from_bytes_x25519() -> anyhow::Result<()> {
130
-    let sk = SecretKey::try_from_bytes(&random_bits())?;
124
+fn try_from_bytes_x25519() {
125
+    let sk = SecretKey::try_from_bytes(&random_bits()).unwrap();
131
     let pk = PublicKey::from(&sk);
126
     let pk = PublicKey::from(&sk);
132
-    let _ = PublicKey::try_from_bytes(&pk.to_bytes())?;
127
+    let _ = PublicKey::try_from_bytes(&pk.to_bytes()).unwrap();
133
 
128
 
134
     assert!(matches!(
129
     assert!(matches!(
135
         PublicKey::try_from_bytes(&[0, 0, 0]),
130
         PublicKey::try_from_bytes(&[0, 0, 0]),
140
         SecretKey::try_from_bytes(&[0, 0, 0]),
135
         SecretKey::try_from_bytes(&[0, 0, 0]),
141
         Err(Error::ConvertFromBytes { .. })
136
         Err(Error::ConvertFromBytes { .. })
142
     ));
137
     ));
143
-
144
-    Ok(())
145
 }
138
 }
146
 
139
 
147
 #[test]
140
 #[test]
148
-fn to_string_x25519() -> anyhow::Result<()> {
149
-    let sk = SecretKey::try_from_bytes(&random_bits())?;
141
+fn to_string_x25519() {
142
+    let sk = SecretKey::try_from_bytes(&random_bits()).unwrap();
150
     let pk = PublicKey::from(&sk);
143
     let pk = PublicKey::from(&sk);
151
 
144
 
152
     assert_eq!(
145
     assert_eq!(
157
         format!("x25519:{}", bs58::encode(&pk.to_bytes()).into_string()),
150
         format!("x25519:{}", bs58::encode(&pk.to_bytes()).into_string()),
158
         pk.string()
151
         pk.string()
159
     );
152
     );
160
-
161
-    Ok(())
162
 }
153
 }
163
 
154
 
164
 #[test]
155
 #[test]
165
-fn from_string_x25519() -> anyhow::Result<()> {
166
-    let sk = SecretKey::try_from_bytes(&random_bits())?;
156
+fn from_string_x25519() {
157
+    let sk = SecretKey::try_from_bytes(&random_bits()).unwrap();
167
     let pk = PublicKey::from(&sk);
158
     let pk = PublicKey::from(&sk);
168
 
159
 
169
     let _ = SecretKey::from_string(
160
     let _ = SecretKey::from_string(
170
         format!("x25519:{}", bs58::encode(&sk.to_bytes()).into_string()).as_str(),
161
         format!("x25519:{}", bs58::encode(&sk.to_bytes()).into_string()).as_str(),
171
-    )?;
162
+    )
163
+    .unwrap();
172
 
164
 
173
     let _ = PublicKey::from_string(
165
     let _ = PublicKey::from_string(
174
         format!("x25519:{}", bs58::encode(&pk.to_bytes()).into_string()).as_str(),
166
         format!("x25519:{}", bs58::encode(&pk.to_bytes()).into_string()).as_str(),
175
-    )?;
167
+    )
168
+    .unwrap();
176
 
169
 
177
     assert!(matches!(
170
     assert!(matches!(
178
         PublicKey::from_string(
171
         PublicKey::from_string(
211
         PublicKey::from_string(format!("x25519:{}", "==1234%#").as_str(),),
204
         PublicKey::from_string(format!("x25519:{}", "==1234%#").as_str(),),
212
         Err(Error::ConvertFromString { .. })
205
         Err(Error::ConvertFromString { .. })
213
     ));
206
     ));
214
-
215
-    Ok(())
216
 }
207
 }
217
 
208
 
218
 #[test]
209
 #[test]
219
-fn public_key_verify() -> anyhow::Result<()> {
220
-    let sk = Ed25519SecretKey::try_from_bytes(&random_bits())?;
210
+fn public_key_verify() {
211
+    let sk = Ed25519SecretKey::try_from_bytes(&random_bits()).unwrap();
221
     let pk = Ed25519PublicKey::from(&sk);
212
     let pk = Ed25519PublicKey::from(&sk);
222
 
213
 
223
     let signature = sk.sign(b"message", &pk);
214
     let signature = sk.sign(b"message", &pk);
224
-    pk.verify(b"message", &signature)?;
225
-
226
-    Ok(())
215
+    pk.verify(b"message", &signature).unwrap();
227
 }
216
 }
228
 
217
 
229
 #[test]
218
 #[test]
230
-fn keypair_verify() -> anyhow::Result<()> {
231
-    let keypair = Keypair::new(Ed25519SecretKey::try_from_bytes(&random_bits())?);
219
+fn keypair_verify() {
220
+    let keypair = Keypair::new(Ed25519SecretKey::try_from_bytes(&random_bits()).unwrap());
232
     let signature = keypair.sign(b"message");
221
     let signature = keypair.sign(b"message");
233
-    keypair.verify(b"message", &signature)?;
234
-
235
-    Ok(())
222
+    keypair.verify(b"message", &signature).unwrap();
236
 }
223
 }
237
 
224
 
238
 #[test]
225
 #[test]
239
-fn key_exchange() -> anyhow::Result<()> {
240
-    let alice_sk = SecretKey::try_from_bytes(&random_bits())?;
226
+fn key_exchange() {
227
+    let alice_sk = SecretKey::try_from_bytes(&random_bits()).unwrap();
241
     let alice_pk = PublicKey::from(&alice_sk);
228
     let alice_pk = PublicKey::from(&alice_sk);
242
 
229
 
243
-    let bob_sk = SecretKey::try_from_bytes(&random_bits())?;
230
+    let bob_sk = SecretKey::try_from_bytes(&random_bits()).unwrap();
244
     let bob_pk = PublicKey::from(&bob_sk);
231
     let bob_pk = PublicKey::from(&bob_sk);
245
 
232
 
246
     assert_eq!(alice_sk.exchange(&bob_pk), bob_sk.exchange(&alice_pk));
233
     assert_eq!(alice_sk.exchange(&bob_pk), bob_sk.exchange(&alice_pk));
247
-    Ok(())
248
 }
234
 }
249
 
235
 
250
 #[test]
236
 #[test]
251
-fn borsh_ed25519() -> anyhow::Result<()> {
252
-    let sk = Ed25519SecretKey::try_from_bytes(&random_bits())?;
253
-    let sk_bytes = borsh::to_vec(&sk)?;
237
+fn borsh_ed25519() {
238
+    let sk = Ed25519SecretKey::try_from_bytes(&random_bits()).unwrap();
239
+    let sk_bytes = borsh::to_vec(&sk).unwrap();
254
     let pk = Ed25519PublicKey::from(&sk);
240
     let pk = Ed25519PublicKey::from(&sk);
255
-    let pk_bytes = borsh::to_vec(&pk)?;
241
+    let pk_bytes = borsh::to_vec(&pk).unwrap();
256
 
242
 
257
     assert_eq!(pk_bytes.len(), pk.as_bytes().len() + 1);
243
     assert_eq!(pk_bytes.len(), pk.as_bytes().len() + 1);
258
     assert_eq!(pk_bytes[0], 0);
244
     assert_eq!(pk_bytes[0], 0);
259
     assert_eq!(sk_bytes.len(), sk.as_bytes().len());
245
     assert_eq!(sk_bytes.len(), sk.as_bytes().len());
260
 
246
 
261
-    let sk = Ed25519SecretKey::try_from_slice(&sk_bytes)?;
262
-    let pk = Ed25519PublicKey::try_from_slice(&pk_bytes)?;
247
+    let sk = Ed25519SecretKey::try_from_slice(&sk_bytes).unwrap();
248
+    let pk = Ed25519PublicKey::try_from_slice(&pk_bytes).unwrap();
263
 
249
 
264
-    let signature_bytes = borsh::to_vec(&sk.sign(b"message", &pk))?;
250
+    let signature_bytes = borsh::to_vec(&sk.sign(b"message", &pk)).unwrap();
265
     pk.verify(
251
     pk.verify(
266
         b"message",
252
         b"message",
267
-        &Ed25519Signature::try_from_slice(&signature_bytes)?,
268
-    )?;
269
-
270
-    Ok(())
253
+        &Ed25519Signature::try_from_slice(&signature_bytes).unwrap(),
254
+    )
255
+    .unwrap();
271
 }
256
 }
272
 
257
 
273
 #[test]
258
 #[test]
274
-fn borsh_x25519() -> anyhow::Result<()> {
275
-    let sk = SecretKey::try_from_bytes(&random_bits())?;
276
-    let sk_bytes = borsh::to_vec(&sk)?;
259
+fn borsh_x25519() {
260
+    let sk = SecretKey::try_from_bytes(&random_bits()).unwrap();
261
+    let sk_bytes = borsh::to_vec(&sk).unwrap();
277
     let pk = PublicKey::from(&sk);
262
     let pk = PublicKey::from(&sk);
278
-    let pk_bytes = borsh::to_vec(&pk)?;
263
+    let pk_bytes = borsh::to_vec(&pk).unwrap();
264
+
265
+    // just try to serialize and deserialize. We doesn't support key-exchange for now
266
+    let _ = SecretKey::try_from_slice(&sk_bytes).unwrap();
267
+    let _ = PublicKey::try_from_slice(&pk_bytes).unwrap();
268
+}
269
+
270
+#[test]
271
+fn keypair_from_str() {
272
+    let sk = Ed25519SecretKey::try_from_bytes(&random_bits()).unwrap();
273
+    let pk = Ed25519PublicKey::from(&sk);
274
+
275
+    let mut sk_bytes = sk.to_bytes().to_vec();
276
+    sk_bytes.extend_from_slice(&pk.to_bytes());
277
+
278
+    let keypair_bs58 = format!("ed25519:{}", bs58::encode(sk_bytes).into_string());
279
+
280
+    let keypair = Keypair::from_str(&keypair_bs58).unwrap();
281
+
282
+    assert_eq!(keypair.secret_key().to_bytes(), sk.to_bytes());
283
+    assert_eq!(keypair.public_key().to_bytes(), pk.to_bytes());
284
+}
285
+
286
+#[test]
287
+fn keypair_to_string() {
288
+    let sk = Ed25519SecretKey::try_from_bytes(&random_bits()).unwrap();
289
+    let pk = Ed25519PublicKey::from(&sk);
290
+
291
+    let mut sk_bytes = sk.to_bytes().to_vec();
292
+    sk_bytes.extend_from_slice(&pk.to_bytes());
279
 
293
 
280
-    let _ = SecretKey::try_from_slice(&sk_bytes)?;
281
-    let _ = PublicKey::try_from_slice(&pk_bytes)?;
294
+    let keypair_bs58 = format!("ed25519:{}", bs58::encode(sk_bytes).into_string());
295
+    let keypair = Keypair::new(sk);
282
 
296
 
283
-    Ok(())
297
+    assert_eq!(keypair_bs58, keypair.to_string());
284
 }
298
 }
285
 
299
 
286
 fn random_bits() -> [u8; ED25519_SECRET_KEY_LENGTH] {
300
 fn random_bits() -> [u8; ED25519_SECRET_KEY_LENGTH] {

Loading…
Cancel
Save