Skip to content

Commit 592cf47

Browse files
committed
(chore): Improve the following state by immediatly updating the state before any committing
1 parent 3d953e0 commit 592cf47

1 file changed

Lines changed: 41 additions & 22 deletions

File tree

apps/polycentric/src/features/follow/hooks/useFollows.ts

Lines changed: 41 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,8 @@ const useFollows = create<FollowsState>((set, get) => ({
4343
* Creates the Follow event and syncs
4444
*/
4545
async addFollow(client, identity) {
46+
const follows = get().follows;
47+
4648
const content = v2.Content.create({
4749
contentBody: {
4850
oneofKind: 'follow',
@@ -53,10 +55,18 @@ const useFollows = create<FollowsState>((set, get) => ({
5355
await client.contentManager.save(content);
5456
const event = await client.buildEvent(content, COLLECTION.GRAPH);
5557
const signedEvent = await client.signEvent(event);
56-
await client.commitEvent(signedEvent, content);
57-
await client.sync();
5858

59-
set({ follows: new Map(get().follows).set(identity, true) });
59+
// Optimistically upate the state
60+
set({ follows: new Map(follows).set(identity, true) });
61+
62+
try {
63+
await client.commitEvent(signedEvent, content);
64+
await client.sync();
65+
} catch (err) {
66+
console.error(err);
67+
// revert the change
68+
set({ follows });
69+
}
6070
},
6171
/**
6272
* Creates a Delete event for the last know Follow event and sync
@@ -65,6 +75,8 @@ const useFollows = create<FollowsState>((set, get) => ({
6575
const self = client.activeIdentityKey;
6676
if (!self) return;
6777

78+
const follows = get().follows;
79+
6880
const bundles = client.listValidEvents(self, COLLECTION.GRAPH);
6981

7082
// Tombstone every active Follow event this identity wrote that targets
@@ -77,30 +89,37 @@ const useFollows = create<FollowsState>((set, get) => ({
7789
entry !== null && entry.identity === identity,
7890
);
7991

80-
for (const { event } of targets) {
81-
if (!event.key) continue;
82-
const deleteContent = v2.Content.create({
83-
contentBody: {
84-
oneofKind: 'delete',
85-
delete: { eventKey: event.key },
86-
},
87-
});
88-
await client.contentManager.save(deleteContent);
89-
const deleteEvent = await client.buildEvent(
90-
deleteContent,
91-
COLLECTION.GRAPH,
92-
);
93-
const signedDelete = await client.signEvent(deleteEvent);
94-
await client.commitEvent(signedDelete, deleteContent);
92+
// Optimistically upate the state
93+
const next = new Map(follows);
94+
next.delete(identity);
95+
set({ follows: next });
96+
97+
try {
98+
for (const { event } of targets) {
99+
if (!event.key) continue;
100+
const deleteContent = v2.Content.create({
101+
contentBody: {
102+
oneofKind: 'delete',
103+
delete: { eventKey: event.key },
104+
},
105+
});
106+
await client.contentManager.save(deleteContent);
107+
const deleteEvent = await client.buildEvent(
108+
deleteContent,
109+
COLLECTION.GRAPH,
110+
);
111+
const signedDelete = await client.signEvent(deleteEvent);
112+
await client.commitEvent(signedDelete, deleteContent);
113+
}
114+
} catch (err) {
115+
console.error(err);
116+
// Revert the state change
117+
set({ follows });
95118
}
96119

97120
if (targets.length > 0) {
98121
await client.sync();
99122
}
100-
101-
const next = new Map(get().follows);
102-
next.delete(identity);
103-
set({ follows: next });
104123
},
105124
/**
106125
* Returns the synced and valid (post tombstoned) Follow events

0 commit comments

Comments
 (0)