Make signature optional, flatten JSON
This commit is contained in:
parent
87cdad3cc2
commit
17e266d1e2
41
src/lib.rs
41
src/lib.rs
@ -14,20 +14,26 @@ use uuid::Uuid;
|
|||||||
|
|
||||||
#[derive(Deserialize, Serialize, Debug)]
|
#[derive(Deserialize, Serialize, Debug)]
|
||||||
pub struct ProxyCommand {
|
pub struct ProxyCommand {
|
||||||
|
#[serde(flatten)]
|
||||||
command: Command,
|
command: Command,
|
||||||
signature: Signature,
|
signature: Option<Signature>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl ProxyCommand {
|
impl ProxyCommand {
|
||||||
fn verify_signature(&self, verifying_key: &VerifyingKey) -> bool {
|
fn verify_signature(&self, verifying_key: &Option<VerifyingKey>) -> bool {
|
||||||
let message = serde_json::to_string(&self.command).unwrap();
|
match (verifying_key, &self.signature) {
|
||||||
verifying_key
|
(Some(key), Some(signature)) => {
|
||||||
.verify(message.as_bytes(), &self.signature)
|
let message = serde_json::to_string(&self.command).unwrap();
|
||||||
.is_ok()
|
key.verify(message.as_bytes(), signature).is_ok()
|
||||||
|
}
|
||||||
|
(Some(_), None) => false,
|
||||||
|
(None, _) => true,
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Deserialize, Serialize, Debug)]
|
#[derive(Deserialize, Serialize, Debug)]
|
||||||
|
#[serde(rename_all = "snake_case")]
|
||||||
enum Command {
|
enum Command {
|
||||||
Create {
|
Create {
|
||||||
incoming_port: u16,
|
incoming_port: u16,
|
||||||
@ -53,14 +59,16 @@ pub struct ProxyResponse {
|
|||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct GlobalState {
|
pub struct GlobalState {
|
||||||
proxies: Mutex<HashMap<Uuid, ProxyState>>,
|
proxies: Mutex<HashMap<Uuid, ProxyState>>,
|
||||||
verifying_key: VerifyingKey,
|
verifying_key: Option<VerifyingKey>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl GlobalState {
|
impl GlobalState {
|
||||||
pub fn new(verifying_key: &str) -> Self {
|
pub fn new<S: AsRef<str>>(verifying_key: Option<S>) -> Self {
|
||||||
Self {
|
Self {
|
||||||
proxies: Mutex::new(HashMap::new()),
|
proxies: Mutex::new(HashMap::new()),
|
||||||
verifying_key: VerifyingKey::from_str(verifying_key).unwrap(),
|
verifying_key: verifying_key
|
||||||
|
.map(|key| VerifyingKey::from_str(key.as_ref()).ok())
|
||||||
|
.flatten(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -263,10 +271,10 @@ mod tests {
|
|||||||
destination_ip: IpAddr::V4(Ipv4Addr::new(127, 0, 0, 1)),
|
destination_ip: IpAddr::V4(Ipv4Addr::new(127, 0, 0, 1)),
|
||||||
id: uuid!("67e55044-10b1-426f-9247-bb680e5fe0c8"),
|
id: uuid!("67e55044-10b1-426f-9247-bb680e5fe0c8"),
|
||||||
},
|
},
|
||||||
signature,
|
signature: Some(signature),
|
||||||
};
|
};
|
||||||
let expected = "{\"command\":{\"Create\":{\"incoming_port\":5555,\"destination_port\":6666,\"\
|
let expected = "{\"create\":{\"incoming_port\":5555,\"destination_port\":6666,\"\
|
||||||
destination_ip\":\"127.0.0.1\",\"id\":\"67e55044-10b1-426f-9247-bb680e5fe0c8\"}},\
|
destination_ip\":\"127.0.0.1\",\"id\":\"67e55044-10b1-426f-9247-bb680e5fe0c8\"},\
|
||||||
\"signature\":\"\
|
\"signature\":\"\
|
||||||
5C912C4B3BFF2ADB49885DCBDB53D6D3041D0632E498CDFF\
|
5C912C4B3BFF2ADB49885DCBDB53D6D3041D0632E498CDFF\
|
||||||
2114CD2DCAC936AB0901B47C411E5BB57FE77BEF96044940\
|
2114CD2DCAC936AB0901B47C411E5BB57FE77BEF96044940\
|
||||||
@ -284,10 +292,9 @@ mod tests {
|
|||||||
command: Command::Delete {
|
command: Command::Delete {
|
||||||
id: uuid!("67e55044-10b1-426f-9247-bb680e5fe0c8"),
|
id: uuid!("67e55044-10b1-426f-9247-bb680e5fe0c8"),
|
||||||
},
|
},
|
||||||
signature,
|
signature: Some(signature),
|
||||||
};
|
};
|
||||||
let expected =
|
let expected = "{\"delete\":{\"id\":\"67e55044-10b1-426f-9247-bb680e5fe0c8\"},\
|
||||||
"{\"command\":{\"Delete\":{\"id\":\"67e55044-10b1-426f-9247-bb680e5fe0c8\"}},\
|
|
||||||
\"signature\":\"\
|
\"signature\":\"\
|
||||||
5C912C4B3BFF2ADB49885DCBDB53D6D3041D0632E498CDFF\
|
5C912C4B3BFF2ADB49885DCBDB53D6D3041D0632E498CDFF\
|
||||||
2114CD2DCAC936AB0901B47C411E5BB57FE77BEF96044940\
|
2114CD2DCAC936AB0901B47C411E5BB57FE77BEF96044940\
|
||||||
@ -314,11 +321,11 @@ mod tests {
|
|||||||
assert_eq!(bytes.len(), 96);
|
assert_eq!(bytes.len(), 96);
|
||||||
let proxy_command = ProxyCommand {
|
let proxy_command = ProxyCommand {
|
||||||
command,
|
command,
|
||||||
signature: bytes.as_slice().try_into().unwrap(),
|
signature: Some(signature),
|
||||||
};
|
};
|
||||||
|
|
||||||
// Verify signed message
|
// Verify signed message
|
||||||
let verifying_key = VerifyingKey::from(&signing_key);
|
let verifying_key = VerifyingKey::from(&signing_key);
|
||||||
assert!(proxy_command.verify_signature(&verifying_key));
|
assert!(proxy_command.verify_signature(&Some(verifying_key)));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -15,9 +15,9 @@ async fn main() {
|
|||||||
|
|
||||||
tracing::subscriber::set_global_default(subscriber).unwrap();
|
tracing::subscriber::set_global_default(subscriber).unwrap();
|
||||||
|
|
||||||
let verifying_key = std::env::args().nth(1).expect("No verifying key provided");
|
let verifying_key = std::env::args().nth(1);
|
||||||
|
|
||||||
let shared_state = Arc::new(GlobalState::new(&verifying_key));
|
let shared_state = Arc::new(GlobalState::new(verifying_key.as_ref()));
|
||||||
// build our application with a route
|
// build our application with a route
|
||||||
let app = Router::new()
|
let app = Router::new()
|
||||||
// `GET /` goes to `root`
|
// `GET /` goes to `root`
|
||||||
|
Loading…
Reference in New Issue
Block a user