http_msgsign_draft/sign/
request.rs

1use crate::errors::{SignError, VerificationError};
2use crate::sign::{SignatureInput, SignatureParams};
3use crate::sign::{SignerKey, VerifierKey};
4use http::Request;
5
6//noinspection DuplicatedCode
7pub trait RequestSign {
8    /// Write the signature to the HTTP header, `Signature`.
9    /// 
10    /// If you want to write to `Authorization` header, consider using [`RequestSign::proof`].
11    fn sign<S: SignerKey>(
12        self,
13        key: &S,
14        params: &SignatureParams,
15    ) -> impl Future<Output = Result<Self, SignError>> + Send
16    where
17        Self: Sized;
18    
19    /// Write the signature to the HTTP header, `Authorization`.
20    /// 
21    /// If you want to write to `Signature` header, consider using [`RequestSign::sign`].
22    fn proof<S: SignerKey>(
23        self,
24        key: &S,
25        params: &SignatureParams,
26    ) -> impl Future<Output = Result<Self, SignError>> + Send
27    where
28        Self: Sized;
29
30    fn verify_sign<V: VerifierKey>(
31        self,
32        key: &V,
33    ) -> impl Future<Output = Result<Self, VerificationError>> + Send
34    where
35        Self: Sized;
36}
37
38impl<B> RequestSign for Request<B>
39where
40    B: http_body::Body + Send,
41    B::Data: Send,
42{
43    async fn sign<S: SignerKey>(
44        self,
45        key: &S,
46        params: &SignatureParams,
47    ) -> Result<Self, SignError> {
48        let base = params.seek_request(&self)?;
49        let (mut parts, body) = self.into_parts();
50        let (name, value) = base.to_signature_header(key);
51        parts.headers.insert(name, value);
52
53        Ok(Self::from_parts(parts, body))
54    }
55
56    async fn proof<S: SignerKey>(
57        self,
58        key: &S,
59        params: &SignatureParams,
60    ) -> Result<Self, SignError> {
61        let base = params.seek_request(&self)?;
62        let (mut parts, body) = self.into_parts();
63        let (name, value) = base.to_authorization_header(key);
64        parts.headers.insert(name, value);
65
66        Ok(Self::from_parts(parts, body))
67    }
68
69    async fn verify_sign<V: VerifierKey>(self, key: &V) -> Result<Self, VerificationError> {
70        let (parts, body) = self.into_parts();
71        let input = SignatureInput::from_header(&parts.headers)?;
72
73        let req = Self::from_parts(parts, body);
74        let seeked = input.seek_request(&req)?;
75
76        seeked.verify(key, &input.signature)?;
77
78        Ok(req)
79    }
80}