feat: http server based key package registry (#124)

* feat: http server based key package registry

* chore: instructions on running the registration service

* chore: remove duplicate post param

* chore: revert out sourced account id for multi devices support

* feat: signature on account id and key packages

* chore: include http registry in contact registry module

* refactor: use device id for retrieve key package

* chore: use string for device id

* feat: server verification on the register

* chore: doc the smoke test

* chore: fix data folder non exist

* chore: use payload for register and retrieve

* chore: fix clippy
This commit is contained in:
kaichao
2026-06-04 10:09:29 +08:00
committed by GitHub
parent 6f5838af51
commit cd7dd6a330
23 changed files with 1825 additions and 53 deletions
+42 -15
View File
@@ -8,7 +8,7 @@ use std::sync::mpsc;
use anyhow::{Context, Result};
use clap::{Parser, ValueEnum};
use logos_chat::DeliveryService;
use logos_chat::{ChatClient, DeliveryService, HttpRegistry, RegistrationService, StorageConfig};
use app::ChatApp;
@@ -55,6 +55,12 @@ struct Cli {
/// Initialize and immediately exit without launching the TUI (for CI).
#[arg(long)]
smoketest: bool,
/// Optional KeyPackage registry base URL. When set, uses the HTTP-backed
/// registry instead of the in-memory `EphemeralRegistry`.
/// Example: `--registry-url http://localhost:8080`.
#[arg(long)]
registry_url: Option<String>,
}
fn main() -> Result<()> {
@@ -104,18 +110,38 @@ fn run<D: DeliveryService + 'static>(
.to_str()
.context("db path contains non-UTF-8 characters")?
.to_string();
let storage = StorageConfig::Encrypted {
path: db_str,
key: "chat-cli".to_string(),
};
let client = logos_chat::ChatClient::open(
cli.name.clone(),
logos_chat::StorageConfig::Encrypted {
path: db_str,
key: "chat-cli".to_string(),
},
transport,
)
.map_err(|e| anyhow::anyhow!("{e:?}"))
.context("failed to open chat client")?;
match cli.registry_url.as_deref() {
Some(url) => {
let registry = HttpRegistry::new(url);
let client =
ChatClient::open_with_registry(cli.name.clone(), storage, transport, registry)
.map_err(|e| anyhow::anyhow!("{e:?}"))
.context("failed to open chat client with HTTP registry")?;
launch_tui(client, inbound, cli)
}
None => {
let client = ChatClient::open(cli.name.clone(), storage, transport)
.map_err(|e| anyhow::anyhow!("{e:?}"))
.context("failed to open chat client")?;
launch_tui(client, inbound, cli)
}
}
}
fn launch_tui<D, R>(
client: ChatClient<D, R>,
inbound: mpsc::Receiver<Vec<u8>>,
cli: &Cli,
) -> Result<()>
where
D: DeliveryService + 'static,
R: RegistrationService + 'static,
{
let mut app = ChatApp::new(client, inbound, &cli.name, &cli.data)?;
if cli.smoketest {
@@ -193,10 +219,11 @@ fn run_logos_delivery(cli: Cli) -> Result<()> {
)
}
fn run_app<D: DeliveryService + 'static>(
terminal: &mut ui::Tui,
app: &mut ChatApp<D>,
) -> Result<()> {
fn run_app<D, R>(terminal: &mut ui::Tui, app: &mut ChatApp<D, R>) -> Result<()>
where
D: DeliveryService + 'static,
R: RegistrationService + 'static,
{
loop {
app.process_incoming()?;
terminal.draw(|frame| ui::draw(frame, app))?;