fix: prevent cascade rollback from restoring deleted session descendants (#1555)
The OpenCode server cascade-deletes all child sessions when a parent is removed. The client was sending individual DELETE requests for each descendant, which returned 404 after the parent's cascade removed them. The 404 triggered rollback in deleteSessionAction, restoring already- deleted sessions back into the global store. Changes: - executeDeleteSession: only send the root session delete; the server cascade handles descendants. - deleteSession / deleteSessionInDirectory: treat 404 in catch as success, acting as a safety net for remaining paths (e.g. sidebar bulk action bar when parent and child are both selected).
This commit is contained in:
@@ -214,16 +214,18 @@ export const useSessionActions = (args: Args) => {
|
|||||||
|
|
||||||
const ids = [session.id, ...descendantIds];
|
const ids = [session.id, ...descendantIds];
|
||||||
if (shouldHardDelete) {
|
if (shouldHardDelete) {
|
||||||
const { deletedIds, failedIds } = await args.deleteSessions(ids);
|
// The server cascade-deletes all descendant sessions when the parent
|
||||||
if (deletedIds.length > 0) {
|
// is removed. Only send the root session delete request; sending
|
||||||
toast.success(deletedIds.length === 1
|
// individual requests for each descendant would hit 404 (already
|
||||||
? t('sessions.sidebar.bulkActions.deletedSingle', { count: deletedIds.length })
|
// deleted by cascade) and trigger rollback that restores them.
|
||||||
: t('sessions.sidebar.bulkActions.deletedPlural', { count: deletedIds.length }));
|
const success = await args.deleteSession(session.id);
|
||||||
}
|
if (success) {
|
||||||
if (failedIds.length > 0) {
|
const totalDeleted = descendantIds.length + 1;
|
||||||
toast.error(failedIds.length === 1
|
toast.success(totalDeleted === 1
|
||||||
? t('sessions.sidebar.bulkActions.failedDeleteSingle', { count: failedIds.length })
|
? t('sessions.sidebar.bulkActions.deletedSingle', { count: totalDeleted })
|
||||||
: t('sessions.sidebar.bulkActions.failedDeletePlural', { count: failedIds.length }));
|
: t('sessions.sidebar.bulkActions.deletedPlural', { count: totalDeleted }));
|
||||||
|
} else {
|
||||||
|
toast.error(t('sessions.sidebar.session.delete.error'));
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -483,6 +483,12 @@ export async function deleteSession(sessionId: string, _options?: Record<string,
|
|||||||
return true
|
return true
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error("[session-actions] deleteSession failed", error)
|
console.error("[session-actions] deleteSession failed", error)
|
||||||
|
// The server cascade-deletes child sessions when the parent is removed.
|
||||||
|
// Subsequent delete attempts for those children return 404; treat as
|
||||||
|
// success since the session was already deleted by the cascade.
|
||||||
|
if ((error as { status?: number })?.status === 404) {
|
||||||
|
return true
|
||||||
|
}
|
||||||
restoreSessionListSnapshots(snapshots)
|
restoreSessionListSnapshots(snapshots)
|
||||||
restoreGlobalSessionSnapshot(globalSnapshot)
|
restoreGlobalSessionSnapshot(globalSnapshot)
|
||||||
return false
|
return false
|
||||||
@@ -507,6 +513,9 @@ export async function deleteSessionInDirectory(sessionId: string, directory: str
|
|||||||
return true
|
return true
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error("[session-actions] deleteSessionInDirectory failed", error)
|
console.error("[session-actions] deleteSessionInDirectory failed", error)
|
||||||
|
if ((error as { status?: number })?.status === 404) {
|
||||||
|
return true
|
||||||
|
}
|
||||||
restoreSessionListSnapshots(snapshots)
|
restoreSessionListSnapshots(snapshots)
|
||||||
restoreGlobalSessionSnapshot(globalSnapshot)
|
restoreGlobalSessionSnapshot(globalSnapshot)
|
||||||
return false
|
return false
|
||||||
|
|||||||
Reference in New Issue
Block a user