Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Conversation

@TWilson023
Copy link
Collaborator

@TWilson023 TWilson023 commented Jun 12, 2025

Screenshot 2025-06-12 at 5 21 01 PM

Summary by CodeRabbit

  • New Features

    • Introduced a floating popup for the Partner Program in the sidebar, providing quick access to partner resources and actions.
    • Added the ability to permanently dismiss the Partner Program popup, with dismissal state remembered per workspace.
  • Improvements

    • Sidebar navigation now supports popups anchored to navigation items, enhancing contextual guidance.
    • Enhanced upgrade call-to-action logic with clearer messaging and links based on user status.
  • Bug Fixes

    • Removed automatic redirect when no default program exists, improving navigation flow.
  • Style

    • Simplified the workspace dropdown placeholder for a cleaner appearance.
  • Removals

    • Removed the Create Program card from the sidebar to streamline the interface.

@vercel
Copy link
Contributor

vercel bot commented Jun 12, 2025

The latest updates on your projects. Learn more about Vercel for Git ↗︎

Name Status Preview Updated (UTC)
dub ✅ Ready (Inspect) Visit Preview Jun 12, 2025 10:59pm

@TWilson023 TWilson023 requested a review from steven-tey June 12, 2025 21:21
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Jun 12, 2025

Walkthrough

A new popup component for the Dub Partners program was introduced and integrated into the sidebar navigation. The workspace schema was updated to track the dismissal state of this popup. The sidebar navigation logic was extended to support rendering popups anchored to navigation items. Minor UI simplifications were made to the workspace dropdown placeholder. Additionally, a previously existing CreateProgramCard component was removed from the sidebar navigation.

Changes

File(s) Change Summary
apps/web/lib/zod/schemas/workspaces.ts Added "dubPartnersPopupDismissed" boolean key to workspaceStoreKeys enum.
apps/web/ui/layout/sidebar/app-sidebar-nav.tsx Imported and linked DubPartnersPopup to the "Partner Program" sidebar navigation group.
apps/web/ui/layout/sidebar/dub-partners-popup.tsx Introduced new DubPartnersPopup React component with conditional rendering and dismissal logic.
apps/web/ui/layout/sidebar/sidebar-nav.tsx Extended nav group type to support optional popup; updated rendering logic to anchor popups; removed CreateProgramCard usage.
apps/web/ui/layout/sidebar/create-program-card.tsx Deleted CreateProgramCard React component file.
apps/web/ui/layout/sidebar/sidebar-nav-old.tsx Removed import and rendering of CreateProgramCard.
apps/web/ui/layout/sidebar/workspace-dropdown.tsx Simplified WorkspaceDropdownPlaceholder UI; removed unused icon import.
apps/web/app/app.dub.co/(dashboard)/[slug]/(ee)/program/auth.tsx Removed redirect logic; integrated default program ID check into existing conditions.
apps/web/app/app.dub.co/(dashboard)/[slug]/(ee)/program/partners-ugrade-cta.tsx Refactored PartnersUpgradeCTA to use memoized object for CTA text and link based on conditions.

Sequence Diagram(s)

sequenceDiagram
    participant User
    participant SidebarNav
    participant DubPartnersPopup
    participant WorkspaceStore

    User->>SidebarNav: Hover/click "Partner Program" nav item
    SidebarNav->>DubPartnersPopup: Render with referenceElement
    DubPartnersPopup->>WorkspaceStore: Check dismissal state & workspace data
    alt Not dismissed and eligible
        DubPartnersPopup-->>User: Show popup anchored to nav item
        User->>DubPartnersPopup: Click dismiss
        DubPartnersPopup->>WorkspaceStore: Set dismissed flag
        DubPartnersPopup-->>User: Hide popup
    else Dismissed or ineligible
        DubPartnersPopup-->>User: No popup rendered
    end
Loading

Suggested reviewers

  • TWilson023

Poem

A popup appears with a cheerful hop,
For partners and programs, it just won't stop!
Anchored and floating, it waves hello,
Until you dismiss it—then off it will go.
With schemas updated and sidebars anew,
The rabbit is proud of this sidebar view!
🐇✨

✨ Finishing Touches
  • 📝 Generate Docstrings

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
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Explain this complex logic.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai explain this code block.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and explain its main purpose.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Support

Need help? Create a ticket on our support page for assistance with any issues or questions.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

CodeRabbit Commands (Invoked using PR comments)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai generate docstrings to generate docstrings for this PR.
  • @coderabbitai generate sequence diagram to generate a sequence diagram of the changes in this PR.
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

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

