57 lines
1.1 KiB
Rust
57 lines
1.1 KiB
Rust
use std::marker::PhantomData;
|
|
use std::time::Duration;
|
|
|
|
use axum_liveview::Html;
|
|
use bincode::config::Configuration;
|
|
use bincode::{Decode, Encode};
|
|
|
|
enum CmdInner<Msg> {
|
|
None,
|
|
Timer(Duration, Msg),
|
|
Batch(Vec<Cmd<Msg>>),
|
|
}
|
|
|
|
pub(crate) struct Cmd<Msg>(CmdInner<Msg>);
|
|
|
|
pub(crate) struct Tea<Msg, Mdl, View, Update> {
|
|
view: View,
|
|
update: Update,
|
|
model: Mdl,
|
|
_msg: PhantomData<Msg>,
|
|
}
|
|
|
|
fn encode<Msg>(msg: Msg) -> String
|
|
where
|
|
Msg: Encode,
|
|
{
|
|
base64::encode(
|
|
bincode::encode_to_vec(msg, Configuration::standard())
|
|
.expect("Message type can be encoded"),
|
|
)
|
|
}
|
|
|
|
fn decode<Msg>(s: &str) -> Result<Msg, Box<dyn std::error::Error>>
|
|
where
|
|
Msg: Decode,
|
|
{
|
|
let bytes = base64::decode(s)?;
|
|
let (msg, _) = bincode::decode_from_slice(&bytes, Configuration::standard())?;
|
|
|
|
Ok(msg)
|
|
}
|
|
|
|
impl<Msg, Mdl, View, Update> Tea<Msg, Mdl, View, Update>
|
|
where
|
|
View: Fn(&Mdl) -> Html,
|
|
Update: Fn(Mdl, Msg) -> (Mdl, Cmd<Msg>),
|
|
Msg: Decode + Encode,
|
|
{
|
|
fn update(mut self, msg: String) -> Self {
|
|
self
|
|
}
|
|
|
|
fn view(&self) -> Html {
|
|
(self.view)(&self.model)
|
|
}
|
|
}
|