Skip to content

Conversation

@mfts
Copy link
Owner

@mfts mfts commented Sep 25, 2025

Duplicate a link's permission group and its access controls when duplicating the link to ensure independent permission management.

Previously, duplicating a link that had an associated permissionGroupId would only copy the ID, causing both the original and the new link to share the same permission group. This PR ensures that a new, independent permission group with identical access controls is created for the duplicated link, preventing unintended permission changes across links.


Slack Thread

Open in Cursor Open in Web

Summary by CodeRabbit

  • New Features

    • Duplicating a link now also copies its permission settings, including the associated permission group and all access controls.
    • The duplicated link retains existing tags and includes a reference to the copied permission group in the response.
    • Webhooks continue to trigger as before for duplicated links.
  • Bug Fixes

    • Ensures consistent authorization checks during link duplication, aligning access with the authenticated user.

@cursor
Copy link

cursor bot commented Sep 25, 2025

Cursor Agent can help with this pull request. Just @cursor in comments and I'll start working on changes in this branch.
Learn more about Cursor Agents

@vercel
Copy link

vercel bot commented Sep 25, 2025

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Preview Comments Updated (UTC)
papermark Ready Ready Preview Comment Sep 25, 2025 0:06am

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Sep 25, 2025

Walkthrough

Updates the link-duplication API to derive userId from NextAuth session, authorize via user-team membership, and, when present, duplicate a link’s permissionGroup and its accessControls within the same flow. The new link references the newly created permissionGroupId and preserves prior tag duplication, webhook trigger, and response structure.

Changes

Cohort / File(s) Summary
Link duplication API
pages/api/links/[id]/duplicate.ts
- Import authOptions from NextAuth API; remove local import
- Use session-derived userId for authorization via userTeam check
- Expand link query to include permissionGroup and accessControls
- If permissionGroup exists, duplicate it and clone its accessControls; capture new permissionGroupId
- Create duplicated link with new permissionGroupId and re-create tags
- Preserve webhook trigger and response payload including permissionGroupId

Sequence Diagram(s)

sequenceDiagram
  autonumber
  participant C as Client
  participant API as /api/links/[id]/duplicate
  participant Auth as NextAuth (getServerSession)
  participant DB as Database

  C->>API: POST duplicate(id)
  API->>Auth: getServerSession()
  Auth-->>API: session(userId) or null
  alt No session
    API-->>C: 401 Unauthorized
  else Session
    API->>DB: Fetch link by id incl. permissionGroup{ accessControls }, tags
    DB-->>API: link { teamId, permissionGroup? }
    API->>DB: Verify userTeam with userId + teamId
    DB-->>API: allowed? (bool)
    alt Not allowed
      API-->>C: 403 Forbidden
    else Allowed
      opt permissionGroup exists
        API->>DB: Create new permissionGroup (name, description, dataroomId, teamId)
        DB-->>API: newPermissionGroupId
        API->>DB: Clone accessControls to newPermissionGroupId
      end
      API->>DB: Create duplicated link (incl. newPermissionGroupId)
      API->>DB: Recreate tags for new link
      API-->>C: 200 { newLink with permissionGroupId }
      note over API: Webhook trigger preserved
    end
  end
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Pre-merge checks and finishing touches

❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (2 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title Check ✅ Passed The title clearly conveys the primary change of the PR, which is to duplicate the permission group when links are duplicated, using precise wording that allows teammates to understand the core update at a glance.
✨ Finishing touches
  • 📝 Generate Docstrings
🧪 Generate unit tests
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch cursor/duplicate-permission-group-for-duplicated-links-6c54

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@mfts mfts marked this pull request as ready for review September 25, 2025 12:02
Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (2)
pages/api/links/[id]/duplicate.ts (2)

149-158: Fix webhook teamId source to avoid mismatched events

Use the created link’s teamId rather than the request body to prevent misattributed webhooks.

       waitUntil(
         sendLinkCreatedWebhook({
-          teamId,
+          teamId: newLink.teamId,
           data: {
             link_id: newLink.id,
             document_id: newLink.documentId,
             dataroom_id: newLink.dataroomId,
           },
         }),
       );

47-49: Use findFirst when filtering by both id and teamId
findUnique accepts only a defined unique or composite-unique field—your Link model only defines id as @id, not a composite of (id, teamId). Replace with:

- const link = await prisma.link.findUnique({
-   where: { id, teamId },
+ const link = await prisma.link.findFirst({
+   where: { id, teamId },
    include: {
🧹 Nitpick comments (3)
pages/api/links/[id]/duplicate.ts (3)

71-71: Avoid spreading entire Link into create payload

Spreading ...rest risks copying fields that shouldn’t be cloned (e.g., archived flags, counters, ownership). Prefer an explicit data shape or a Prisma select to retrieve only fields you intend to copy.


43-45: Use 403 for authorized session without required team access

Optional: return 403 Forbidden when the session exists but the user lacks team access; reserve 401 for unauthenticated requests.


23-23: Align method documentation/comments with implementation

Comment says PUT; route accepts POST. Update comments and Allow header documentation for clarity.

-    // PUT /api/links/:id/duplicate
+    // POST /api/links/:id/duplicate
@@
-  // We only allow PUT requests
+  // We only allow POST requests

Also applies to: 166-168

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 286ff88 and 55bd557.

📒 Files selected for processing (1)
  • pages/api/links/[id]/duplicate.ts (4 hunks)
🧰 Additional context used
🧬 Code graph analysis (1)
pages/api/links/[id]/duplicate.ts (1)
lib/types.ts (1)
  • CustomUser (17-17)
🔇 Additional comments (2)
pages/api/links/[id]/duplicate.ts (2)

92-104: Confirm parity of access control fields

Ensure all relevant access control fields are cloned (timestamps/createdBy may rely on defaults; but policy/constraints like expiresAt, domain/email rules, etc., if present, should be included).


31-31: Confirm session user type has id

Ensure session.user conforms to CustomUser and includes id in this API context to avoid runtime undefined.

@mfts mfts merged commit 3dd80e4 into main Sep 25, 2025
9 checks passed
@github-actions github-actions bot locked and limited conversation to collaborators Sep 25, 2025
@mfts mfts deleted the cursor/duplicate-permission-group-for-duplicated-links-6c54 branch November 19, 2025 11:46
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants