new debug server outline
This commit is contained in:
@@ -46,35 +46,9 @@ pub async fn debug_server(
|
||||
let change_receiver = WatchStream::new(change_receiver.clone());
|
||||
async move {
|
||||
match (req.method(), req.uri().path()) {
|
||||
(&Method::GET, "/") => Ok(Response::new(Body::from(
|
||||
r#"
|
||||
<script>
|
||||
window.onload = () => {
|
||||
evtSource = new EventSource("/events");
|
||||
evtSource.addEventListener("change", event => {
|
||||
console.log(event);
|
||||
|
||||
const newElement = document.createElement("li");
|
||||
const eventList = document.getElementById("list");
|
||||
newElement.textContent = `change at ${+event.data}`;
|
||||
eventList.appendChild(newElement);
|
||||
});
|
||||
|
||||
evtSource.addEventListener("ping", event => {
|
||||
console.log(event);
|
||||
|
||||
const newElement = document.createElement("li");
|
||||
const eventList = document.getElementById("list");
|
||||
newElement.textContent = `ping at ${+event.data}`;
|
||||
eventList.appendChild(newElement);
|
||||
});
|
||||
};
|
||||
</script>
|
||||
|
||||
<list id="list" />
|
||||
|
||||
"#,
|
||||
))),
|
||||
(&Method::GET, "/") => Ok(Response::new(Body::from(include_str!(
|
||||
concat!(env!("OUT_DIR"), "/minified.html")
|
||||
)))),
|
||||
|
||||
(&Method::GET, "/data") => {
|
||||
let res = Response::builder().header("Cache-Control", "no-store");
|
||||
|
||||
@@ -2,6 +2,7 @@ use std::{ffi::CStr, fmt::Debug};
|
||||
|
||||
use bytemuck::{Pod, Zeroable};
|
||||
use eyre::eyre;
|
||||
use serde::Serialize;
|
||||
use tokio::{
|
||||
io::{AsyncReadExt, AsyncWriteExt},
|
||||
net::tcp::{ReadHalf, WriteHalf},
|
||||
@@ -68,14 +69,14 @@ impl PacketKind {
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Default, Clone, Copy, Pod, Zeroable)]
|
||||
#[derive(Serialize, Default, Clone, Copy, Pod, Zeroable)]
|
||||
#[repr(C)]
|
||||
pub struct Header {
|
||||
pub kind: u8,
|
||||
pub length: u8,
|
||||
}
|
||||
|
||||
#[derive(Default, Clone)]
|
||||
#[derive(Serialize, Default, Clone)]
|
||||
pub struct Packet {
|
||||
pub header: Header,
|
||||
pub data: Vec<u8>,
|
||||
|
||||
45
src/ports.rs
45
src/ports.rs
@@ -10,7 +10,7 @@ use std::{
|
||||
};
|
||||
|
||||
use eyre::eyre;
|
||||
use serde::{Deserialize, Serialize};
|
||||
use serde::{Deserialize, Serialize, Serializer};
|
||||
use tokio::{
|
||||
net::TcpListener,
|
||||
sync::{watch::Receiver, Mutex},
|
||||
@@ -27,19 +27,21 @@ use crate::{
|
||||
|
||||
#[derive(Default, Serialize, Deserialize)]
|
||||
pub struct PortHandler {
|
||||
#[serde(skip)]
|
||||
#[serde(skip_deserializing)]
|
||||
#[serde(serialize_with = "serialize_last_update")]
|
||||
pub last_update: Option<std::time::Instant>,
|
||||
|
||||
#[serde(skip)]
|
||||
pub change_sender: Option<tokio::sync::watch::Sender<std::time::Instant>>,
|
||||
|
||||
#[serde(skip)]
|
||||
#[serde(skip_deserializing)]
|
||||
port_guards: HashMap<Port, Rejector>,
|
||||
|
||||
allowed_ports: AllowedList,
|
||||
|
||||
#[serde(skip)]
|
||||
free_ports: HashSet<Port>,
|
||||
|
||||
errored_ports: BTreeSet<(UnixTimestamp, Port)>,
|
||||
allocated_ports: HashMap<Number, Port>,
|
||||
|
||||
@@ -50,6 +52,23 @@ pub struct PortHandler {
|
||||
pub names: HashMap<Number, String>,
|
||||
}
|
||||
|
||||
#[allow(clippy::missing_errors_doc)]
|
||||
pub fn serialize_last_update<S: Serializer>(
|
||||
last_update: &Option<std::time::Instant>,
|
||||
serializer: S,
|
||||
) -> Result<S::Ok, S::Error> {
|
||||
last_update
|
||||
.and_then(|instant| {
|
||||
Some(
|
||||
(SystemTime::now() + instant.elapsed())
|
||||
.duration_since(UNIX_EPOCH)
|
||||
.ok()?
|
||||
.as_secs(),
|
||||
)
|
||||
})
|
||||
.serialize(serializer)
|
||||
}
|
||||
|
||||
#[instrument(skip(port_handler, change_receiver))]
|
||||
pub async fn cache_daemon(
|
||||
port_handler: Arc<Mutex<PortHandler>>,
|
||||
@@ -151,9 +170,16 @@ impl PortHandler {
|
||||
#[instrument(skip(self))]
|
||||
pub fn store(&self, cache: &Path) -> std::io::Result<()> {
|
||||
debug!("storing cache");
|
||||
let temp_file = cache.with_extension(".temp");
|
||||
let temp_file = cache.with_extension("temp");
|
||||
|
||||
serde_json::to_writer(BufWriter::new(File::create(&temp_file)?), self)?;
|
||||
let mut value = serde_json::to_value(self)?;
|
||||
|
||||
let value_object = value.as_object_mut().unwrap();
|
||||
|
||||
value_object.remove("port_guards").unwrap();
|
||||
value_object.remove("last_update").unwrap();
|
||||
|
||||
serde_json::to_writer(BufWriter::new(File::create(&temp_file)?), &value)?;
|
||||
std::fs::rename(temp_file, cache)?;
|
||||
|
||||
Ok(())
|
||||
@@ -259,6 +285,15 @@ struct Rejector {
|
||||
handle: JoinHandle<()>,
|
||||
}
|
||||
|
||||
impl Serialize for Rejector {
|
||||
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
|
||||
where
|
||||
S: Serializer,
|
||||
{
|
||||
self.state.1.serialize(serializer)
|
||||
}
|
||||
}
|
||||
|
||||
impl Debug for Rejector {
|
||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||
f.debug_struct("Rejector")
|
||||
|
||||
Reference in New Issue
Block a user