🧹 Nitpick comments (5)
apps/web/ui/layout/sidebar/app-sidebar-nav.tsx (1)

34-35: Consider lazy-loading the popup component

DubPartnersPopup is only needed when the sidebar is rendered client-side and the relevant nav link is visible. Importing it eagerly makes the whole component (and its dependencies such as @floating-ui) part of the main sidebar bundle.
Wrapping the import in next/dynamic (or React .lazy) can keep the sidebar’s first-load footprint smaller.

-import { DubPartnersPopup } from "./dub-partners-popup";
+const DubPartnersPopup = dynamic(
+  () => import("./dub-partners-popup").then((m) => m.DubPartnersPopup),
+  { ssr: false },
+);
apps/web/ui/layout/sidebar/workspace-dropdown.tsx (1)

113-116: Minor a11y / visual nitpick on the skeleton placeholder

The placeholder div currently has gap-x-1.5 but no child elements, so the gap utility has no effect and slightly bloats the class list.
Also, consider adding role="img" aria-label="loading" (or aria-hidden="true") to keep screen readers silent.

No functional impact, just polish.

apps/web/ui/layout/sidebar/sidebar-nav.tsx (2)

45-48: Prop name collision risk

Exposing the prop as popup is clear, but we now have both NavGroupType.popup and NavGroupItem.Popup within the same file.
Renaming the local destructured variable (popup: Popup) to something like PopupComponent would avoid mis-reads and keep lint rules happy.

-  popup: Popup,
+  popup: PopupComponent,
...
- {Popup && element && <Popup referenceElement={element} />}
+ {PopupComponent && element && (
+   <PopupComponent referenceElement={element} />
+ )}

270-303: Element ref is never cleared on unmount

setElement stores the anchor element but we don’t reset it if the nav group unmounts.
A tiny cleanup prevents leaking stale DOM refs:

-const [element, setElement] = useState<HTMLAnchorElement | null>(null);
+const [element, setElement] = useState<HTMLAnchorElement | null>(null);
+useEffect(() => () => setElement(null), []);
apps/web/ui/layout/sidebar/dub-partners-popup.tsx (1)

74-82: TypeScript whileElementsMounted signature

The inline method form is valid, but the parameter names (referenceEl, floatingEl) shadow nothing and differ from the surrounding context (referenceElement). Rename for clarity to avoid confusion:

