keygate_jwt/algorithms/
es256k.rs

1use std::convert::TryFrom;
2
3use base64ct::{Base64UrlUnpadded, Encoding};
4use k256::ecdsa::{self, signature::DigestVerifier as _, signature::RandomizedDigestSigner as _};
5use k256::pkcs8::{DecodePrivateKey, DecodePublicKey, EncodePrivateKey, EncodePublicKey};
6use serde::{de::DeserializeOwned, Serialize};
7use sha2::{Digest, Sha256};
8
9use crate::claims::*;
10use crate::common::*;
11use crate::error::*;
12use crate::jwt_header::*;
13use crate::token::*;
14
15#[doc(hidden)]
16#[derive(Debug, Clone)]
17pub struct K256PublicKey(ecdsa::VerifyingKey);
18
19impl AsRef<ecdsa::VerifyingKey> for K256PublicKey {
20    fn as_ref(&self) -> &ecdsa::VerifyingKey {
21        &self.0
22    }
23}
24
25impl K256PublicKey {
26    pub fn from_bytes(raw: &[u8]) -> Result<Self, JWTError> {
27        let k256_pk =
28            ecdsa::VerifyingKey::from_sec1_bytes(raw).map_err(|_| JWTError::InvalidPublicKey)?;
29        Ok(K256PublicKey(k256_pk))
30    }
31
32    pub fn from_der(der: &[u8]) -> Result<Self, JWTError> {
33        let k256_pk = ecdsa::VerifyingKey::from_public_key_der(der)
34            .map_err(|_| JWTError::InvalidPublicKey)?;
35        Ok(K256PublicKey(k256_pk))
36    }
37
38    pub fn from_pem(pem: &str) -> Result<Self, JWTError> {
39        let k256_pk = ecdsa::VerifyingKey::from_public_key_pem(pem)
40            .map_err(|_| JWTError::InvalidPublicKey)?;
41        Ok(K256PublicKey(k256_pk))
42    }
43
44    pub fn to_bytes(&self) -> Vec<u8> {
45        self.0.to_encoded_point(false).as_bytes().to_vec()
46    }
47
48    pub fn to_der(&self) -> Result<Vec<u8>, JWTError> {
49        let k256_pk = k256::PublicKey::from(self.0);
50        Ok(k256_pk
51            .to_public_key_der()
52            .map_err(|_| JWTError::InvalidPublicKey)?
53            .as_ref()
54            .to_vec())
55    }
56
57    pub fn to_pem(&self) -> Result<String, JWTError> {
58        let k256_pk = k256::PublicKey::from(self.0);
59        k256_pk
60            .to_public_key_pem(Default::default())
61            .map_err(|_| JWTError::InvalidPublicKey)
62    }
63}
64
65#[doc(hidden)]
66pub struct K256KeyPair {
67    k256_sk: ecdsa::SigningKey,
68    metadata: Option<KeyMetadata>,
69}
70
71impl AsRef<ecdsa::SigningKey> for K256KeyPair {
72    fn as_ref(&self) -> &ecdsa::SigningKey {
73        &self.k256_sk
74    }
75}
76
77impl K256KeyPair {
78    pub fn from_bytes(raw: &[u8]) -> Result<Self, JWTError> {
79        let k256_sk =
80            ecdsa::SigningKey::from_bytes(raw.into()).map_err(|_| JWTError::InvalidKeyPair)?;
81        Ok(K256KeyPair {
82            k256_sk,
83            metadata: None,
84        })
85    }
86
87    pub fn from_der(der: &[u8]) -> Result<Self, JWTError> {
88        let k256_sk =
89            ecdsa::SigningKey::from_pkcs8_der(der).map_err(|_| JWTError::InvalidKeyPair)?;
90        Ok(K256KeyPair {
91            k256_sk,
92            metadata: None,
93        })
94    }
95
96    pub fn from_pem(pem: &str) -> Result<Self, JWTError> {
97        let k256_sk =
98            ecdsa::SigningKey::from_pkcs8_pem(pem).map_err(|_| JWTError::InvalidKeyPair)?;
99        Ok(K256KeyPair {
100            k256_sk,
101            metadata: None,
102        })
103    }
104
105    pub fn to_bytes(&self) -> Vec<u8> {
106        self.k256_sk.to_bytes().to_vec()
107    }
108
109    pub fn to_der(&self) -> Result<Vec<u8>, JWTError> {
110        let k256_sk = k256::SecretKey::from(&self.k256_sk);
111        Ok(k256_sk
112            .to_pkcs8_der()
113            .map_err(|_| JWTError::InvalidKeyPair)?
114            .as_bytes()
115            .to_vec())
116    }
117
118    pub fn to_pem(&self) -> Result<String, JWTError> {
119        let k256_sk = k256::SecretKey::from(&self.k256_sk);
120        Ok(k256_sk
121            .to_pkcs8_pem(Default::default())
122            .map_err(|_| JWTError::InvalidKeyPair)?
123            .to_string())
124    }
125
126    pub fn public_key(&self) -> K256PublicKey {
127        let k256_pk = self.k256_sk.verifying_key();
128        K256PublicKey(*k256_pk)
129    }
130
131    pub fn generate() -> Self {
132        let mut rng = rand::thread_rng();
133        let k256_sk = ecdsa::SigningKey::random(&mut rng);
134        K256KeyPair {
135            k256_sk,
136            metadata: None,
137        }
138    }
139}
140
141pub trait ECDSAP256kKeyPairLike {
142    fn jwt_alg_name() -> &'static str;
143    fn key_pair(&self) -> &K256KeyPair;
144    fn key_id(&self) -> &Option<String>;
145    fn metadata(&self) -> &Option<KeyMetadata>;
146    fn attach_metadata(&mut self, metadata: KeyMetadata) -> Result<(), JWTError>;
147
148    fn sign<CustomClaims: Serialize + DeserializeOwned>(
149        &self,
150        claims: JWTClaims<CustomClaims>,
151    ) -> Result<String, JWTError> {
152        let jwt_header = JWTHeader::new(Self::jwt_alg_name().to_string(), self.key_id().clone())
153            .with_metadata(self.metadata());
154        Token::build(&jwt_header, claims, |authenticated| {
155            let mut digest = Sha256::new();
156            digest.update(authenticated.as_bytes());
157            let mut rng = rand::thread_rng();
158            let signature: ecdsa::Signature = self
159                .key_pair()
160                .as_ref()
161                .sign_digest_with_rng(&mut rng, digest);
162            Ok(signature.to_vec())
163        })
164    }
165}
166
167pub trait ECDSAP256kPublicKeyLike {
168    fn jwt_alg_name() -> &'static str;
169    fn public_key(&self) -> &K256PublicKey;
170    fn key_id(&self) -> &Option<String>;
171    fn set_key_id(&mut self, key_id: String);
172
173    fn verify_token<CustomClaims: Serialize + DeserializeOwned>(
174        &self,
175        token: &str,
176        options: Option<VerificationOptions>,
177    ) -> Result<JWTClaims<CustomClaims>, JWTError> {
178        Token::verify(
179            Self::jwt_alg_name(),
180            token,
181            options,
182            |authenticated, signature| {
183                let ecdsa_signature = ecdsa::Signature::try_from(signature)
184                    .map_err(|_| JWTError::InvalidSignature)?;
185                let mut digest = Sha256::new();
186                digest.update(authenticated.as_bytes());
187                self.public_key()
188                    .as_ref()
189                    .verify_digest(digest, &ecdsa_signature)
190                    .map_err(|_| JWTError::InvalidSignature)?;
191                Ok(())
192            },
193        )
194    }
195
196    fn create_key_id(&mut self) -> Result<String, JWTError> {
197        let mut hasher = sha2::Sha256::new();
198        hasher.update(self.public_key().to_bytes());
199        let key_id = Base64UrlUnpadded::encode_string(&hasher.finalize());
200        self.set_key_id(key_id.clone());
201        Ok(key_id)
202    }
203}
204
205pub struct ES256kKeyPair {
206    key_pair: K256KeyPair,
207    key_id: Option<String>,
208}
209
210#[derive(Debug, Clone)]
211pub struct ES256kPublicKey {
212    pk: K256PublicKey,
213    key_id: Option<String>,
214}
215
216impl ECDSAP256kKeyPairLike for ES256kKeyPair {
217    fn jwt_alg_name() -> &'static str {
218        "ES256K"
219    }
220
221    fn key_pair(&self) -> &K256KeyPair {
222        &self.key_pair
223    }
224
225    fn key_id(&self) -> &Option<String> {
226        &self.key_id
227    }
228
229    fn metadata(&self) -> &Option<KeyMetadata> {
230        &self.key_pair.metadata
231    }
232
233    fn attach_metadata(&mut self, metadata: KeyMetadata) -> Result<(), JWTError> {
234        self.key_pair.metadata = Some(metadata);
235        Ok(())
236    }
237}
238
239impl ES256kKeyPair {
240    pub fn from_bytes(raw: &[u8]) -> Result<Self, JWTError> {
241        Ok(ES256kKeyPair {
242            key_pair: K256KeyPair::from_bytes(raw)?,
243            key_id: None,
244        })
245    }
246
247    pub fn from_der(der: &[u8]) -> Result<Self, JWTError> {
248        Ok(ES256kKeyPair {
249            key_pair: K256KeyPair::from_der(der)?,
250            key_id: None,
251        })
252    }
253
254    pub fn from_pem(pem: &str) -> Result<Self, JWTError> {
255        Ok(ES256kKeyPair {
256            key_pair: K256KeyPair::from_pem(pem)?,
257            key_id: None,
258        })
259    }
260
261    pub fn to_bytes(&self) -> Vec<u8> {
262        self.key_pair.to_bytes()
263    }
264
265    pub fn to_der(&self) -> Result<Vec<u8>, JWTError> {
266        self.key_pair.to_der()
267    }
268
269    pub fn to_pem(&self) -> Result<String, JWTError> {
270        self.key_pair.to_pem()
271    }
272
273    pub fn public_key(&self) -> ES256kPublicKey {
274        ES256kPublicKey {
275            pk: self.key_pair.public_key(),
276            key_id: self.key_id.clone(),
277        }
278    }
279
280    pub fn generate() -> Self {
281        ES256kKeyPair {
282            key_pair: K256KeyPair::generate(),
283            key_id: None,
284        }
285    }
286
287    pub fn with_key_id(mut self, key_id: &str) -> Self {
288        self.key_id = Some(key_id.to_string());
289        self
290    }
291}
292
293impl ECDSAP256kPublicKeyLike for ES256kPublicKey {
294    fn jwt_alg_name() -> &'static str {
295        "ES256K"
296    }
297
298    fn public_key(&self) -> &K256PublicKey {
299        &self.pk
300    }
301
302    fn key_id(&self) -> &Option<String> {
303        &self.key_id
304    }
305
306    fn set_key_id(&mut self, key_id: String) {
307        self.key_id = Some(key_id);
308    }
309}
310
311impl ES256kPublicKey {
312    pub fn from_bytes(raw: &[u8]) -> Result<Self, JWTError> {
313        Ok(ES256kPublicKey {
314            pk: K256PublicKey::from_bytes(raw)?,
315            key_id: None,
316        })
317    }
318
319    pub fn from_der(der: &[u8]) -> Result<Self, JWTError> {
320        Ok(ES256kPublicKey {
321            pk: K256PublicKey::from_der(der)?,
322            key_id: None,
323        })
324    }
325
326    pub fn from_pem(pem: &str) -> Result<Self, JWTError> {
327        Ok(ES256kPublicKey {
328            pk: K256PublicKey::from_pem(pem)?,
329            key_id: None,
330        })
331    }
332
333    pub fn to_bytes(&self) -> Vec<u8> {
334        self.pk.to_bytes()
335    }
336
337    pub fn to_der(&self) -> Result<Vec<u8>, JWTError> {
338        self.pk.to_der()
339    }
340
341    pub fn to_pem(&self) -> Result<String, JWTError> {
342        self.pk.to_pem()
343    }
344
345    pub fn with_key_id(mut self, key_id: &str) -> Self {
346        self.key_id = Some(key_id.to_string());
347        self
348    }
349}