[PR #5647] [MERGED] fix(backend): prevent cross-user orderIndex corruption and collection deadlocks #5297

Closed
opened 2026-03-17 02:45:33 +03:00 by kerem · 0 comments
Owner

📋 Pull Request Information

Original PR: https://github.com/hoppscotch/hoppscotch/pull/5647
Author: @shaezard
Created: 12/2/2025
Status: Merged
Merged: 1/22/2026
Merged by: @mirarifhasan

Base: nextHead: order_index_bug_fix


📝 Commits (5)

  • d8823a6 fix: add teamID/userUid filter to updateMany queries
  • dce98e5 fix: fix orderIndex of existing collections
  • ee9c626 feat(backend): add cascade delete for collections
  • 880cfb8 refactor(team-collection): remove manual deleteCollectionData method
  • d45ec2c fix(backend): fixed locking mechanisms for collections and requests

📊 Changes

11 files changed (+1822 additions, -719 deletions)

View changed files

packages/hoppscotch-backend/prisma/migrations/20251202154928_fix_order_index/migration.sql (+30 -0)
packages/hoppscotch-backend/prisma/migrations/20251203202452_cascade_delete/migration.sql (+11 -0)
📝 packages/hoppscotch-backend/prisma/schema.prisma (+2 -2)
📝 packages/hoppscotch-backend/src/prisma/prisma.service.ts (+37 -44)
📝 packages/hoppscotch-backend/src/team-collection/team-collection.service.spec.ts (+520 -28)
📝 packages/hoppscotch-backend/src/team-collection/team-collection.service.ts (+216 -229)
📝 packages/hoppscotch-backend/src/team-request/team-request.service.spec.ts (+2 -2)
📝 packages/hoppscotch-backend/src/team-request/team-request.service.ts (+75 -72)
📝 packages/hoppscotch-backend/src/user-collection/user-collection.service.spec.ts (+616 -16)
📝 packages/hoppscotch-backend/src/user-collection/user-collection.service.ts (+240 -255)
📝 packages/hoppscotch-backend/src/user-request/user-request.service.ts (+73 -71)

📄 Description

Closes #5646

This PR fixes a critical bug where updateMany queries for root collections
(where parentID: null) were missing the userUid/teamID filter, potentially
causing cross-user/cross-team data corruption.

What's changed

  • Added userUid filter to user-collection.service.ts:

    • changeParentAndUpdateOrderIndex
    • removeCollectionAndUpdateSiblingsOrderIndex
    • updateUserCollectionOrder (both cases)
    • getCollectionCount (now accepts userUid parameter)
  • Added teamID filter to team-collection.service.ts:

    • deleteCollectionAndUpdateSiblingsOrderIndex
    • updateCollectionOrder (both cases)
    • getCollectionCount (now accepts teamID parameter)
  • Added unit tests to verify the fix works correctly

  • Added scenario tests to verify multi-user/multi-team isolation

Notes to reviewers

  • All existing tests pass
  • The fix ensures operations on root collections are properly scoped to the
    specific user/team
  • The getCollectionCount method signature was changed to require
    userUid/teamID parameter - all callers have been updated accordingly

Summary by cubic

Fixes missing user/team scoping in updateMany on root collections to prevent cross-user/team orderIndex corruption. Adds orderIndex normalization, cascade deletes, and scoped row locks to avoid deadlocks.

  • Bug Fixes

    • Added userUid/teamID filters to all updateMany queries for root-level collections in user/team services.
    • Replaced table-wide locks with scoped row-level locks for collections and requests to reduce contention and prevent deadlocks.
    • Added unit and scenario tests to ensure multi-user/team isolation and safe concurrency.
  • Migration

    • Recalculated orderIndex partitioned by userUid/teamID and parentID for UserCollection and TeamCollection.
    • Added ON DELETE CASCADE for TeamCollection parent and UserRequest→UserCollection; removed manual recursive delete logic.

Written for commit d45ec2cf1c. Summary will update on new commits.


🔄 This issue represents a GitHub Pull Request. It cannot be merged through Gitea due to API limitations.

## 📋 Pull Request Information **Original PR:** https://github.com/hoppscotch/hoppscotch/pull/5647 **Author:** [@shaezard](https://github.com/shaezard) **Created:** 12/2/2025 **Status:** ✅ Merged **Merged:** 1/22/2026 **Merged by:** [@mirarifhasan](https://github.com/mirarifhasan) **Base:** `next` ← **Head:** `order_index_bug_fix` --- ### 📝 Commits (5) - [`d8823a6`](https://github.com/hoppscotch/hoppscotch/commit/d8823a69f285385b76490a34a1f9c7aea1f08b32) fix: add teamID/userUid filter to updateMany queries - [`dce98e5`](https://github.com/hoppscotch/hoppscotch/commit/dce98e59b1b39bc006a83ea1028f321ff031e119) fix: fix orderIndex of existing collections - [`ee9c626`](https://github.com/hoppscotch/hoppscotch/commit/ee9c626a718883f5e103a6c5a631611738c7216c) feat(backend): add cascade delete for collections - [`880cfb8`](https://github.com/hoppscotch/hoppscotch/commit/880cfb80681fa35374bcd7b8be06e0e66bd4b308) refactor(team-collection): remove manual deleteCollectionData method - [`d45ec2c`](https://github.com/hoppscotch/hoppscotch/commit/d45ec2cf1cedd9d15abf0605ca10b5cfeabec6f1) fix(backend): fixed locking mechanisms for collections and requests ### 📊 Changes **11 files changed** (+1822 additions, -719 deletions) <details> <summary>View changed files</summary> ➕ `packages/hoppscotch-backend/prisma/migrations/20251202154928_fix_order_index/migration.sql` (+30 -0) ➕ `packages/hoppscotch-backend/prisma/migrations/20251203202452_cascade_delete/migration.sql` (+11 -0) 📝 `packages/hoppscotch-backend/prisma/schema.prisma` (+2 -2) 📝 `packages/hoppscotch-backend/src/prisma/prisma.service.ts` (+37 -44) 📝 `packages/hoppscotch-backend/src/team-collection/team-collection.service.spec.ts` (+520 -28) 📝 `packages/hoppscotch-backend/src/team-collection/team-collection.service.ts` (+216 -229) 📝 `packages/hoppscotch-backend/src/team-request/team-request.service.spec.ts` (+2 -2) 📝 `packages/hoppscotch-backend/src/team-request/team-request.service.ts` (+75 -72) 📝 `packages/hoppscotch-backend/src/user-collection/user-collection.service.spec.ts` (+616 -16) 📝 `packages/hoppscotch-backend/src/user-collection/user-collection.service.ts` (+240 -255) 📝 `packages/hoppscotch-backend/src/user-request/user-request.service.ts` (+73 -71) </details> ### 📄 Description Closes #5646 This PR fixes a critical bug where `updateMany` queries for root collections (where `parentID: null`) were missing the `userUid`/`teamID` filter, potentially causing cross-user/cross-team data corruption. ### What's changed - [x] Added `userUid` filter to `user-collection.service.ts`: - `changeParentAndUpdateOrderIndex` - `removeCollectionAndUpdateSiblingsOrderIndex` - `updateUserCollectionOrder` (both cases) - `getCollectionCount` (now accepts `userUid` parameter) - [x] Added `teamID` filter to `team-collection.service.ts`: - `deleteCollectionAndUpdateSiblingsOrderIndex` - `updateCollectionOrder` (both cases) - `getCollectionCount` (now accepts `teamID` parameter) - [x] Added unit tests to verify the fix works correctly - [x] Added scenario tests to verify multi-user/multi-team isolation ### Notes to reviewers - All existing tests pass - The fix ensures operations on root collections are properly scoped to the specific user/team - The `getCollectionCount` method signature was changed to require `userUid`/`teamID` parameter - all callers have been updated accordingly <!-- This is an auto-generated description by cubic. --> --- ## Summary by cubic Fixes missing user/team scoping in updateMany on root collections to prevent cross-user/team orderIndex corruption. Adds orderIndex normalization, cascade deletes, and scoped row locks to avoid deadlocks. - **Bug Fixes** - Added userUid/teamID filters to all updateMany queries for root-level collections in user/team services. - Replaced table-wide locks with scoped row-level locks for collections and requests to reduce contention and prevent deadlocks. - Added unit and scenario tests to ensure multi-user/team isolation and safe concurrency. - **Migration** - Recalculated orderIndex partitioned by userUid/teamID and parentID for UserCollection and TeamCollection. - Added ON DELETE CASCADE for TeamCollection parent and UserRequest→UserCollection; removed manual recursive delete logic. <sup>Written for commit d45ec2cf1cedd9d15abf0605ca10b5cfeabec6f1. Summary will update on new commits.</sup> <!-- End of auto-generated description by cubic. --> --- <sub>🔄 This issue represents a GitHub Pull Request. It cannot be merged through Gitea due to API limitations.</sub>
kerem 2026-03-17 02:45:33 +03:00
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
starred/hoppscotch#5297
No description provided.