Files
2026-07-10 15:02:09 +01:00

86 lines
3.6 KiB
TOML

[package]
name = "skald-relay-server"
version = "0.1.0"
edition = "2024"
description = "Skald Remote Control relay: zero-trust store-and-forward + push bridge (see data/ios-app/relay.md)"
license = "MIT"
# Main binary (the relay). Deploy entrypoint is /skald-relay-server.
# Frame types + crypto live in the shared `skald-relay-common` crate; the
# `gen-vectors` reference generator (crypto interop test vectors,
# data/ios-app/test-vectors.md §3) moved there too (run with
# `cargo run -p skald-relay-common --bin gen-vectors`).
[dependencies]
# --- shared frame types + crypto (frames + verify/namespace subset) ---
skald-relay-common = { path = "../skald-relay-common" }
# --- async runtime + web/WS ---
axum = { version = "0.8", features = ["ws"] }
tokio = { version = "1", features = ["full"] }
tokio-util = { version = "0.7", features = ["rt"] }
futures-util = "0.3"
# --- serde / frames ---
serde = { version = "1", features = ["derive"] }
serde_json = "1"
async-trait = "0.1"
# --- persistence ---
sqlx = { version = "0.9.0", features = ["runtime-tokio", "sqlite"] }
# --- encoding used directly in the WS handler ---
hex = "0.4"
base64 = "0.22"
rand = "0.8" # CSPRNG for the 32-byte challenge nonce
# --- v2 wire format (data/ios-app/v2/relay-protocol.md) ---
# `prost`: matches the major used by `skald-relay-common` so the
# generated `proto::v2::RelayFrame` types here are the same compile-time
# ones the common crate re-exports. `bytes`: `prost` 0.13 generates
# `bytes` fields as `prost::bytes::Bytes`; we use the crate directly in
# the WS handler to build zero-copy frame payloads.
prost = "0.13"
bytes = "1"
# --- observability + misc ---
anyhow = "1"
tracing = "0.1"
tracing-subscriber = { version = "0.3", features = ["env-filter"] }
tracing-appender = "0.2"
chrono = { version = "0.4", default-features = false, features = ["clock", "std"] }
# --- push-live senders (optional, off by default) ---
# reqwest: HTTP/2 client for APNs (`http2` enables ALPN h2, `rustls-no-provider`
# uses rustls without pulling a crypto provider — the binary installs `ring`
# as the process default, avoiding any OpenSSL/aws-lc C build; `json` matches
# the body type).
# jsonwebtoken: ES256 JWT signing for APNs provider auth tokens.
# `use_pem` lets us load the .p8 PEM directly; `p256` covers Apple's ES256
# algorithm (the only curve APNs accepts) without pulling a separate crypto
# crate.
# uuid: APNs requires a unique `apns-id` per message so retries are de-duped.
reqwest = { version = "0.13", default-features = false, features = ["http2", "json", "rustls-no-provider"], optional = true }
jsonwebtoken = { version = "9", features = ["use_pem"], optional = true }
uuid = { version = "1", features = ["v4"], optional = true }
[features]
default = []
# Live push senders (need real APNs/FCM credentials). Off by default so the
# relay builds & runs without external creds; the normative decision/payload
# logic is always compiled and unit-tested. See push.rs.
push-live = ["dep:reqwest", "dep:jsonwebtoken", "dep:uuid"]
[dev-dependencies]
# WebSocket client used by the protocol integration tests (tests/protocol.rs).
tokio-tungstenite = "0.29"
# Sign challenges / compute namespace_id from the test harness side.
ed25519-dalek = "2"
sha2 = "0.10"
# The integration test constructs the same protobuf `RelayFrame`s the relay
# sends on the wire (data/ios-app/v2/relay-protocol.md) — prost matches the
# generator used by `skald-relay-common`, bytes is the `Bytes` type prost 0.13
# generates for `bytes` fields.
prost = "0.13"
bytes = "1"