use super::*;
fn keypair() -> Keypair {
Keypair::from_seed([7u8; 32]).unwrap()
}
#[test]
fn the_signed_bytes_are_the_beps_spelling() {
assert_eq!(
signed_bytes(b"foobar", 1, b"Hello World!"),
b"4:salt6:foobar3:seqi1e1:v12:Hello World!"
);
assert_eq!(
signed_bytes(b"", 1, b"Hello World!"),
b"3:seqi1e1:v12:Hello World!"
);
}
#[test]
fn an_item_signs_verifies_and_fails_when_touched() {
let kp = keypair();
let item = kp.sign(b"salt".to_vec(), 3, b"value".to_vec()).unwrap();
assert_eq!(item.key, kp.public());
assert!(item.verify());
let mut forged = item.clone();
forged.seq += 1;
assert!(!forged.verify());
let mut other_key = item.clone();
other_key.key = Keypair::from_seed([8u8; 32]).unwrap().public();
assert!(!other_key.verify());
assert_eq!(keypair().public(), kp.public());
assert_ne!(Keypair::generate().unwrap().public(), kp.public());
}
#[test]
fn a_value_over_the_beps_cap_is_refused_before_it_leaves() {
let kp = keypair();
assert!(kp.sign(vec![], 1, vec![0u8; 996]).is_ok());
let e = kp.sign(vec![], 1, vec![0u8; 997]).unwrap_err();
assert_eq!(e, "value bencodes to 1001 bytes; BEP 44 allows 1000");
}
#[test]
fn the_target_is_sha1_of_key_and_salt() {
let key = [1u8; 32];
let plain = target_of(&key, b"");
let salted = target_of(&key, b"s");
assert_ne!(plain, salted);
let expect = ring::digest::digest(&ring::digest::SHA1_FOR_LEGACY_USE_ONLY, &key);
assert_eq!(plain.0.as_slice(), expect.as_ref());
let item = keypair().sign(b"s".to_vec(), 1, vec![]).unwrap();
assert_eq!(item.target(), target_of(&keypair().public(), b"s"));
}
#[test]
fn a_reply_yields_its_item_only_when_it_verifies() {
let kp = keypair();
let item = kp.sign(b"s".to_vec(), 5, b"v".to_vec()).unwrap();
let mut r = Dict::from([
entry("seq", Value::Int(5)),
entry("sig", bytes(&item.sig)),
entry("v", bytes(b"v")),
]);
assert_eq!(
Mutable::from_reply(&r, kp.public(), b"s"),
Some(item.clone())
);
assert_eq!(Mutable::from_reply(&r, kp.public(), b"t"), None);
assert_eq!(Mutable::from_reply(&Dict::new(), kp.public(), b"s"), None);
r.insert(b"v".to_vec(), Value::Int(1));
assert_eq!(Mutable::from_reply(&r, kp.public(), b"s"), None);
r.insert(b"sig".to_vec(), bytes(b"short"));
assert_eq!(Mutable::from_reply(&r, kp.public(), b"s"), None);
}
#[test]
fn put_arguments_carry_the_salt_only_when_there_is_one() {
let kp = keypair();
let salted = kp.sign(b"s".to_vec(), 1, b"v".to_vec()).unwrap();
let args = salted.put_args(b"tok");
assert_eq!(args.get(b"salt".as_slice()), Some(&bytes(b"s")));
assert_eq!(args.get(b"token".as_slice()), Some(&bytes(b"tok")));
assert_eq!(args.get(b"k".as_slice()), Some(&bytes(&kp.public())));
assert_eq!(args.get(b"seq".as_slice()), Some(&Value::Int(1)));
assert_eq!(args.get(b"v".as_slice()), Some(&bytes(b"v")));
assert_eq!(args.get(b"sig".as_slice()), Some(&bytes(&salted.sig)));
let plain = kp.sign(vec![], 1, b"v".to_vec()).unwrap();
assert_eq!(plain.put_args(b"tok").get(b"salt".as_slice()), None);
}