1pub struct Cell<T, Seq> {
2 sequence: Seq,
3 value: T,
4}
5
6impl<T, SequenceFactory: crate::SequenceFactory> Cell<T, crate::Sequence<SequenceFactory>> {
7 pub fn new(ctx: &mut crate::Context<SequenceFactory>, value: T) -> Self {
8 Cell {
9 sequence: ctx.next_sequence(),
10 value,
11 }
12 }
13
14 pub fn set(&mut self, ctx: &mut crate::Context<SequenceFactory>, value: T) {
15 *self.borrow_mut(ctx) = value;
16 }
17
18 pub fn last_modified(&self) -> &crate::Sequence<SequenceFactory> {
19 &self.sequence
20 }
21
22 pub fn borrow_mut(&mut self, ctx: &mut crate::Context<SequenceFactory>) -> &mut T {
34 self.sequence = ctx.next_sequence();
35 &mut self.value
36 }
37
38 pub fn into(self) -> T {
39 self.value
40 }
41}
42
43#[derive(Clone,Debug)]
44pub struct CellDiff<T, Seq>(Option<Update<T, Seq>>);
45
46#[derive(Clone,Debug)]
47struct Update<T, Seq> {
48 new: Cell<T, Seq>,
49 old: T,
50}
51
52impl<
53 T: Clone,
54 SequenceFactory: crate::SequenceFactory,
55> crate::Mergable
56for Cell<T, crate::Sequence<SequenceFactory>> {
57 type Diff = CellDiff<T, crate::Sequence<SequenceFactory>>;
58 type Seq = crate::Sequence<SequenceFactory>;
59
60 fn merge(&mut self, other: Self) {
61 if other.sequence > self.sequence {
62 *self = other
63 }
64
65 }
67
68 fn diff(&self, other: &Self) -> Self::Diff {
69 CellDiff(if self.sequence > other.sequence {
70 Some(Update{
71 new: self.clone(),
72 old: other.value.clone(),
73 })
74 } else {
75 None
76 })
77 }
78
79 fn apply(&mut self, diff: Self::Diff) -> Result<(), crate::ApplyError> {
80 if let Some(diff) = diff.0 {
81 self.merge(diff.new);
82 }
83
84 Ok(())
85 }
86
87 fn clean(&mut self, _cutoff: &Self::Seq) {
88 }
93}
94
95
96impl<T, SequenceFactory: crate::SequenceFactory> crate::Diff
97for CellDiff<T, crate::Sequence<SequenceFactory>> {
98 fn is_empty(&self) -> bool {
99 self.0.is_none()
100 }
101
102 fn revert(mut self) -> Result<Self, crate::RevertError> {
103 if let Some(ref mut diff) = self.0 {
104 diff.new.sequence = diff.new.sequence.undo()?;
105 std::mem::swap(&mut diff.new.value, &mut diff.old);
106 }
107 Ok(self)
108 }
109}
110
111impl<T: Clone, SF: Clone> Clone for Cell<T, SF> {
112 fn clone(&self) -> Self {
113 Cell {
114 sequence: self.sequence.clone(),
115 value: self.value.clone(),
116 }
117 }
118}
119
120impl<T, SF> std::ops::Deref for Cell<T, SF> {
121 type Target = T;
122
123 fn deref(&self) -> &T {
124 &self.value
125 }
126}
127
128impl<T: PartialEq, Seq> PartialEq for Cell<T, Seq> {
129 fn eq(&self, other: &Self) -> bool {
130 self.value == other.value
131 }
132}
133
134impl<T: std::fmt::Debug, Seq> std::fmt::Debug for Cell<T, Seq> {
135 fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
136 self.value.fmt(f)
137 }
138}
139
140#[test]
141fn test_merge() {
142 let mut ctx = crate::Context::default();
143
144 let result = crate::test::test_merge(&mut [
145 &Cell::new(&mut ctx, "one"),
146 &Cell::new(&mut ctx, "two"),
147 &Cell::new(&mut ctx, "six"),
148 ]);
149 assert_eq!(result.value, "six");
150}
151
152#[test]
153fn test_update() {
154 let mut ctx = crate::Context::default();
155
156 let initial = Cell::new(&mut ctx, "old");
157 let mut update = initial.clone();
158 update.set(&mut ctx, "new");
159
160 let result = crate::test::test_merge(&mut [&initial, &update]);
161 assert_eq!(result.value, "new");
162}
163
164#[test]
165fn test_revert() {
166 let mut ctx = crate::Context::default();
167
168 let initial = Cell::new(&mut ctx, "old");
169 let mut update = initial.clone();
170 update.set(&mut ctx, "new");
171
172 let diff = crate::Mergable::diff(&update, &initial);
173 let revert = crate::Diff::revert(diff).unwrap();
174 crate::Mergable::apply(&mut update, revert).unwrap();
175
176 assert_eq!(update.value, "old");
177}
178
179#[test]
180fn test_revert_stale() {
181 let mut ctx = crate::Context::default();
182
183 let orig = Cell::new(&mut ctx, "old");
184
185 let mut base = orig.clone();
186
187 let mut updated = base.clone();
188 updated.set(&mut ctx, "new");
189
190 let diff_new = crate::Mergable::diff(&updated, &base);
191 crate::Mergable::apply(&mut base, diff_new.clone()).unwrap();
192
193 updated.set(&mut ctx, "newer");
194
195 let diff_newer = crate::Mergable::diff(&updated, &base);
196 crate::Mergable::apply(&mut base, diff_newer.clone()).unwrap();
197
198 let revert = crate::Diff::revert(diff_new.clone()).unwrap();
199
200 let result = crate::test::test_apply(orig, &mut [
201 diff_new,
202 diff_newer,
203 revert,
204 ]);
205
206 assert_eq!(result.value, "newer");
207}