From 74af08840122993ff1d4536fe8d082dfb541b09c Mon Sep 17 00:00:00 2001 From: Ian Jackson Date: Wed, 14 Oct 2020 23:12:49 +0100 Subject: [PATCH] wip format timestamps Before try into Signed-off-by: Ian Jackson --- Cargo.lock.example | 1 + Cargo.toml | 1 + src/cmdlistener.rs | 2 +- src/gamestate.rs | 7 +++++++ src/global.rs | 22 +++++++++++++++++----- src/imports.rs | 4 ++++ src/sse.rs | 9 +++++---- src/updates.rs | 22 +++++++++++++++++----- templates/script.ts | 2 +- 9 files changed, 54 insertions(+), 16 deletions(-) diff --git a/Cargo.lock.example b/Cargo.lock.example index 7d8c4cfa..28229ab7 100644 --- a/Cargo.lock.example +++ b/Cargo.lock.example @@ -1057,6 +1057,7 @@ dependencies = [ "rocket_cors", "serde", "serde_json", + "serde_with", "slotmap", "thiserror", "toml 0.5.6", diff --git a/Cargo.toml b/Cargo.toml index 99dd5c51..7a45ae70 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -46,6 +46,7 @@ rmp-serde = "0.14" rocket_cors = "0.5" serde = { version = "1", features = ["derive","rc"] } serde_json = "1" +serde_with = "1" slotmap = { version = "0.4", features = ['serde'] } thiserror = "1" toml = "0.5" diff --git a/src/cmdlistener.rs b/src/cmdlistener.rs index 47a7d698..6bad6eae 100644 --- a/src/cmdlistener.rs +++ b/src/cmdlistener.rs @@ -166,7 +166,7 @@ fn execute_game_insn(cs: &CommandStream, html: Html(format!("{} added a player: {}", &who, htmlescape::encode_minimal(&pl.nick))), }; - let (player, logentry) = ig.player_new(pl, logentry)?; + let (player, logentry) = ig.player_new(pl, Timezone{}, logentry)?; (U{ pcs: vec![], log: vec![ logentry ], raw: None }, diff --git a/src/gamestate.rs b/src/gamestate.rs index 340aac71..db536c7c 100644 --- a/src/gamestate.rs +++ b/src/gamestate.rs @@ -27,6 +27,9 @@ pub struct Html (pub String); #[serde(transparent)] pub struct Timestamp(pub u64); /* time_t */ +#[derive(Clone,Debug,Default,Serialize,Deserialize)] +pub struct Timezone { } // todo + pub const DEFAULT_TABLE_SIZE : Pos = PosC([ 400, 200 ]); // ---------- general data types ---------- @@ -169,6 +172,10 @@ impl Timestamp { .as_secs(); Timestamp(now) } + + pub fn render(&self, tz: &Timezone) -> String { + format!("TS{}(@{:?})", self.0, tz) + } } pub trait ClampTable : Sized { diff --git a/src/global.rs b/src/global.rs index 3bb35141..ba335682 100644 --- a/src/global.rs +++ b/src/global.rs @@ -193,6 +193,12 @@ pub struct InstanceContainer { struct InstanceSaveAccesses { pieces: PiecesLoadedRef, tokens_players: Vec<(RawTokenStr, PlayerId)>, + aplayers: SecondarySlotMap, +} + +#[derive(Debug,Default,Serialize,Deserialize)] +struct PlayerSaveAccess { + tz: Timezone, } display_as_debug!{InstanceLockError} @@ -352,7 +358,7 @@ impl InstanceGuard<'_> { /// caller is responsible for logging; threading it through /// proves the caller has a log entry. #[throws(MgmtError)] - pub fn player_new(&mut self, newplayer: PlayerState, + pub fn player_new(&mut self, newplayer: PlayerState, tz: Timezone, logentry: LogEntry) -> (PlayerId, LogEntry) { // saving is fallible, but we can't attempt to save unless // we have a thing to serialise with the player in it @@ -366,7 +372,7 @@ impl InstanceGuard<'_> { })?; (||{ let pu_bc = PlayerUpdates::new_begin(&self.c.g.gs); - self.c.g.updates.insert(player, pu_bc.new()); + self.c.g.updates.insert(player, pu_bc.new(tz)); })(); // <- No ?, ensures that IEFE is infallible (barring panics) (player, logentry) } @@ -685,7 +691,11 @@ impl InstanceGuard<'_> { .flatten() .collect() }; - let isa = InstanceSaveAccesses { pieces, tokens_players }; + let aplayers = s.c.g.updates.iter().map( + |(player, PlayerUpdates { tz, .. })| + (player, PlayerSaveAccess { tz: tz.clone() }) + ).collect(); + let isa = InstanceSaveAccesses { pieces, tokens_players, aplayers }; rmp_serde::encode::write_named(w, &isa) })?; self.c.access_dirty = false; @@ -718,7 +728,8 @@ impl InstanceGuard<'_> { } } let InstanceSaveAccesses:: - { mut tokens_players, mut pieces } = Self::load_something(&name, "a-") + { mut tokens_players, mut pieces, mut aplayers } + = Self::load_something(&name, "a-") .or_else(|e| { if let InternalError::Anyhow(ae) = &e { if let Some(ioe) = ae.downcast_ref::() { @@ -744,7 +755,8 @@ impl InstanceGuard<'_> { let mut updates : SecondarySlotMap<_,_> = Default::default(); let pu_bc = PlayerUpdates::new_begin(&gs); for player in gs.players.keys() { - updates.insert(player, pu_bc.new()); + let aplayer = aplayers.remove(player).unwrap_or_default(); + updates.insert(player, pu_bc.new(aplayer.tz)); } let name = Arc::new(name); tokens_players.retain( diff --git a/src/imports.rs b/src/imports.rs index 155adc52..e86d1989 100644 --- a/src/imports.rs +++ b/src/imports.rs @@ -41,6 +41,7 @@ pub use fehler::{throws,throw}; pub use serde::{Serialize,Deserialize,de::DeserializeOwned}; pub use serde::{Serializer,Deserializer}; +pub use serde::ser::SerializeTuple; pub use rocket_contrib::helmet::*; pub use rocket_contrib::templates::Template; @@ -93,6 +94,9 @@ pub use itertools::Itertools; pub use rental::RentalError; pub use rental::common::RentRef; +pub use serde_with; +pub use serde_with::serde_as; + pub use ordered_float::OrderedFloat; pub use crate::global::*; diff --git a/src/sse.rs b/src/sse.rs index 8af08b0a..4910ff90 100644 --- a/src/sse.rs +++ b/src/sse.rs @@ -48,9 +48,10 @@ struct FlushWouldBlockError{} impl UpdateReaderWN { #[throws(io::Error)] - fn write_next(&mut self, mut buf: &mut U, next: &PreparedUpdate) + fn write_next(&mut self, mut buf: &mut U, tz: &Timezone, + next: &PreparedUpdate) where U : Write { - let tu = next.for_transmit(self.client); + let tu = next.for_transmit(tz, self.client); write!(buf, "data: ")?; serde_json::to_writer(&mut buf, &tu)?; @@ -123,7 +124,7 @@ impl Read for UpdateReader { } self.overflow = { let mut overflow = Vec::with_capacity(next_len); - self.wn.write_next(&mut overflow, &next) + self.wn.write_next(&mut overflow, &pu.tz, &next) .map_err(|e| self.wn.trouble("overflow.write_next",&e))?; debug!("overflow {} {}, len={}", &self.wn.player, &self.wn.client, &overflow.len()); @@ -132,7 +133,7 @@ impl Read for UpdateReader { continue; } - self.wn.write_next(&mut buf, &next) + self.wn.write_next(&mut buf, &pu.tz, &next) .map_err(|e| self.wn.trouble("UpdateReader.write_next",&e))?; let before = next.when - UPDATE_EXPIRE; diff --git a/src/updates.rs b/src/updates.rs index 11df724f..e5e5c491 100644 --- a/src/updates.rs +++ b/src/updates.rs @@ -30,6 +30,7 @@ pub type PlayerUpdatesLog = pub struct PlayerUpdates { log : PlayerUpdatesLog, cv : Arc, + pub tz: Timezone, } #[derive(Debug)] @@ -103,7 +104,8 @@ enum TransmitUpdateEntry<'u> { ns: &'u PreparedPieceState, }, SetTableSize(Pos), - Log (&'u CommittedLogEntry), + #[serde(serialize_with="serialize_logentry")] + Log (&'u Timezone, &'u CommittedLogEntry), Error(&'u ErrorSignaledViaUpdate), } @@ -117,11 +119,11 @@ pub struct PlayerUpdatesBuildContext { } impl PlayerUpdatesBuildContext { - pub fn new(&self) -> PlayerUpdates { + pub fn new(&self, tz: Timezone) -> PlayerUpdates { let mut log = StableIndexVecDeque::with_capacity(50); log.push_back(self.u1.clone()); let cv = Default::default(); - PlayerUpdates { log, cv } + PlayerUpdates { log, tz, cv } } } @@ -438,7 +440,8 @@ impl<'r> Drop for PrepareUpdatesBuffer<'r> { type WRC = WhatResponseToClientOp; impl PreparedUpdate { - pub fn for_transmit(&self, dest : ClientId) -> TransmitUpdate { + pub fn for_transmit<'u>(&'u self, tz: &'u Timezone, dest : ClientId) + -> TransmitUpdate<'u> { type ESVU = ErrorSignaledViaUpdate; type PUE = PreparedUpdateEntry; type TUE<'u> = TransmitUpdateEntry<'u>; @@ -477,7 +480,7 @@ impl PreparedUpdate { } }, PUE::Log(logent) => { - TUE::Log(&logent) + TUE::Log(&tz, &logent) }, &PUE::SetTableSize(size) => { TUE::SetTableSize(size) @@ -498,3 +501,12 @@ impl PreparedUpdate { TransmitUpdate(self.gen, ents) } } + +fn serialize_logentry(tz: &Timezone, logent: &CommittedLogEntry, + s:S) -> Result { + let mut tup = s.serialize_tuple(2)?; + let ts = logent.when.render(&tz); + tup.serialize_element(&ts)?; + tup.serialize_element(&logent.logent)?; + tup.end() +} diff --git a/templates/script.ts b/templates/script.ts index 9f38f0a4..b3efaeb6 100644 --- a/templates/script.ts +++ b/templates/script.ts @@ -778,7 +778,7 @@ function drag_cancel() { // ----- logs ----- messages.Log = function -(j: { when: Timestamp, logent: { html: string } }) { +(j: { when: string, logent: { html: string } }) { add_log_message(j.when + '|' + j.logent.html); } -- 2.30.2