Bytes everywhere for sign/verify

This commit is contained in:
Vincent Prouillet 2020-11-17 14:28:07 +01:00
parent 4aee8bc382
commit ea4ed55551
9 changed files with 27 additions and 37 deletions

View File

@ -1,5 +1,10 @@
# Changelog
## 8.0.0 (unreleased)
- Add EdDSA algorithm
- `sign`/`verify` now takes a `&[u8]` instead of `&str` to be more flexible
## 7.2.0 (2020-06-30)
- Add `dangerous_insecure_decode` to replace `dangerous_unsafe_decode`, which is now deprecated

View File

@ -16,8 +16,8 @@ pub(crate) fn alg_to_ec_verification(alg: Algorithm) -> &'static signature::EdDS
/// The actual EdDSA signing + encoding
/// The key needs to be in PKCS8 format
pub fn sign(key: &[u8], message: &str) -> Result<String> {
pub fn sign(key: &[u8], message: &[u8]) -> Result<String> {
let signing_key = signature::Ed25519KeyPair::from_pkcs8_maybe_unchecked(key)?;
let out = signing_key.sign(message.as_bytes());
let out = signing_key.sign(message);
Ok(b64_encode(out.as_ref()))
}

View File

@ -22,12 +22,7 @@ pub(crate) fn sign_hmac(alg: hmac::Algorithm, key: &[u8], message: &[u8]) -> Res
/// the base64 url safe encoded of the result.
///
/// If you just want to encode a JWT, use `encode` instead.
pub fn sign(message: &str, key: &EncodingKey, algorithm: Algorithm) -> Result<String> {
sign_bytes(message.as_bytes(), key, algorithm)
}
/// Same as sign() but for message as bytes
pub fn sign_bytes(message: &[u8], key: &EncodingKey, algorithm: Algorithm) -> Result<String> {
pub fn sign(message: &[u8], key: &EncodingKey, algorithm: Algorithm) -> Result<String> {
match algorithm {
Algorithm::HS256 => sign_hmac(hmac::HMAC_SHA256, key.inner(), message),
Algorithm::HS384 => sign_hmac(hmac::HMAC_SHA384, key.inner(), message),
@ -71,16 +66,6 @@ fn verify_ring(
///
/// `message` is base64(header) + "." + base64(claims)
pub fn verify(
signature: &str,
message: &str,
key: &DecodingKey,
algorithm: Algorithm,
) -> Result<bool> {
Ok(verify_bytes(signature, message.as_bytes(), key, algorithm)?)
}
/// Same as verify() but for message as bytes
pub fn verify_bytes(
signature: &str,
message: &[u8],
key: &DecodingKey,
@ -89,7 +74,7 @@ pub fn verify_bytes(
match algorithm {
Algorithm::HS256 | Algorithm::HS384 | Algorithm::HS512 => {
// we just re-sign the message with the key and compare if they are equal
let signed = sign_bytes(message, &EncodingKey::from_secret(key.as_bytes()), algorithm)?;
let signed = sign(message, &EncodingKey::from_secret(key.as_bytes()), algorithm)?;
Ok(verify_slices_are_equal(signature.as_ref(), signed.as_ref()).is_ok())
}
Algorithm::ES256 | Algorithm::ES384 => verify_ring(

View File

@ -186,7 +186,7 @@ pub fn decode<T: DeserializeOwned>(
return Err(new_error(ErrorKind::InvalidAlgorithm));
}
if !verify(signature, message, key, header.alg)? {
if !verify(signature, message.as_bytes(), key, header.alg)? {
return Err(new_error(ErrorKind::InvalidSignature));
}

View File

@ -117,7 +117,7 @@ pub fn encode<T: Serialize>(header: &Header, claims: &T, key: &EncodingKey) -> R
let encoded_header = b64_encode_part(&header)?;
let encoded_claims = b64_encode_part(&claims)?;
let message = [encoded_header.as_ref(), encoded_claims.as_ref()].join(".");
let signature = crypto::sign(&*message, key, header.alg)?;
let signature = crypto::sign(&*message.as_bytes(), key, header.alg)?;
Ok([message, signature].join("."))
}

View File

@ -18,9 +18,9 @@ fn round_trip_sign_verification_pk8() {
let pubkey = include_bytes!("public_ecdsa_key.pk8");
let encrypted =
sign("hello world", &EncodingKey::from_ec_der(privkey), Algorithm::ES256).unwrap();
sign("hello world".as_bytes(), &EncodingKey::from_ec_der(privkey), Algorithm::ES256).unwrap();
let is_valid =
verify(&encrypted, "hello world", &DecodingKey::from_ec_der(pubkey), Algorithm::ES256)
verify(&encrypted, "hello world".as_bytes(), &DecodingKey::from_ec_der(pubkey), Algorithm::ES256)
.unwrap();
assert!(is_valid);
}
@ -30,11 +30,11 @@ fn round_trip_sign_verification_pem() {
let privkey_pem = include_bytes!("private_ecdsa_key.pem");
let pubkey_pem = include_bytes!("public_ecdsa_key.pem");
let encrypted =
sign("hello world", &EncodingKey::from_ec_pem(privkey_pem).unwrap(), Algorithm::ES256)
sign("hello world".as_bytes(), &EncodingKey::from_ec_pem(privkey_pem).unwrap(), Algorithm::ES256)
.unwrap();
let is_valid = verify(
&encrypted,
"hello world",
"hello world".as_bytes(),
&DecodingKey::from_ec_pem(pubkey_pem).unwrap(),
Algorithm::ES256,
)

View File

@ -18,9 +18,9 @@ fn round_trip_sign_verification_pk8() {
let pubkey = include_bytes!("public_ed25519_key.pk8");
let encrypted =
sign("hello world", &EncodingKey::from_ed_der(privkey), Algorithm::EdDSA).unwrap();
sign("hello world".as_bytes(), &EncodingKey::from_ed_der(privkey), Algorithm::EdDSA).unwrap();
let is_valid =
verify(&encrypted, "hello world", &DecodingKey::from_ed_der(pubkey), Algorithm::EdDSA)
verify(&encrypted, "hello world".as_bytes(), &DecodingKey::from_ed_der(pubkey), Algorithm::EdDSA)
.unwrap();
assert!(is_valid);
}
@ -30,11 +30,11 @@ fn round_trip_sign_verification_pem() {
let privkey_pem = include_bytes!("private_ed25519_key.pem");
let pubkey_pem = include_bytes!("public_ed25519_key.pem");
let encrypted =
sign("hello world", &EncodingKey::from_ed_pem(privkey_pem).unwrap(), Algorithm::EdDSA)
sign("hello world".as_bytes(), &EncodingKey::from_ed_pem(privkey_pem).unwrap(), Algorithm::EdDSA)
.unwrap();
let is_valid = verify(
&encrypted,
"hello world",
"hello world".as_bytes(),
&DecodingKey::from_ed_pem(pubkey_pem).unwrap(),
Algorithm::EdDSA,
)

View File

@ -17,7 +17,7 @@ pub struct Claims {
#[test]
fn sign_hs256() {
let result =
sign("hello world", &EncodingKey::from_secret(b"secret"), Algorithm::HS256).unwrap();
sign("hello world".as_bytes(), &EncodingKey::from_secret(b"secret"), Algorithm::HS256).unwrap();
let expected = "c0zGLzKEFWj0VxWuufTXiRMk5tlI5MbGDAYhzaxIYjo";
assert_eq!(result, expected);
}
@ -26,7 +26,7 @@ fn sign_hs256() {
fn verify_hs256() {
let sig = "c0zGLzKEFWj0VxWuufTXiRMk5tlI5MbGDAYhzaxIYjo";
let valid =
verify(sig, "hello world", &DecodingKey::from_secret(b"secret"), Algorithm::HS256).unwrap();
verify(sig, "hello world".as_bytes(), &DecodingKey::from_secret(b"secret"), Algorithm::HS256).unwrap();
assert!(valid);
}

View File

@ -28,9 +28,9 @@ fn round_trip_sign_verification_pem_pkcs1() {
for &alg in RSA_ALGORITHMS {
let encrypted =
sign("hello world", &EncodingKey::from_rsa_pem(privkey_pem).unwrap(), alg).unwrap();
sign("hello world".as_bytes(), &EncodingKey::from_rsa_pem(privkey_pem).unwrap(), alg).unwrap();
let is_valid =
verify(&encrypted, "hello world", &DecodingKey::from_rsa_pem(pubkey_pem).unwrap(), alg)
verify(&encrypted, "hello world".as_bytes(), &DecodingKey::from_rsa_pem(pubkey_pem).unwrap(), alg)
.unwrap();
assert!(is_valid);
}
@ -43,9 +43,9 @@ fn round_trip_sign_verification_pem_pkcs8() {
for &alg in RSA_ALGORITHMS {
let encrypted =
sign("hello world", &EncodingKey::from_rsa_pem(privkey_pem).unwrap(), alg).unwrap();
sign("hello world".as_bytes(), &EncodingKey::from_rsa_pem(privkey_pem).unwrap(), alg).unwrap();
let is_valid =
verify(&encrypted, "hello world", &DecodingKey::from_rsa_pem(pubkey_pem).unwrap(), alg)
verify(&encrypted, "hello world".as_bytes(), &DecodingKey::from_rsa_pem(pubkey_pem).unwrap(), alg)
.unwrap();
assert!(is_valid);
}
@ -57,9 +57,9 @@ fn round_trip_sign_verification_der() {
let pubkey_der = include_bytes!("public_rsa_key.der");
for &alg in RSA_ALGORITHMS {
let encrypted = sign("hello world", &EncodingKey::from_rsa_der(privkey_der), alg).unwrap();
let encrypted = sign("hello world".as_bytes(), &EncodingKey::from_rsa_der(privkey_der), alg).unwrap();
let is_valid =
verify(&encrypted, "hello world", &DecodingKey::from_rsa_der(pubkey_der), alg).unwrap();
verify(&encrypted, "hello world".as_bytes(), &DecodingKey::from_rsa_der(pubkey_der), alg).unwrap();
assert!(is_valid);
}
}