# Noise Keys

> UCall for Rust

Interfaces and calls can run over the Noise protocol instead of plain TCP, authenticating both sides by 32-byte Curve25519 static keys.

```rust
use std::sync::Arc;
use ucall::*;

let (server_private_key, server_public_key) = generate_noise_keypair()?;
let (client_private_key, _) = generate_noise_keypair()?;
let client_public_key = derive_noise_public_key(&client_private_key);

let sealed = Interface::new("0.0.0.0:8546")
    .security(Security::NoiseXX, server_private_key)
    .peer_authorizer(move |key: &NoiseKey| *key == client_public_key);
let server = Server::new(&[sealed])?;

let client = Client::new(ClientOptions {
    connections: 1,
    noise_private_key: Some(client_private_key),
    peer_authorizer: Some(Arc::new(move |key: &NoiseKey| *key == server_public_key)),
    ..Default::default()
})?;
```

`generate_noise_keypair` draws from the operating system's entropy and fails with `Status::IO` when it is refused.
`derive_noise_public_key` recovers the public half of a stored private key, which peers compare in their authorizers.
Under Noise XX both sides learn each other's key during the handshake, so both need an authorizer; Noise IK has the client name the server's key in advance through `ClientCallOptions::noise_peer_key`.
Noise KK has both sides know each other in advance: the interface admits the one key `Interface::noise_peer_key` names, and the call presents `ClientCallOptions::noise_private_key` or the client's own key.
An `http+noise://` URL implies Noise XX, and a handler reads the client's authenticated key through `Request::peer`.

`use ucall::Security;`

`use ucall::*;`

## NoiseKey

A 32-byte Curve25519 key, private or public, as every Noise handshake takes it.

```rust
pub type NoiseKey = [u8; 32];
```

## PeerAuthorizer

Decides whether a peer presenting an authenticated static key may proceed past the handshake.

```rust
pub type PeerAuthorizer = dyn Fn(&NoiseKey) -> bool + Send + Sync;
```

A server runs it on the polling thread completing the handshake, and a client on its owner
thread inside [`Client::take_completed`](https://www.unum.cloud/docs/ucall/rust/calling.md#take_completed). A panic rejects the
peer.

## Security

The transport security of a server interface or a client call.

```rust
pub enum Security
```

- `None`: Plain TCP.
- `NoiseXX`: Noise XX: both parties learn each other's static keys during the handshake.
- `NoiseIK`: Noise IK: the client knows the server's static key in advance.
- `NoiseKK`: Noise KK: both parties know each other's static keys in advance; client calls only.

Implements: `Clone`, `Copy`, `StructuralPartialEq`, `PartialEq`, `Eq`, [`Debug`](https://www.unum.cloud/docs/ucall/rust/serving.md#Debug), `Hash`, `Default`

## generate_noise_keypair

Draws a fresh `(private_key, public_key)` pair from the operating system's entropy.

```rust
pub fn generate_noise_keypair() -> Result<(NoiseKey, NoiseKey)>
```

Fails with [`Status::IO`](https://www.unum.cloud/docs/ucall/rust/errors.md#IO) when the operating system refuses entropy.

```
use ucall::{derive_noise_public_key, generate_noise_keypair};

let (private_key, public_key) = generate_noise_keypair()?;
assert_eq!(derive_noise_public_key(&#x26;private_key), public_key);
```

## derive_noise_public_key

The public key of `private_key`, as a [`PeerAuthorizer`](#PeerAuthorizer) on the other side sees it.

```rust
pub fn derive_noise_public_key(private_key: &NoiseKey) -> NoiseKey
```

