fix(offline): let the cache drop what was deleted elsewhere

The trip sync and every repo list only ever upserted, so a place a
collaborator deleted while this device was offline came back on the
next offline read, and a trip the user had been removed from stayed on
the device. A sync and a full list now replace the trip's rows, keeping
only the ones created offline that have not synced yet, and a cached
trip the server no longer lists is cleared.
This commit is contained in:
Maurice
2026-10-07 16:32:02 +02:00
parent f092e7a95f
commit 38656eeffd
11 changed files with 100 additions and 33 deletions
+28 -1
View File
@@ -345,9 +345,36 @@ export async function upsertAccommodations(items: Accommodation[]): Promise<void
await offlineDb.accommodations.bulkPut(items);
}
type TripScopedTable = 'days' | 'places' | 'packingItems' | 'todoItems' | 'budgetItems' | 'reservations' | 'tripFiles' | 'accommodations';
/**
* Make one trip's rows in `table` match the server's list: put every row it
* sent and drop the ones it no longer has, so a place a collaborator deleted
* while this device was offline does not come back on the next offline read.
* Rows with a negative (temporary) id were created offline and have not
* synced yet; they stay.
*/
export async function replaceTripRows<T extends { id: number }>(table: TripScopedTable, tripId: number, rows: T[]): Promise<void> {
const target = offlineDb[table] as unknown as Table<T, number>;
const keep = new Set(rows.map(r => r.id));
await offlineDb.transaction('rw', target, async () => {
await target
.where('trip_id')
.equals(tripId)
.filter(row => row.id > 0 && !keep.has(row.id))
.delete();
await target.bulkPut(rows);
});
}
export async function upsertTripMembers(tripId: number, members: TripMember[]): Promise<void> {
const rows: CachedTripMember[] = members.map(m => ({ ...m, tripId }));
await offlineDb.tripMembers.bulkPut(rows);
const keep = new Set(rows.map(r => r.id));
await offlineDb.transaction('rw', offlineDb.tripMembers, async () => {
// A member who left the trip leaves the cached list too.
await offlineDb.tripMembers.where('tripId').equals(tripId).filter(m => !keep.has(m.id)).delete();
await offlineDb.tripMembers.bulkPut(rows);
});
}
export async function upsertTags(tags: Tag[]): Promise<void> {