use std::{sync::Arc, time::Duration};
use axum::{Router, routing::post};
use lexe_api_core::error::BackendApiError;
use lexe_common::net;
use lexe_tokio::notify_once::NotifyOnce;
use serde::{Deserialize, Serialize};
use tracing::info_span;
use crate::{
rest::RestClient,
server::{self, LayerConfig, LxJson},
};
pub async fn do_http_request(
client_config: rustls::ClientConfig,
server_config: Arc<rustls::ServerConfig>,
server_dns: &str,
) {
#[derive(Serialize, Deserialize)]
struct TestRequest {
data: String,
}
#[derive(Serialize, Deserialize)]
struct TestResponse {
data: String,
}
async fn handler(
LxJson(TestRequest { mut data }): LxJson<TestRequest>,
) -> LxJson<TestResponse> {
data.push_str(", world");
LxJson(TestResponse { data })
}
let router = Router::new().route("/test_endpoint", post(handler));
let shutdown = NotifyOnce::new();
let tls_and_dns = Some((server_config, server_dns));
const TEST_SPAN_NAME: &str = "(test-server)";
let (server_task, server_url) = server::spawn_server_task(
net::LOCALHOST_WITH_EPHEMERAL_PORT,
router,
LayerConfig::default(),
tls_and_dns,
TEST_SPAN_NAME.into(),
info_span!(parent: None, TEST_SPAN_NAME),
shutdown.clone(),
)
.expect("Failed to spawn test server");
let rest = RestClient::new("test-client", "test-server", client_config);
let req = TestRequest {
data: "hello".to_owned(),
};
let http_req = rest.post(format!("{server_url}/test_endpoint"), &req);
let resp: TestResponse = rest
.send::<_, BackendApiError>(http_req)
.await
.expect("Request failed");
assert_eq!(resp.data, "hello, world");
shutdown.send();
tokio::time::timeout(Duration::from_secs(5), server_task)
.await
.expect("Server shutdown timed out")
.expect("Server task panicked");
}