Skip to content

Commit e45af23

Browse files
committed
fix: notify subscriptions for optimistic ids when the equivalent realistic id is updated
1 parent 7bfde98 commit e45af23

File tree

3 files changed

+57
-11
lines changed

3 files changed

+57
-11
lines changed

shared/src/sync_engine/optimistic/db/object_store.rs

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -180,8 +180,22 @@ where
180180
.remove_successful_for_id::<S>(item.id());
181181

182182
if let Some(commit_listener) = self.commit_listener.as_ref() {
183+
let optimistic_id = self
184+
.optimistic_changes
185+
.get_realistic_to_optimistic_for_creations()
186+
.get(&SerializedId::new_from_id::<S>(item.id()))
187+
.map(|i| i.clone());
188+
183189
let reactivity_trackers = ReactivityTrackers {
184-
stores_modified: hashmap![S::NAME => hashset![SerializedId::new_from_row(item)]],
190+
stores_modified: hashmap![
191+
S::NAME => [
192+
Some(SerializedId::new_from_row(item)),
193+
optimistic_id,
194+
]
195+
.into_iter()
196+
.filter_map(|i| i)
197+
.collect(),
198+
],
185199
..Default::default()
186200
};
187201
tracing::trace!(
@@ -214,6 +228,7 @@ where
214228
stores_modified: hashmap![S::NAME => hashset![SerializedId::new_from_row(&row)]],
215229
..Default::default()
216230
};
231+
217232
self.optimistic_changes.create(row, create_fut);
218233

219234
if let Some(commit_listener) = self.commit_listener.as_ref() {

shared/src/sync_engine/optimistic/optimistic_change_map.rs

Lines changed: 36 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -65,8 +65,20 @@ mod status {
6565
}
6666
}
6767

68-
type OptimisticChangeMapInner<T, RealisticId> =
69-
HashMap<StoreName, HashMap<SerializedId, BTreeMap<MonotonicTime, Status<T, RealisticId>>>>;
68+
struct OptimisticChangeMapInner<T, RealisticId> {
69+
changes:
70+
HashMap<StoreName, HashMap<SerializedId, BTreeMap<MonotonicTime, Status<T, RealisticId>>>>,
71+
realistic_to_optimistic: HashMap<RealisticId, SerializedId>,
72+
}
73+
74+
impl<T, RealisticId> Default for OptimisticChangeMapInner<T, RealisticId> {
75+
fn default() -> Self {
76+
Self {
77+
changes: Default::default(),
78+
realistic_to_optimistic: Default::default(),
79+
}
80+
}
81+
}
7082

7183
pub struct OptimisticChangeMap<T, RealisticId = ()> {
7284
inner: Arc<RwLock<OptimisticChangeMapInner<T, RealisticId>>>,
@@ -94,6 +106,7 @@ impl<T, RealisticId: Eq + std::fmt::Debug> OptimisticChangeMap<T, RealisticId> {
94106
let time = MonotonicTime::new();
95107
self.inner
96108
.write()
109+
.changes
97110
.entry(S::NAME)
98111
.or_default()
99112
.entry(optimistic_id)
@@ -107,7 +120,7 @@ impl<T, RealisticId: Eq + std::fmt::Debug> OptimisticChangeMap<T, RealisticId> {
107120
let optimistic_id = SerializedId::new_from_id::<S>(optimistic_id);
108121
let mut by_id_len = None;
109122
let mut inner = self.inner.write();
110-
if let Some(by_id) = inner.get_mut(&S::NAME) {
123+
if let Some(by_id) = inner.changes.get_mut(&S::NAME) {
111124
let mut by_time_len = None;
112125
if let Some(by_time) = by_id.get_mut(&optimistic_id) {
113126
match by_time.entry(*time) {
@@ -128,7 +141,7 @@ impl<T, RealisticId: Eq + std::fmt::Debug> OptimisticChangeMap<T, RealisticId> {
128141
by_id_len = Some(by_id.len());
129142
}
130143
if by_id_len == Some(0) {
131-
inner.remove(&S::NAME);
144+
inner.changes.remove(&S::NAME);
132145
}
133146
}
134147

@@ -140,7 +153,7 @@ impl<T, RealisticId: Eq + std::fmt::Debug> OptimisticChangeMap<T, RealisticId> {
140153
let optimistic_id = SerializedId::new_from_id::<S>(optimistic_id);
141154
let mut by_id_len = None;
142155
let mut inner = self.inner.write();
143-
if let Some(by_id) = inner.get_mut(&S::NAME) {
156+
if let Some(by_id) = inner.changes.get_mut(&S::NAME) {
144157
let mut by_time_len = None;
145158
if let Some(by_time) = by_id.get_mut(&optimistic_id) {
146159
let to_remove_keys = by_time
@@ -165,26 +178,37 @@ impl<T, RealisticId: Eq + std::fmt::Debug> OptimisticChangeMap<T, RealisticId> {
165178
by_id_len = Some(by_id.len());
166179
}
167180
if by_id_len == Some(0) {
168-
inner.remove(&S::NAME);
181+
inner.changes.remove(&S::NAME);
169182
}
170183
}
184+
}
171185

186+
impl<T, RealisticId: Clone + Eq + std::hash::Hash> OptimisticChangeMap<T, RealisticId> {
172187
pub fn mark_realistic<S: Store>(
173188
&self,
174189
optimistic_id: &S::Id,
175190
time: &MonotonicTime,
176191
realistic_id: RealisticId,
177192
) {
178193
let optimistic_id = SerializedId::new_from_id::<S>(optimistic_id);
179-
self.inner
180-
.write()
194+
let mut inner = self.inner.write();
195+
inner
196+
.changes
181197
.get_mut(&S::NAME)
182198
.unwrap()
183199
.get_mut(&optimistic_id)
184200
.expect("id to mark realistic not found")
185201
.get_mut(time)
186202
.expect("could not find the monotonic time to mark realistic")
187-
.mark_realistic(realistic_id);
203+
.mark_realistic(realistic_id.clone());
204+
205+
inner
206+
.realistic_to_optimistic
207+
.insert(realistic_id, optimistic_id);
208+
}
209+
210+
pub fn get_realistic_to_optimistic(&self) -> HashMap<RealisticId, SerializedId> {
211+
self.inner.read().realistic_to_optimistic.clone()
188212
}
189213
}
190214

@@ -194,6 +218,7 @@ impl<T: Clone, RealisticId: Clone> OptimisticChangeMap<T, RealisticId> {
194218
Some(
195219
self.inner
196220
.read()
221+
.changes
197222
.get(&S::NAME)?
198223
.get(&optimistic_id)?
199224
.last_key_value()?
@@ -209,6 +234,7 @@ impl<RealisticId> OptimisticChangeMap<Rc<dyn Any>, RealisticId> {
209234
Some(
210235
self.inner
211236
.read()
237+
.changes
212238
.get(&S::NAME)?
213239
.get(&optimistic_id)?
214240
.last_key_value()?
@@ -223,6 +249,7 @@ impl<RealisticId> OptimisticChangeMap<Rc<dyn Any>, RealisticId> {
223249
pub fn all_the_latest_downcasted<S: Store + 'static>(&self) -> Vec<S> {
224250
self.inner
225251
.read()
252+
.changes
226253
.get(&S::NAME)
227254
.map(|s| s.values())
228255
.into_iter()

shared/src/sync_engine/optimistic/optimistic_changes.rs

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
#![allow(dead_code)]
22
#![allow(clippy::type_complexity)]
33

4-
use std::{any::Any, future::Future, rc::Rc};
4+
use std::{any::Any, collections::HashMap, future::Future, rc::Rc};
55

66
use any_spawner::Executor;
77
use typesafe_idb::Store;
@@ -94,4 +94,8 @@ impl OptimisticChanges {
9494
self.creations
9595
.remove_all_realistic::<S>(id, &SerializedId::new_from_id::<S>(id));
9696
}
97+
98+
pub fn get_realistic_to_optimistic_for_creations(&self) -> HashMap<SerializedId, SerializedId> {
99+
self.creations.get_realistic_to_optimistic()
100+
}
97101
}

0 commit comments

Comments
 (0)