PeerAllowPush: consent to exchange pushes, for a while, and nothing else
PeerTrust syncs a peer's pins and serves it everything - too much to grant a stranger. An app that wants two peers sharing something (two phones at the same place) to hand each other new content allows pushes for ttl_secs (at most a day): both sides may push, the receiver pins, and the allowance lapses on its own. Asking again extends it; PeerUntrust ends it. varde-ctl peer allow-push. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5.5
parent
0006a188e3
commit
2063d11890
@@ -422,3 +422,49 @@ fn push_rejected_without_receiver_trust() {
|
||||
// And the receiver holds none of it.
|
||||
assert!(!is_complete(&b.socket, &hash));
|
||||
}
|
||||
|
||||
/// A push allowance is enough on both sides: two daemons that only
|
||||
/// allowed pushes with each other (strangers sharing a place, in redoal)
|
||||
/// exchange content without trusting each other - and the allowance
|
||||
/// grants nothing else, so neither lists the other as a trusted peer.
|
||||
#[test]
|
||||
fn push_allowance_is_enough_and_is_not_trust() {
|
||||
let _serial = MDNS_SERIAL.lock().unwrap_or_else(|e| e.into_inner());
|
||||
let dir_a = tempfile::tempdir().unwrap();
|
||||
let dir_b = tempfile::tempdir().unwrap();
|
||||
let a = support::spawn_daemon_with_env(dir_a.path(), &[("VARDE_DISCOVERY", "true")]);
|
||||
let b = support::spawn_daemon_with_env(dir_b.path(), &[("VARDE_DISCOVERY", "true")]);
|
||||
let mut client_a = support::Client::connect(&a.socket);
|
||||
let mut client_b = support::Client::connect(&b.socket);
|
||||
let id_a = node_id(&mut client_a);
|
||||
let id_b = node_id(&mut client_b);
|
||||
|
||||
let dir = tempfile::tempdir().unwrap();
|
||||
let src = dir.path().join("voice.bin");
|
||||
let payload = vec![7u8; 120_000];
|
||||
std::fs::write(&src, &payload).unwrap();
|
||||
let hash = add_file(&mut client_a, &src);
|
||||
pin(&mut client_a, &hash, false);
|
||||
|
||||
assert!(client_a.request(&Request::PeerAllowPush { node_id: id_b.clone(), ttl_secs: 600 }).ok);
|
||||
assert!(client_b.request(&Request::PeerAllowPush { node_id: id_a, ttl_secs: 600 }).ok);
|
||||
match client_a.request(&Request::PeerList {}).data {
|
||||
Some(ResponseData::Peers { peers }) => assert!(peers.is_empty(), "an allowance is not trust: {peers:?}"),
|
||||
other => panic!("unexpected peer list: {other:?}"),
|
||||
}
|
||||
|
||||
// The peer's address arrives by mdns; retry until it does.
|
||||
let deadline = Instant::now() + Duration::from_secs(30);
|
||||
let reply = loop {
|
||||
let reply = client_a.request(&Request::Push { hash: hash.clone(), node_id: id_b.clone() });
|
||||
if reply.ok || Instant::now() > deadline {
|
||||
break reply;
|
||||
}
|
||||
std::thread::sleep(Duration::from_millis(500));
|
||||
};
|
||||
if !reply.ok {
|
||||
eprintln!("SKIP: push never reached the peer (multicast unavailable?): {:?}", reply.error);
|
||||
return;
|
||||
}
|
||||
assert!(wait_complete(&b.socket, &hash, Duration::from_secs(60)), "pushed content not complete on receiver");
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user