-whileElementsMounted(referenceEl, floatingEl, update) {
-  return autoUpdate(referenceEl, floatingEl, update, { animationFrame: true });
+whileElementsMounted(ref, floating, update) {
+  return autoUpdate(ref, floating, update, { animationFrame: true });
}
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between aa43e14 and 0780778.

📒 Files selected for processing (5)
  • apps/web/lib/zod/schemas/workspaces.ts (1 hunks)
  • apps/web/ui/layout/sidebar/app-sidebar-nav.tsx (2 hunks)
  • apps/web/ui/layout/sidebar/dub-partners-popup.tsx (1 hunks)
  • apps/web/ui/layout/sidebar/sidebar-nav.tsx (3 hunks)
  • apps/web/ui/layout/sidebar/workspace-dropdown.tsx (1 hunks)
🧰 Additional context used
🧬 Code Graph Analysis (1)
apps/web/ui/layout/sidebar/app-sidebar-nav.tsx (1)
apps/web/ui/layout/sidebar/dub-partners-popup.tsx (1)
  • DubPartnersPopup (21-63)
⏰ Context from checks skipped due to timeout of 90000ms (1)
  • GitHub Check: build
🔇 Additional comments (3)
apps/web/ui/layout/sidebar/app-sidebar-nav.tsx (1)

85-86: Popup integration looks correct

The new popup prop is wired up properly and matches the extended NavGroupType interface. Nice.

apps/web/lib/zod/schemas/workspaces.ts (1)

169-171: Verify downstream handling of the new store key

Adding "dubPartnersPopupDismissed" to the workspaceStoreKeys enum is fine, but remember to:

  1. Run any required DB/data-migration so that existing records don’t violate enum constraints.
  2. Ensure API layers that validate this enum have been regenerated or recompiled.

Confirming these avoids 422/400 responses in production.

apps/web/ui/layout/sidebar/dub-partners-popup.tsx (1)

148-151: Potential undefined slug in “Create program” link

If slug is unexpectedly undefined, the CTA becomes /undefined/program/new, leading to a 404.
Either guard the render or fallback to window.location.pathname.split("/")[1].

href={slug ? `/${slug}/program/new` : "/program/new"}

Comment on lines +42 to +55
if (
// Loading
loadingWorkspace ||
loadingDismissed ||
// Program/partners status/capabilities
// defaultProgramId ||
!partnersEnabled ||
!canManageProgram ||
// Device
isMobile ||
// Dismissed
dismissed
)
return null;
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue

Popup shows even when a program already exists

The guard for defaultProgramId is commented out.
If a workspace already has a Partner Program, the popup will still appear, which feels spammy.

-    // defaultProgramId ||
+    defaultProgramId ||

Uncommenting (or explicitly checking !defaultProgramId) will suppress the popup for workspaces that have already onboarded.

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
if (
// Loading
loadingWorkspace ||
loadingDismissed ||
// Program/partners status/capabilities
// defaultProgramId ||
!partnersEnabled ||
!canManageProgram ||
// Device
isMobile ||
// Dismissed
dismissed
)
return null;
if (
// Loading
loadingWorkspace ||
loadingDismissed ||
// Program/partners status/capabilities
defaultProgramId ||
!partnersEnabled ||
!canManageProgram ||
// Device
isMobile ||
// Dismissed
dismissed
)
return null;
🤖 Prompt for AI Agents
In apps/web/ui/layout/sidebar/dub-partners-popup.tsx between lines 42 and 55,
the condition checking for defaultProgramId is commented out, causing the popup
to show even when a program already exists. Uncomment the check for
!defaultProgramId in the if statement to prevent the popup from appearing for
workspaces that have already onboarded a Partner Program.

Comment on lines +74 to +97
const { refs, floatingStyles, context } = useFloating({
placement: "right",
strategy: "fixed",
whileElementsMounted(referenceEl, floatingEl, update) {
return autoUpdate(referenceEl, floatingEl, update, {
// Not good for performance but keeps the arrow and floating element in the right spot
animationFrame: true,
});
},
elements: {
reference: referenceElement,
},
middleware: [
offset({
mainAxis: 12,
}),
shift({
padding: 32,
}),
arrow({
element: arrowRef,
}),
],
});
Copy link
Contributor

Choose a reason for hiding this comment

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

🛠️ Refactor suggestion

Duplicate SWR call & unnecessary re-rendering cost

DubPartnersPopup fetches workspace data once, yet DubPartnersPopupInner invokes useWorkspace() again just to obtain slug.
That triggers an extra SWR request and an additional re-render.

Pass slug (or the whole workspace object) down as a prop instead:

-  return (
-    <DubPartnersPopupInner
-      referenceElement={referenceElement}
-      onDismiss={() => setDismissed(true)}
-    />
-  );
+  return (
+    <DubPartnersPopupInner
+      referenceElement={referenceElement}
+      slug={slug}
+      onDismiss={() => setDismissed(true)}
+    />
+  );

…and remove the second useWorkspace() call.

Committable suggestion skipped: line range outside the PR's diff.

🤖 Prompt for AI Agents
In apps/web/ui/layout/sidebar/dub-partners-popup.tsx around lines 74 to 97, the
DubPartnersPopupInner component calls useWorkspace() again to get the slug,
causing a duplicate SWR fetch and extra re-render. To fix this, retrieve the
slug once in DubPartnersPopup and pass it down as a prop to
DubPartnersPopupInner, then remove the second useWorkspace() call inside
DubPartnersPopupInner to avoid redundant data fetching and rendering.

@bug0-qa-agent
Copy link

bug0-qa-agent bot commented Jun 12, 2025

🤖 Bug0 QA Agent

Here are the results of the automated tests for PR #2522:

To re-run the tests, please comment /bug0 run or push a new commit to this PR.

@bug0-qa-agent
Copy link

bug0-qa-agent bot commented Jun 12, 2025

🤖 Bug0 QA Agent

Here are the results of the automated tests for PR #2522:

To re-run the tests, please comment /bug0 run or push a new commit to this PR.

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: 1

🧹 Nitpick comments (3)
apps/web/app/app.dub.co/(dashboard)/[slug]/(ee)/program/auth.tsx (1)

33-37: Consider extracting the composite check into a named constant for clarity & testability

The three-part condition (!partnersEnabled || !getPlanCapabilities(plan).canManageProgram || !defaultProgramId) is correct but fairly dense. Moving this into a well-named boolean (e.g. needsPartnersUpgradeCTA) improves readability, avoids accidental precedence mistakes when the condition evolves, and makes it trivial to unit-test the auth logic in isolation.

-  if (
-    !partnersEnabled ||
-    !getPlanCapabilities(plan).canManageProgram ||
-    !defaultProgramId
-  ) {
+  const needsPartnersUpgradeCTA =
+    !partnersEnabled ||
+    !getPlanCapabilities(plan).canManageProgram ||
+    !defaultProgramId;
+
+  if (needsPartnersUpgradeCTA) {
apps/web/app/app.dub.co/(dashboard)/[slug]/(ee)/program/partners-ugrade-cta.tsx (2)

8-8: useMemo import becomes redundant if you inline the CTA computation

Should you decide to remove useMemo per the previous comment, remember to delete the useMemo import to avoid an unused-import linter error.

-import { useMemo } from "react";
+// import { useMemo } from "react";  // remove if `useMemo` is dropped

72-79: External wait-list URL opens in the same tab

When partnersEnabled === false, href resolves to https://dub.co/partners, but the Link component omits target="_blank" rel="noopener" so the dashboard is replaced by the marketing page.
Consider conditionally adding these attributes for external destinations to preserve user context.

-        <Link
-          href={href}
+        <Link
+          href={href}
+          {...(href.startsWith("http") && {
+            target: "_blank",
+            rel: "noopener noreferrer",
+          })}
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 0780778 and 2943cf2.

📒 Files selected for processing (6)
  • apps/web/app/app.dub.co/(dashboard)/[slug]/(ee)/program/auth.tsx (1 hunks)
  • apps/web/app/app.dub.co/(dashboard)/[slug]/(ee)/program/partners-ugrade-cta.tsx (3 hunks)
  • apps/web/ui/layout/sidebar/create-program-card.tsx (0 hunks)
  • apps/web/ui/layout/sidebar/dub-partners-popup.tsx (1 hunks)
  • apps/web/ui/layout/sidebar/sidebar-nav-old.tsx (0 hunks)
  • apps/web/ui/layout/sidebar/sidebar-nav.tsx (3 hunks)
💤 Files with no reviewable changes (2)
  • apps/web/ui/layout/sidebar/sidebar-nav-old.tsx
  • apps/web/ui/layout/sidebar/create-program-card.tsx
🚧 Files skipped from review as they are similar to previous changes (2)
  • apps/web/ui/layout/sidebar/sidebar-nav.tsx
  • apps/web/ui/layout/sidebar/dub-partners-popup.tsx
🧰 Additional context used
🧬 Code Graph Analysis (2)
apps/web/app/app.dub.co/(dashboard)/[slug]/(ee)/program/partners-ugrade-cta.tsx (1)
apps/web/lib/plan-capabilities.ts (1)
  • getPlanCapabilities (4-14)
apps/web/app/app.dub.co/(dashboard)/[slug]/(ee)/program/auth.tsx (1)
apps/web/lib/plan-capabilities.ts (1)
  • getPlanCapabilities (4-14)
⏰ Context from checks skipped due to timeout of 90000ms (1)
  • GitHub Check: build

Comment on lines +21 to 41
const { cta, href } = useMemo(() => {
if (partnersEnabled) {
if (!canManageProgram) {
return {
cta: "Upgrade plan",
href: `/${slug}/upgrade`,
};
} else {
return {
cta: store?.programOnboarding ? "Finish creating" : "Create program",
href: `/${slug}/program/new`,
};
}
} else {
return {
cta: "Join the waitlist",
href: "https://dub.co/partners",
};
}
}, [canManageProgram, partnersEnabled, slug]);

Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue

useMemo is missing store?.programOnboarding in its dependency list

store?.programOnboarding directly affects the returned { cta, href }, yet it is omitted from the dependency array.
If onboarding status changes after the first render, the CTA label will stay stale (“Create program” vs “Finish creating”).
Either add the missing dependency or drop the useMemo (the computation is cheap).

-  }, [canManageProgram, partnersEnabled, slug]);
+  }, [canManageProgram, partnersEnabled, slug, store?.programOnboarding]);
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
const { cta, href } = useMemo(() => {
if (partnersEnabled) {
if (!canManageProgram) {
return {
cta: "Upgrade plan",
href: `/${slug}/upgrade`,
};
} else {
return {
cta: store?.programOnboarding ? "Finish creating" : "Create program",
href: `/${slug}/program/new`,
};
}
} else {
return {
cta: "Join the waitlist",
href: "https://dub.co/partners",
};
}
}, [canManageProgram, partnersEnabled, slug]);
const { cta, href } = useMemo(() => {
if (partnersEnabled) {
if (!canManageProgram) {
return {
cta: "Upgrade plan",
href: `/${slug}/upgrade`,
};
} else {
return {
cta: store?.programOnboarding ? "Finish creating" : "Create program",
href: `/${slug}/program/new`,
};
}
} else {
return {
cta: "Join the waitlist",
href: "https://dub.co/partners",
};
}
}, [canManageProgram, partnersEnabled, slug, store?.programOnboarding]);
🤖 Prompt for AI Agents
In
apps/web/app/app.dub.co/(dashboard)/[slug]/(ee)/program/partners-ugrade-cta.tsx
around lines 21 to 41, the useMemo hook's dependency array is missing
store?.programOnboarding, which affects the returned cta and href values. To fix
this, add store?.programOnboarding to the dependency array to ensure the
memoized values update correctly when onboarding status changes, or
alternatively remove useMemo entirely since the computation is inexpensive.

