jws/
none.rs

1//! [`Verifier`] and [`Signer`] implementations for the `none` algorithm.
2//!
3//! The `none` algorithm is defined in [RFC 7518 section 3.6](https://tools.ietf.org/html/rfc7518#section-3.6).
4//! It does not provide any integrity protection.
5//!
6//! It doesn't often make sense to use this "algorithm".
7
8use crate::{Error, JsonObject, JsonValue, parse_required_header_param, Result, Signer, Verifier};
9
10/// Message verifier for the `none` algorithm.
11///
12/// The `none` algorithm has an empty signature and does not provide integrity protection.
13/// The verifier does check that the signature is indeed empty as required by [RFC 7518 (section 3.6)](https://tools.ietf.org/html/rfc7518#section-3.6).
14#[derive(Copy, Clone, Debug)]
15pub struct NoneVerifier;
16
17/// Message signer for the `none` algorithm.
18///
19/// Adds an empty signature that does not provide integrity protection.
20#[derive(Copy, Clone, Debug)]
21pub struct NoneSigner;
22
23impl Verifier for NoneVerifier {
24	fn verify(&self, protected_header: Option<&JsonObject>, unprotected_header: Option<&JsonObject>, _encoded_header: &[u8], _encoded_payload: &[u8], signature: &[u8]) -> Result<()> {
25		let algorithm : &str = parse_required_header_param(protected_header, unprotected_header, "alg")?;
26
27		if algorithm != "none" {
28			Err(Error::unsupported_mac_algorithm(algorithm))
29		} else if !signature.is_empty() {
30			Err(Error::invalid_signature(""))
31		} else {
32			Ok(())
33		}
34	}
35}
36
37impl Signer for NoneSigner {
38	fn set_header_params(&self, header: &mut JsonObject) {
39		header.insert("alg".to_string(), JsonValue::from("none"));
40	}
41
42	fn compute_mac(&self, _encoded_header: &[u8], _encoded_payload: &[u8]) -> Result<Vec<u8>> {
43		Ok(Vec::new())
44	}
45}
46
47#[cfg(test)]
48mod test {
49	use super::*;
50	use crate::{ErrorKind, json_object};
51	use assert2::assert;
52
53	#[test]
54	fn test_none_signer_header() {
55		let mut header = json_object!{};
56		let signer = NoneSigner;
57
58		signer.set_header_params(&mut header);
59		assert!(header == json_object!{"alg": "none"});
60	}
61
62	#[test]
63	fn test_none_signer_mac() {
64		let signer = NoneSigner;
65		assert!(&signer.compute_mac(b"fake_header", b"fake_payload").unwrap() == b"");
66		assert!(&signer.compute_mac(b"fake_header", b"").unwrap() == b"");
67		assert!(&signer.compute_mac(b"",            b"fake_payload").unwrap() == b"");
68		assert!(&signer.compute_mac(b"",            b"").unwrap() == b"");
69	}
70
71	#[test]
72	fn test_verify_none() {
73		let header  = &json_object!{"alg": "none"};
74		let verifier = NoneVerifier;
75
76		// Test that an empty signature is accepted.
77		assert!(let Ok(_) = verifier.verify(Some(header), None, b"fake_header", b"fake_payload", b""));
78		assert!(let Ok(_) = verifier.verify(Some(header), None, b"fake_header", b"",             b""));
79		assert!(let Ok(_) = verifier.verify(Some(header), None, b"",            b"fake_payload", b""));
80		assert!(let Ok(_) = verifier.verify(Some(header), None, b"",            b"fake_payload", b""));
81
82		// Test that a non-empty signature is rejected.
83		assert!(let Err(Error { kind: ErrorKind::InvalidSignature, .. }) = verifier.verify(Some(header), None, b"fake_header", b"fake_payload", b"bad-signature"));
84		assert!(let Err(Error { kind: ErrorKind::InvalidSignature, .. }) = verifier.verify(Some(header), None, b"fake_header", b"",             b"bad-signature"));
85		assert!(let Err(Error { kind: ErrorKind::InvalidSignature, .. }) = verifier.verify(Some(header), None, b"",            b"fake_payload", b"bad-signature"));
86		assert!(let Err(Error { kind: ErrorKind::InvalidSignature, .. }) = verifier.verify(Some(header), None, b"",            b"fake_payload", b"bad-signature"));
87	}
88}