|
1 | | -use std::fmt::Display; |
2 | | - |
3 | | -/// Types that can generate their own keys for persistent storage |
4 | | -pub trait Value: serde::Serialize + serde::de::DeserializeOwned + Sized + Clone { |
5 | | - type Key: AsRef<[u8]> + Clone + Display; |
6 | | - |
7 | | - /// Unique identifier for this persisted value |
8 | | - fn key(&self) -> Self::Key; |
9 | | -} |
10 | | - |
11 | | -/// Implemented types that should be persisted by the application. |
12 | | -pub trait Persister<V: Value> { |
13 | | - type Token: From<V>; |
14 | | - type Error: std::error::Error + Send + Sync + 'static; |
15 | | - |
16 | | - fn save(&mut self, value: V) -> Result<Self::Token, Self::Error>; |
17 | | - fn load(&self, token: Self::Token) -> Result<V, Self::Error>; |
18 | | -} |
19 | | - |
20 | | -/// A key type that stores the value itself for no-op persistence |
21 | | -#[derive(Debug, Clone, serde::Serialize)] |
22 | | -pub struct NoopToken<V: Value>(V); |
23 | | - |
24 | | -impl<V: Value> AsRef<[u8]> for NoopToken<V> { |
25 | | - fn as_ref(&self) -> &[u8] { |
26 | | - // Since this is a no-op implementation, we can return an empty slice |
27 | | - // as we never actually need to use the bytes |
28 | | - &[] |
29 | | - } |
30 | | -} |
31 | | - |
32 | | -impl<'de, V: Value> serde::Deserialize<'de> for NoopToken<V> { |
33 | | - fn deserialize<D>(deserializer: D) -> Result<Self, D::Error> |
34 | | - where |
35 | | - D: serde::Deserializer<'de>, |
36 | | - { |
37 | | - Ok(NoopToken(V::deserialize(deserializer)?)) |
38 | | - } |
39 | | -} |
40 | | - |
41 | | -impl<V: Value> Value for NoopToken<V> { |
42 | | - type Key = V::Key; |
43 | | - |
44 | | - fn key(&self) -> Self::Key { self.0.key() } |
45 | | -} |
46 | | - |
47 | | -/// A persister that does nothing but store values in memory |
48 | | -#[derive(Debug, Clone)] |
49 | | -pub struct NoopPersister; |
50 | | - |
51 | | -impl<V: Value> From<V> for NoopToken<V> { |
52 | | - fn from(value: V) -> Self { NoopToken(value) } |
53 | | -} |
54 | | -impl<V: Value> Persister<V> for NoopPersister { |
55 | | - type Token = NoopToken<V>; |
56 | | - type Error = std::convert::Infallible; |
57 | | - |
58 | | - fn save(&mut self, value: V) -> Result<Self::Token, Self::Error> { Ok(NoopToken(value)) } |
59 | | - |
60 | | - fn load(&self, token: Self::Token) -> Result<V, Self::Error> { Ok(token.0) } |
61 | | -} |
62 | | - |
63 | 1 | /// Handles cases where the transition either succeeds with a final result that ends the session, or hits a static condition and stays in the same state. |
64 | 2 | /// State transition may also be a fatal error or transient error. |
65 | 3 | pub struct MaybeSuccessTransitionWithNoResults<Event, SuccessValue, CurrentState, Err>( |
|
0 commit comments