@steven-tey
Copy link
Collaborator

@CodeRabbit final review

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Jun 12, 2025

Tip

For best results, initiate chat on the files or code changes.

@steven-tey below is the holistic “final review” for PR #2522.


🌟 What looks great

  • Nice UX touch – the contextual, floating DubPartnersPopup feels much lighter than the old sidebar card and should surface the feature at the right moment without bloating the nav.
  • Well-scoped gating logic – the popup checks plan, feature flag, device, dismissal state, and workspace loading before displaying, minimising user annoyance and unnecessary renders.
  • Clean sidebar-nav refactor – adding a generic popup prop to NavGroupType is a neat, reusable extension point and avoids hard-coding partner-specific logic into the sidebar.
  • Dead-code removal – deleting create-program-card.tsx and its usages keeps the sidebar lean.

⚠️ Things to consider before merging

Area Concern Impact Suggested action
State key propagation You added the new key dubPartnersPopupDismissed to the Zod workspace schema, but server-side validation/migrations aren’t visible in this PR. Workspace API calls that include this key could be rejected if the backend schema isn’t updated simultaneously. Confirm the API/schema change is already deployed, or coordinate a backend PR.
Persisted dismissal The dismissal flag is written via useWorkspaceStore.setValue, which only saves to localStorage (per the existing store pattern). That means the popup re-appears on another browser / after clearing storage. Could annoy users who use multiple devices. If product requirements expect cross-device persistence, also POST the dismissal to the workspace backend. Otherwise, leave as-is.
Accessibility The popup contains interactive elements but is rendered in a FloatingPortal without a focus trap. Screen-reader / keyboard users may tab behind the overlay. WCAG non-compliance risk. Wrap content in a focus-scope (e.g., @radix-ui/react-focus-scope) or at least set aria-modal="true" and move focus on open.
Mobile check const isMobile = useMediaQuery("(max-width: 768px)") is evaluated client-side only. During SSR the first paint may briefly show the popup on mobile, then hide. Layout jank on mobile devices. Default isMobile to true on first render when typeof window === "undefined".
CSS arrow The popup arrow relies on [data-side="right"] & selector inside <Arrow /> but @floating-ui sets data-placement. Works as shipped, yet any placement change needs matching styles. Minor – future-proofing. Consider using [data-placement^="right"] to cover right-start/end.
Test coverage No new unit/e2e tests were added for the popup visibility logic. Regression risk if gating logic changes. Add a Jest test for DubPartnersPopup render conditions or a Playwright e2e that asserts dismissal persistence.

✨ Finishing touches

  • Several new/modified components (dub-partners-popup.tsx, sidebar-nav.tsx, partners-ugrade-cta.tsx) lack JSDoc/TS docstrings. Adding a brief summary + param/return annotations will satisfy internal lint rules and help future maintainers.

✅ Merge checklist

  • Backend accepts dubPartnersPopupDismissed.
  • Decide if dismissal should sync across devices.
  • (Optional) Add focus-management for accessibility.
  • (Optional) Add tests.
  • Add docstrings (see “Finishing Touches” task tick-box in PR).

Let me know if you’d like code snippets or follow-up issues opened for any of the above. Great work!

@bug0-qa-agent
Copy link

bug0-qa-agent bot commented Jun 12, 2025

🤖 Bug0 QA Agent

Here are the results of the automated tests for PR #2522:

To re-run the tests, please comment /bug0 run or push a new commit to this PR.

@steven-tey steven-tey merged commit 8fe532d into main Jun 12, 2025
8 checks passed
@steven-tey steven-tey deleted the partners-popup branch June 12, 2025 23:05
@coderabbitai coderabbitai bot mentioned this pull request Sep 15, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants