aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/config.rs98
-rw-r--r--src/main.rs3
-rw-r--r--src/ui.rs8
-rw-r--r--static/settings.js1
-rw-r--r--templates/settings.html3
5 files changed, 105 insertions, 8 deletions
diff --git a/src/config.rs b/src/config.rs
index 54f94dd..64f3c09 100644
--- a/src/config.rs
+++ b/src/config.rs
@@ -1,11 +1,13 @@
-use std::fs;
+use std::{collections::HashMap, fs};
use anyhow::Context;
use serde::{Deserialize, Serialize};
+use serde_json::json;
type Protection = u8;
#[derive(Debug, Serialize, Deserialize, Clone)]
pub struct Service {
+ pub unique_id: String,
pub sid: u32,
pub ecc: u8,
pub label: String,
@@ -23,6 +25,30 @@ impl Service {
pub fn ecc_hex(&self) -> String {
format!("{:02X}", self.ecc)
}
+
+ pub fn dump_to_service_json(&self) -> serde_json::Value {
+ json!({
+ "id": self.sid,
+ "ecc": self.ecc,
+ "label": self.label,
+ "shortlabel": self.shortlabel,
+ })
+ }
+
+ pub fn dump_to_subchannel_json(&self, id: u32) -> serde_json::Value {
+ json!({
+ "type": "dabplus",
+ "bitrate": self.bitrate,
+ "id": id,
+ "protection": self.protection,
+
+ "inputproto": "edi",
+ "inputuri": format!("tcp://127.0.0.1:{}", self.input_port),
+ "buffer-management": "prebuffering",
+ "buffer": 40,
+ "prebuffering": 20
+ })
+ }
}
#[derive(Debug, Serialize, Deserialize, Clone)]
@@ -62,6 +88,7 @@ impl Default for Config {
output_edi_port: 8951,
services: vec![
Service {
+ unique_id: "nothing".to_owned(),
sid: 0x4DAA,
ecc: 0xE1,
label: "nothing".to_owned(),
@@ -92,4 +119,73 @@ impl Config {
fs::write(CONFIGFILE, toml::to_string_pretty(&self)?)
.context("writing config file")
}
+
+ pub fn dump_to_json(&self) -> serde_json::Value {
+ let now = chrono::Utc::now().to_rfc3339();
+
+ let mut services = HashMap::new();
+ for s in &self.services {
+ let uid = format!("srv-{}", s.unique_id);
+ services.insert(uid, s.dump_to_service_json());
+ }
+
+ let mut subchannels = HashMap::new();
+ let mut id = 0;
+ for s in &self.services {
+ id += 1;
+ let uid = format!("sub-{}", s.unique_id);
+ subchannels.insert(uid, s.dump_to_subchannel_json(id));
+ }
+
+ let mut components = HashMap::new();
+ for s in &self.services {
+ components.insert(
+ format!("comp-{}", s.unique_id),
+ json!({
+ "service": format!("srv-{}", s.unique_id),
+ "subchannel": format!("sub-{}", s.unique_id),
+ "user-applications": {
+ "userapp": "slideshow"
+ }
+ }));
+ }
+
+ json!({
+ "_comment": format!("Generated at {} by odr-dabmux-gui", now),
+ "general": {
+ "dabmode": 1,
+ "nbframes": 0,
+ "syslog": false,
+ "tist": self.tist,
+ "tist_offset": self.tist_offset,
+ "managementport": 12720
+ },
+ "remotecontrol": {
+ "telnetport": 12721,
+ "zmqendpoint": "tcp://lo:12722"
+ },
+ "ensemble": {
+ "id": self.ensemble_id,
+ "ecc": self.ensemble_ecc,
+ "local-time-offset": "auto",
+ "reconfig-counter": "hash",
+ "label": self.ensemble_label,
+ "shortlabel": self.ensemble_shortlabel
+ },
+ "services": services,
+ "subchannels": subchannels,
+ "components": components,
+ "outputs": {
+ "throttle": "simul://",
+ "edi": {
+ "destinations": {
+ "example_tcp": {
+ "protocol": "tcp",
+ "listenport": self.output_edi_port
+ }
+ }
+ }
+ }
+ })
+ }
}
diff --git a/src/main.rs b/src/main.rs
index 66fbe23..4ff491b 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -1,6 +1,5 @@
use std::sync::{Arc, Mutex};
-use anyhow::{anyhow, Context};
-use log::{debug, info, warn, error};
+use log::info;
mod ui;
mod config;
diff --git a/src/ui.rs b/src/ui.rs
index 6bcb04d..a5be6a5 100644
--- a/src/ui.rs
+++ b/src/ui.rs
@@ -1,19 +1,15 @@
use std::net::SocketAddr;
-use anyhow::{anyhow, Context};
use askama::Template;
use axum::{
- Form,
Json,
Router,
extract::State,
- extract::{ws::{Message, WebSocket, WebSocketUpgrade}, ConnectInfo},
http::StatusCode,
- response::IntoResponse,
routing::{get, post},
};
use serde::Deserialize;
-use log::{debug, info, warn, error};
+use log::info;
use tower_http::services::ServeDir;
use crate::config;
@@ -150,6 +146,8 @@ async fn post_settings(
Ok(()) => {
state.lock().unwrap().conf.clone_from(&conf);
+ info!("{}", conf.dump_to_json());
+
(StatusCode::OK, SettingsAppliedTemplate {
title: "Settings",
conf,
diff --git a/static/settings.js b/static/settings.js
index 287f6f6..7f5a067 100644
--- a/static/settings.js
+++ b/static/settings.js
@@ -26,6 +26,7 @@ async function btn_settings_send() {
const destList = services.querySelectorAll("p.service");
for (let i = 0; i < destList.length; i++) {
data.services.push({
+ 'unique_id': destList[i].querySelector("input.srv_unique_id").value,
'sid': parseInt(destList[i].querySelector("input.srv_sid").value, 16),
'ecc': parseInt(destList[i].querySelector("input.srv_ecc").value, 16),
'label': destList[i].querySelector("input.srv_label").value,
diff --git a/templates/settings.html b/templates/settings.html
index ca9a77a..74843fb 100644
--- a/templates/settings.html
+++ b/templates/settings.html
@@ -37,6 +37,7 @@
<div class="section">
<template id="service_template">
<p class="service">
+ <input class="textinput srv_unique_id" type="text" placeholder="Service Unique ID">
<input class="textinput srv_sid" type="text" placeholder="Service ID in hex">
<input class="textinput srv_ecc" type="text" placeholder="Service ECC in hex">
<input class="textinput srv_label" type="text" placeholder="Service Label">
@@ -50,6 +51,8 @@
<div id="services">
{% for srv in conf.services %}
<p class="service">
+ <input class="textinput srv_unique_id" type="text" placeholder="Service Unique ID"
+ value="{{ srv.unique_id }}">
<input class="textinput srv_sid" type="text" placeholder="Service ID in hex"
value="{{ srv.sid_hex() }}">
<input class="textinput srv_ecc" type="text" placeholder="Service ECC in hex"