aboutsummaryrefslogtreecommitdiffstats
path: root/src/ui.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/ui.rs')
-rw-r--r--src/ui.rs58
1 files changed, 57 insertions, 1 deletions
diff --git a/src/ui.rs b/src/ui.rs
index 5a13bc0..aedf56c 100644
--- a/src/ui.rs
+++ b/src/ui.rs
@@ -1,9 +1,12 @@
+use anyhow::{anyhow, Context};
use std::str::FromStr;
+use axum::Json;
+use log::info;
use serde::Deserialize;
use askama::Template;
use axum::{
extract::State,
- routing::get,
+ routing::{get, post},
Router,
response::Html,
Form,
@@ -11,6 +14,11 @@ use axum::{
};
use tower_http::services::ServeDir;
+use ham_cats::{
+ buffer::Buffer,
+ whisker::Identification,
+};
+
use crate::config;
use crate::SharedState;
@@ -19,6 +27,7 @@ pub async fn serve(port: u16, shared_state: SharedState) {
.route("/", get(dashboard))
.route("/incoming", get(incoming))
.route("/send", get(send))
+ .route("/api/send_packet", post(post_packet))
.route("/settings", get(show_settings).post(post_settings))
.nest_service("/static", ServeDir::new("static"))
/* For an example for timeouts and tracing, have a look at the git history */
@@ -84,6 +93,53 @@ async fn send(State(state): State<SharedState>) -> SendTemplate<'static> {
}
}
+#[derive(Deserialize, Debug)]
+struct ApiSendPacket {
+ comment : Option<String>,
+}
+
+fn build_packet(config: config::Config, comment: Option<String>) -> anyhow::Result<Vec<u8>> {
+ let mut buf = [0; crate::radio::MAX_PACKET_LEN];
+ let mut pkt = ham_cats::packet::Packet::new(&mut buf);
+ pkt.add_identification(
+ Identification::new(&config.callsign, config.ssid, config.icon)
+ .context("Invalid identification")?,
+ )
+ .map_err(|e| anyhow!("Could not add identification to packet: {e}"))?;
+
+ if let Some(c) = comment {
+ pkt.add_comment(&c)
+ .map_err(|e| anyhow!("Could not add comment to packet: {e}"))?;
+ }
+
+ let mut buf2 = [0; crate::radio::MAX_PACKET_LEN];
+ let mut data = Buffer::new_empty(&mut buf2);
+ pkt.fully_encode(&mut data)
+ .map_err(|e| anyhow!("Could not encode packet: {e}"))?;
+
+ Ok(data.to_vec())
+}
+
+async fn post_packet(State(state): State<SharedState>, Json(payload): Json<ApiSendPacket>) -> StatusCode {
+ let (config, transmit_queue) = {
+ let s = state.lock().unwrap();
+ (s.conf.clone(), s.transmit_queue.clone())
+ };
+
+ info!("send_packet {:?}", payload);
+
+ match build_packet(config, payload.comment) {
+ Ok(p) => {
+ info!("Built packet of {} bytes", p.len());
+ match transmit_queue.send(p).await {
+ Ok(()) => StatusCode::OK,
+ Err(_) => StatusCode::BAD_REQUEST,
+ }
+ },
+ Err(_) =>StatusCode::INTERNAL_SERVER_ERROR,
+ }
+}
+
#[derive(Template)]
#[template(path = "settings.html")]
struct SettingsTemplate<'a> {