-
Notifications
You must be signed in to change notification settings - Fork 409
feat(clerk-js,clerk-react,vue): Introduce development modal to enable organizations #7159
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
🦋 Changeset detectedLatest commit: 21d53a9 The changes in this PR will be included in the next version bump. This PR includes changesets to release 22 packages
Not sure what this means? Click here to learn what changesets are. Click here if you're a maintainer who wants to add another changeset to this PR |
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
WalkthroughAdds an in-app development prompt to enable Organizations, new Clerk internal APIs and DevTools method, a lazy modal UI and provider, hook integrations to trigger prompt on first use, type and bundle manifest updates, and tests for the new enable flow. Changes
Sequence Diagram(s)sequenceDiagram
participant App as App Component
participant Hook as useOrganization / useOrganizationList
participant Clerk as Clerk Instance
participant UI as EnableOrganizationsPrompt (lazy)
participant DevTools as DevTools API
App->>Hook: mount (uses org-related API)
Hook->>Clerk: __internal_attemptToEnableEnvironmentSetting({ for: "organizations", caller })
alt isEnabled === true
Clerk-->>Hook: { isEnabled: true }
Hook-->>App: render organization UI
else isEnabled === false and devInstance
Clerk->>UI: __internal_openEnableOrganizationsPrompt(props)
UI->>DevTools: __internal_enableEnvironmentSetting({ enable_organizations: true, ... })
DevTools-->>UI: success
UI->>Clerk: onSuccess (may trigger reload)
Clerk->>App: reload (invalidate resources)
else isEnabled === false and prod
Clerk-->>Hook: { isEnabled: false }
Hook-->>App: short-circuit rendering (no prompt)
end
Estimated code review effort🎯 4 (Complex) | ⏱️ ~60 minutes Areas requiring extra attention:
Poem
Pre-merge checks and finishing touches❌ Failed checks (1 warning)
✅ Passed checks (2 passed)
✨ Finishing touches
🧪 Generate unit tests (beta)
Comment |
2014336 to
c9c9e99
Compare
c9c9e99 to
b8fb3db
Compare
b8fb3db to
06a951f
Compare
06a951f to
c990467
Compare
c990467 to
9ade3ae
Compare
8953897 to
a3f9bed
Compare
a3f9bed to
c145bf9
Compare
c145bf9 to
b456c24
Compare
b456c24 to
81ce300
Compare
81ce300 to
b2b3ad4
Compare
04f0eb7 to
7cec59b
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
♻️ Duplicate comments (2)
packages/clerk-js/src/core/clerk.ts (1)
787-794: UseeventPrebuiltComponentOpenedfor the enable-organizations promptOther modal-style entrypoints (e.g.
openSignIn,__internal_openPlanDetails,__internal_openReverification) emiteventPrebuiltComponentOpened, while__internal_openEnableOrganizationsPromptcurrently recordseventPrebuiltComponentMounted. For consistency of telemetry semantics and dashboards, consider switching this toeventPrebuiltComponentOpened('EnableOrganizationsPrompt', props).packages/shared/src/types/clerk.ts (1)
1449-1475: Unifycallerunions between attempt params and prompt props to remove unsafe casts
__internal_EnableOrganizationsPromptProps['caller']is missing'CreateOrganization'and'TaskChooseOrganization', which are present in__internal_AttemptToEnableEnvironmentSettingParams['caller']. This mismatch is currently papered over inClerk.__internal_attemptToEnableEnvironmentSettingby casting the prompt propsas __internal_EnableOrganizationsPromptProps, which defeats type checking and can hide future breakage if the prompt branches oncaller.Recommend:
- Extract a shared alias, e.g.
type __internal_OrganizationsCaller = 'OrganizationSwitcher' | 'OrganizationProfile' | 'OrganizationList' | 'CreateOrganization' | 'TaskChooseOrganization' | 'useOrganizationList' | 'useOrganization';- Use that alias for the
callerfield in both__internal_EnableOrganizationsPromptPropsand__internal_AttemptToEnableEnvironmentSettingParams.- Then remove the
as __internal_EnableOrganizationsPromptPropscast at the call site inpackages/clerk-js/src/core/clerk.ts.This keeps the internal surface self-consistent and lets the compiler enforce exhaustiveness as you add more callers.
🧹 Nitpick comments (1)
packages/clerk-js/src/core/__tests__/clerk.test.ts (1)
2512-2634: Align test keys and environment flags with test descriptionsThe new tests correctly exercise the dev-only prompt behavior, but a couple of fixtures are slightly misleading:
- In “does not open prompt if organizations is enabled in development”,
productionPublishableKeyis used; consider usingdevelopmentPublishableKeyto match the description.- In “does not open prompt if organizations is disabled in production”, the stubbed environment sets
isProduction: () => falsewhile the test name mentions production.These don’t affect correctness (the code gates on
instanceType), but tightening them up will make the intent clearer for future readers.
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Disabled knowledge base sources:
- Linear integration is disabled by default for public repositories
You can enable these sources in your CodeRabbit configuration.
📒 Files selected for processing (3)
packages/clerk-js/src/core/__tests__/clerk.test.ts(1 hunks)packages/clerk-js/src/core/clerk.ts(9 hunks)packages/shared/src/types/clerk.ts(2 hunks)
🧰 Additional context used
📓 Path-based instructions (9)
**/*.{js,jsx,ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
All code must pass ESLint checks with the project's configuration
Files:
packages/clerk-js/src/core/__tests__/clerk.test.tspackages/clerk-js/src/core/clerk.tspackages/shared/src/types/clerk.ts
**/*.{js,jsx,ts,tsx,json,md,yml,yaml}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Use Prettier for consistent code formatting
Files:
packages/clerk-js/src/core/__tests__/clerk.test.tspackages/clerk-js/src/core/clerk.tspackages/shared/src/types/clerk.ts
packages/**/src/**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
TypeScript is required for all packages
Files:
packages/clerk-js/src/core/__tests__/clerk.test.tspackages/clerk-js/src/core/clerk.tspackages/shared/src/types/clerk.ts
**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Follow established naming conventions (PascalCase for components, camelCase for variables)
Prefer importing types from
@clerk/shared/typesinstead of the deprecated@clerk/typesalias
Files:
packages/clerk-js/src/core/__tests__/clerk.test.tspackages/clerk-js/src/core/clerk.tspackages/shared/src/types/clerk.ts
packages/**/src/**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
packages/**/src/**/*.{ts,tsx,js,jsx}: Maintain comprehensive JSDoc comments for public APIs
Use tree-shaking friendly exports
Validate all inputs and sanitize outputs
All public APIs must be documented with JSDoc
Use dynamic imports for optional features
Provide meaningful error messages to developers
Include error recovery suggestions where applicable
Log errors appropriately for debugging
Lazy load components and features when possible
Implement proper caching strategies
Use efficient data structures and algorithms
Implement proper logging with different levels
Files:
packages/clerk-js/src/core/__tests__/clerk.test.tspackages/clerk-js/src/core/clerk.tspackages/shared/src/types/clerk.ts
**/*.{test,spec}.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
**/*.{test,spec}.{ts,tsx,js,jsx}: Unit tests are required for all new functionality
Verify proper error handling and edge cases
Include tests for all new features
Files:
packages/clerk-js/src/core/__tests__/clerk.test.ts
**/*.ts?(x)
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Use proper TypeScript error types
Files:
packages/clerk-js/src/core/__tests__/clerk.test.tspackages/clerk-js/src/core/clerk.tspackages/shared/src/types/clerk.ts
**/*.{test,spec,e2e}.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Use real Clerk instances for integration tests
Files:
packages/clerk-js/src/core/__tests__/clerk.test.ts
**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/typescript.mdc)
**/*.{ts,tsx}: Always define explicit return types for functions, especially public APIs
Use proper type annotations for variables and parameters where inference isn't clear
Avoidanytype - preferunknownwhen type is uncertain, then narrow with type guards
Implement type guards forunknowntypes using the patternfunction isType(value: unknown): value is Type
Useinterfacefor object shapes that might be extended
Usetypefor unions, primitives, and computed types
Preferreadonlyproperties for immutable data structures
Useprivatefor internal implementation details in classes
Useprotectedfor inheritance hierarchies
Usepublicexplicitly for clarity in public APIs
Use mixins for shared behavior across unrelated classes in TypeScript
Use generic constraints with bounded type parameters like<T extends { id: string }>
Use utility types likeOmit,Partial, andPickfor data transformation instead of manual type construction
Use discriminated unions instead of boolean flags for state management and API responses
Use mapped types for transforming object types
Use conditional types for type-level logic
Leverage template literal types for string manipulation at the type level
Use ES6 imports/exports consistently
Use default exports sparingly, prefer named exports
Document functions with JSDoc comments including @param, @returns, @throws, and @example tags
Create custom error classes that extend Error for specific error types
Use the Result pattern for error handling instead of throwing exceptions
Use optional chaining (?.) and nullish coalescing (??) operators for safe property access
Let TypeScript infer obvious types to reduce verbosity
Useconst assertionswithas constfor literal types
Usesatisfiesoperator for type checking without widening types
Declare readonly arrays and objects for immutable data structures
Use spread operator and array spread for immutable updates instead of mutations
Use lazy loading for large types...
Files:
packages/clerk-js/src/core/__tests__/clerk.test.tspackages/clerk-js/src/core/clerk.tspackages/shared/src/types/clerk.ts
🧬 Code graph analysis (1)
packages/clerk-js/src/core/clerk.ts (2)
packages/shared/src/types/clerk.ts (3)
__internal_AttemptToEnableEnvironmentSettingParams(1461-1472)__internal_AttemptToEnableEnvironmentSettingResult(1474-1476)__internal_EnableOrganizationsPromptProps(1449-1459)packages/clerk-js/src/utils/componentGuards.ts (1)
disabledOrganizationsFeature(21-23)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (2)
- GitHub Check: semgrep-cloud-platform/scan
- GitHub Check: semgrep-cloud-platform/scan
🔇 Additional comments (1)
packages/clerk-js/src/core/clerk.ts (1)
872-886: Centralized organizations enablement guard is a solid improvementWiring all organization entrypoints (open/mount for OrganizationProfile, CreateOrganization, OrganizationSwitcher, OrganizationList, TaskChooseOrganization) through
__internal_attemptToEnableEnvironmentSettinggives you a single place to manage dev-only prompting vs. silent no-op behavior when organizations are disabled. The pattern is consistent and the early return on!isEnabledkeeps the call sites straightforward.Also applies to: 907-923, 1056-1072, 1103-1119, 1141-1157, 1187-1203, 1389-1403
There was a problem hiding this 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 (1)
packages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsx (1)
116-145:alignItems/justifyContentuse invalid value'flex-center'At lines 134-135,
alignItems: 'flex-center'andjustifyContent: 'flex-center'are not valid CSS values and will be ignored, likely breaking centering in the expanded state.Consider changing both to
'center':- '&[data-expanded="true"]': { - flexDirection: 'column', - alignItems: 'flex-center', - justifyContent: 'flex-center', + '&[data-expanded="true"]': { + flexDirection: 'column', + alignItems: 'center', + justifyContent: 'center',
♻️ Duplicate comments (6)
packages/vue/src/composables/useOrganization.ts (1)
59-72: Guard the watcher to avoid redundant enablement attempts and ensure cleanupAs written, every
useOrganization()invocation creates a watcher that will call__internal_attemptToEnableEnvironmentSettingonce and thenunwatch(). If multiple components use this composable, they can all trigger the internal enablement call, which is unnecessary work and diverges from the guarded behavior in the React hooks.To align with the React implementation and the earlier review, add a module-level idempotency guard and ensure
unwatch()always runs:-import { computed, watch } from 'vue'; +import { computed, watch } from 'vue'; + +let hasAttemptedToEnableOrganizations = false; // ... - const unwatch = watch( - clerk, - value => { - if (value) { - // Optional chaining is important for `@clerk/vue` usage with older clerk-js versions that don't have the method - value.__internal_attemptToEnableEnvironmentSetting?.({ - for: 'organizations', - caller: 'useOrganization', - }); - unwatch(); - } - }, - { immediate: true }, - ); + const unwatch = watch( + clerk, + value => { + if (!value || hasAttemptedToEnableOrganizations) { + return; + } + + hasAttemptedToEnableOrganizations = true; + try { + // Optional chaining is important for `@clerk/vue` usage with older clerk-js versions that don't have the method + value.__internal_attemptToEnableEnvironmentSetting?.({ + for: 'organizations', + caller: 'useOrganization', + }); + } finally { + unwatch(); + } + }, + { immediate: true }, + );This ensures the enablement attempt runs at most once across all
useOrganizationinstances and that the watcher is always cleaned up, even if the internal method throws.packages/react/src/isomorphicClerk.ts (1)
1490-1499: Return type inconsistency: missing return value when clerkjs not loaded.The method declares
__internal_AttemptToEnableEnvironmentSettingResult | voidas return type, allowing the implicitvoidreturn in the else branch (line 1497). However, this creates an inconsistent contract: callers cannot determine whether the feature is enabled when invoked before clerkjs loads.Since this method is designed to return synchronous enablement status, consider returning a concrete result immediately when clerkjs is unavailable rather than queueing the call:
__internal_attemptToEnableEnvironmentSetting = ( options: __internal_AttemptToEnableEnvironmentSettingParams, ): __internal_AttemptToEnableEnvironmentSettingResult | void => { const callback = () => this.clerkjs?.__internal_attemptToEnableEnvironmentSetting(options); if (this.clerkjs && this.loaded) { return callback() as __internal_AttemptToEnableEnvironmentSettingResult; } else { - this.premountMethodCalls.set('__internal_attemptToEnableEnvironmentSetting', callback); + // Return a result indicating enablement cannot be determined/performed yet + return { isEnabled: false }; } };This ensures callers always receive a typed response indicating the current enablement state.
packages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsx (1)
503-526: Add hover and focus-visible styles to Link component for accessibility.The Link component lacks interactive states. Past review comments flagged this, but the styles are not yet present in the code. Without these states, keyboard users don't get clear focus indicators, and mouse users don't get hover feedback.
Apply this diff to add the missing styles:
const Link = forwardRef<HTMLAnchorElement, React.ComponentProps<'a'> & { css?: SerializedStyles }>( ({ children, css: cssProp, ...props }, ref) => { return ( <a ref={ref} {...props} css={[ basePromptElementStyles, css` color: #a8a8ff; font-size: inherit; font-weight: 500; line-height: 1.3; font-size: 0.8125rem; min-width: 0; + cursor: pointer; + transition: color 120ms ease-in-out; + + &:hover { + color: #c4c4ff; + } + + &:focus-visible { + outline: 2px solid white; + outline-offset: 2px; + border-radius: 2px; + } + + @media (prefers-reduced-motion: reduce) { + transition: none; + } `, cssProp, ]} > {children} </a> ); }, );packages/shared/src/types/clerk.ts (1)
1449-1476: Align caller unions to avoid unsafe type assertions.The
callerunion in__internal_EnableOrganizationsPromptProps(lines 1453-1458) includes 5 values, while__internal_AttemptToEnableEnvironmentSettingParams.caller(lines 1463-1470) includes 7 values—adding'CreateOrganization'and'TaskChooseOrganization'. This mismatch forces unsafe casting when passing the caller from__internal_attemptToEnableEnvironmentSettingto__internal_openEnableOrganizationsPrompt.Consider one of these approaches:
- Extend the prompt type to include all callers:
export type __internal_EnableOrganizationsPromptProps = { onSuccess?: () => void; onClose?: () => void; } & { caller: | 'OrganizationSwitcher' | 'OrganizationProfile' | 'OrganizationList' + | 'CreateOrganization' + | 'TaskChooseOrganization' | 'useOrganizationList' | 'useOrganization'; };
- Extract a shared union type:
+export type OrganizationFeatureCaller = + | 'OrganizationSwitcher' + | 'OrganizationProfile' + | 'OrganizationList' + | 'CreateOrganization' + | 'TaskChooseOrganization' + | 'useOrganizationList' + | 'useOrganization'; + export type __internal_EnableOrganizationsPromptProps = { onSuccess?: () => void; onClose?: () => void; } & { - caller: - | 'OrganizationSwitcher' - | 'OrganizationProfile' - | 'OrganizationList' - | 'useOrganizationList' - | 'useOrganization'; + caller: OrganizationFeatureCaller; }; export type __internal_AttemptToEnableEnvironmentSettingParams = { for: 'organizations'; - caller: - | 'OrganizationSwitcher' - | 'OrganizationProfile' - | 'OrganizationList' - | 'CreateOrganization' - | 'TaskChooseOrganization' - | 'useOrganizationList' - | 'useOrganization'; + caller: OrganizationFeatureCaller; onClose?: () => void; };Either approach eliminates the need for type assertions and ensures type safety across all call sites.
packages/clerk-js/src/core/clerk.ts (2)
787-795: UseeventPrebuiltComponentOpenedfor the enable‑organizations prompt telemetry
__internal_openEnableOrganizationsPromptopens a modal but records telemetry witheventPrebuiltComponentMounted:this.telemetry?.record(eventPrebuiltComponentMounted('EnableOrganizationsPrompt', props));Other modal “open*” APIs (e.g.
openSignIn,__internal_openPlanDetails) useeventPrebuiltComponentOpenedso analytics reflect “prompt shown” rather than “component mounted”.For consistency and clearer metrics, switch this to:
this.telemetry?.record(eventPrebuiltComponentOpened('EnableOrganizationsPrompt', props));As per coding guidelines, keeping telemetry semantics consistent across prebuilt components simplifies downstream analysis.
751-781: Removeas __internal_EnableOrganizationsPromptPropsand align types between attempt params and prompt props
__internal_attemptToEnableEnvironmentSettingbuilds the props for__internal_openEnableOrganizationsPromptand then forces them to__internal_EnableOrganizationsPromptPropswith anascast:this.__internal_openEnableOrganizationsPrompt({ caller, onSuccess: () => window.location.reload(), onClose: params.onClose, } as __internal_EnableOrganizationsPromptProps);This hides type drift between
__internal_AttemptToEnableEnvironmentSettingParams['caller']and__internal_EnableOrganizationsPromptProps['caller']and weakens exhaustiveness checks inside the prompt.Prefer to:
- Expand
__internal_EnableOrganizationsPromptPropsso that the object constructed here is assignable without a cast, and- Drop the
as __internal_EnableOrganizationsPromptPropsso the compiler enforces compatibility in both directions.This keeps the internal flow type‑safe and avoids future breakage when new callers are added.
As per coding guidelines, we should avoid masking type mismatches with assertions.
🧹 Nitpick comments (3)
packages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsx (1)
87-112: Good reuse ofbasePromptElementStyles; consider further consolidation into themed primitivesInjecting
basePromptElementStylesinto the main CTA, header button, header text, body copy, and secondary CTA (lines 88, 154, 260, 326, 477) is a solid step toward consistent prompt styling.As a follow-up, you might want to:
- Extract small shared components (e.g.
PromptHeaderText,PromptBodyText,PromptSecondaryLink) that already bake inbasePromptElementStyles.- Gradually replace the hard-coded hex colors and ad‑hoc Emotion blocks here with
sx+ theme tokens, to better match the styled-system guidance and reduce one-off overrides.Also applies to: 154-159, 260-266, 326-343, 477-501
packages/shared/src/react/hooks/useCheckout.ts (1)
125-126: This bypass pattern is widespread—coordinate an architectural fix across affected files.The comment accurately describes the issue, but this same workaround appears in 6+ files across the codebase (PricingTable, APIKeys, SubscriptionDetails, PaymentMethods, Plans, and now useCheckout), suggesting this is an intentional architectural decision rather than an isolated workaround.
Since the enable organizations prompt is a real, intentionally-triggered feature in dev instances, consider addressing this at the architectural level rather than accepting the pattern piecemeal:
Make the prompt logic more selective: Extend
useOrganization()or the triggering logic to skip prompting for specific flows (checkout, billing components, etc.) that access organizations in expected contexts.Add a suppression flag: Enable
useOrganization({ suppressEnablePrompt: true })for all affected locations, ensuring consistent behavior.Document the decision: If this pattern must remain, centralize the comment in a shared constant or doc to avoid duplication across 6+ files.
Coordinate fixes across: useCheckout.ts, PricingTableDefault.tsx, APIKeys.tsx, SubscriptionDetails.tsx, PaymentMethods.tsx, and Plans.tsx.
packages/clerk-js/src/core/clerk.ts (1)
872-885: Confirm intended non‑dev behavior when organizations are disabledAll organization entrypoints now short‑circuit through
__internal_attemptToEnableEnvironmentSetting:
openOrganizationProfileopenCreateOrganizationmountOrganizationProfilemountCreateOrganizationmountOrganizationSwitchermountOrganizationListmountTaskChooseOrganizationEach pattern is:
const { isEnabled: isOrganizationsEnabled } = this.__internal_attemptToEnableEnvironmentSetting({ ... }); if (!isOrganizationsEnabled) { return; }and
__internal_attemptToEnableEnvironmentSettingreturns{ isEnabled: false }wheneverdisabledOrganizationsFeature(this, this.environment)is true, regardless ofinstanceType.This means that in staging/production environments where organizations are disabled, these methods now become silent no‑ops (no UI, no error), whereas previously they may have mounted components or relied on different guards/runtime errors.
Please double‑check that this semantic change for non‑dev instances is intentional; if the goal was “dev‑only prompt, preserve prior behavior elsewhere”, you may want to:
- Either make
__internal_attemptToEnableEnvironmentSettingalways return{ isEnabled: true }outside development, or- Keep non‑dev behavior (e.g. specific
ClerkRuntimeErrorpaths) explicitly mirrored here.As per coding guidelines, it’s worth validating that new central guards don’t inadvertently change production semantics.
Also applies to: 909-922, 1058-1072, 1105-1119, 1143-1157, 1189-1203, 1392-1404
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Disabled knowledge base sources:
- Linear integration is disabled by default for public repositories
You can enable these sources in your CodeRabbit configuration.
📒 Files selected for processing (28)
.changeset/flat-ravens-call.md(1 hunks)packages/clerk-js/bundlewatch.config.json(2 hunks)packages/clerk-js/src/core/__tests__/clerk.test.ts(1 hunks)packages/clerk-js/src/core/clerk.ts(9 hunks)packages/clerk-js/src/core/resources/DevTools.ts(1 hunks)packages/clerk-js/src/ui/Components.tsx(11 hunks)packages/clerk-js/src/ui/components/APIKeys/APIKeys.tsx(2 hunks)packages/clerk-js/src/ui/components/KeylessPrompt/ClerkLogoIcon.tsx(0 hunks)packages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsx(1 hunks)packages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsx(9 hunks)packages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/use-revalidate-environment.ts(1 hunks)packages/clerk-js/src/ui/components/devPrompts/shared.tsx(1 hunks)packages/clerk-js/src/ui/customizables/parseAppearance.ts(1 hunks)packages/clerk-js/src/ui/elements/Modal.tsx(2 hunks)packages/clerk-js/src/ui/elements/contexts/index.tsx(1 hunks)packages/clerk-js/src/ui/lazyModules/components.ts(4 hunks)packages/clerk-js/src/ui/lazyModules/providers.tsx(1 hunks)packages/react/src/isomorphicClerk.ts(5 hunks)packages/shared/src/organization.ts(2 hunks)packages/shared/src/react/__tests__/payment-element.test.tsx(0 hunks)packages/shared/src/react/hooks/useCheckout.ts(1 hunks)packages/shared/src/react/hooks/useOrganization.tsx(2 hunks)packages/shared/src/react/hooks/useOrganizationList.tsx(2 hunks)packages/shared/src/types/appearance.ts(2 hunks)packages/shared/src/types/clerk.ts(2 hunks)packages/shared/src/types/devtools.ts(1 hunks)packages/shared/src/types/index.ts(1 hunks)packages/vue/src/composables/useOrganization.ts(2 hunks)
💤 Files with no reviewable changes (2)
- packages/shared/src/react/tests/payment-element.test.tsx
- packages/clerk-js/src/ui/components/KeylessPrompt/ClerkLogoIcon.tsx
🚧 Files skipped from review as they are similar to previous changes (10)
- packages/shared/src/react/hooks/useOrganizationList.tsx
- packages/clerk-js/src/ui/elements/Modal.tsx
- packages/clerk-js/src/core/tests/clerk.test.ts
- packages/clerk-js/src/ui/lazyModules/components.ts
- packages/shared/src/react/hooks/useOrganization.tsx
- packages/clerk-js/src/core/resources/DevTools.ts
- packages/clerk-js/src/ui/components/APIKeys/APIKeys.tsx
- packages/clerk-js/src/ui/components/devPrompts/shared.tsx
- packages/clerk-js/src/ui/elements/contexts/index.tsx
- .changeset/flat-ravens-call.md
🧰 Additional context used
📓 Path-based instructions (12)
packages/clerk-js/src/ui/**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/clerk-js-ui.mdc)
packages/clerk-js/src/ui/**/*.{ts,tsx}: Element descriptors should be written in camelCase
Use useCardState for card-level state management
Use useFormState for form-level state management
Use useLoadingStatus for managing loading states
Use useFormControl hook for form field state management with validation and localization support
All rendered values must be localized using useLocalizations hook - hard coded values are not allowed
Use localizationKeys for translating UI text with support for parameters and error messages
Use handleError utility for API error handling and provide field states for proper error mapping
Use the styled system sx prop with theme tokens for custom styling instead of inline styles
Use the Card component pattern with Card.Root, Card.Header, Card.Title, Card.Content, and Card.Footer for consistent card layouts
Use FormContainer with headerTitle and headerSubtitle localization keys combined with Form.Root and FormButtons for consistent form layouts
When form submission occurs, manage loading and error states by calling status.setLoading(), card.setLoading(), and card.setError() appropriately
Files:
packages/clerk-js/src/ui/customizables/parseAppearance.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/use-revalidate-environment.tspackages/clerk-js/src/ui/Components.tsxpackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsxpackages/clerk-js/src/ui/lazyModules/providers.tsxpackages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsx
**/*.{js,jsx,ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
All code must pass ESLint checks with the project's configuration
Files:
packages/clerk-js/src/ui/customizables/parseAppearance.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/use-revalidate-environment.tspackages/shared/src/types/devtools.tspackages/shared/src/organization.tspackages/clerk-js/src/ui/Components.tsxpackages/shared/src/types/index.tspackages/react/src/isomorphicClerk.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsxpackages/clerk-js/src/ui/lazyModules/providers.tsxpackages/shared/src/types/clerk.tspackages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsxpackages/shared/src/types/appearance.tspackages/clerk-js/src/core/clerk.tspackages/vue/src/composables/useOrganization.tspackages/shared/src/react/hooks/useCheckout.ts
**/*.{js,jsx,ts,tsx,json,md,yml,yaml}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Use Prettier for consistent code formatting
Files:
packages/clerk-js/src/ui/customizables/parseAppearance.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/use-revalidate-environment.tspackages/shared/src/types/devtools.tspackages/shared/src/organization.tspackages/clerk-js/src/ui/Components.tsxpackages/shared/src/types/index.tspackages/react/src/isomorphicClerk.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsxpackages/clerk-js/src/ui/lazyModules/providers.tsxpackages/clerk-js/bundlewatch.config.jsonpackages/shared/src/types/clerk.tspackages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsxpackages/shared/src/types/appearance.tspackages/clerk-js/src/core/clerk.tspackages/vue/src/composables/useOrganization.tspackages/shared/src/react/hooks/useCheckout.ts
packages/**/src/**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
TypeScript is required for all packages
Files:
packages/clerk-js/src/ui/customizables/parseAppearance.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/use-revalidate-environment.tspackages/shared/src/types/devtools.tspackages/shared/src/organization.tspackages/clerk-js/src/ui/Components.tsxpackages/shared/src/types/index.tspackages/react/src/isomorphicClerk.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsxpackages/clerk-js/src/ui/lazyModules/providers.tsxpackages/shared/src/types/clerk.tspackages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsxpackages/shared/src/types/appearance.tspackages/clerk-js/src/core/clerk.tspackages/vue/src/composables/useOrganization.tspackages/shared/src/react/hooks/useCheckout.ts
**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Follow established naming conventions (PascalCase for components, camelCase for variables)
Prefer importing types from
@clerk/shared/typesinstead of the deprecated@clerk/typesalias
Files:
packages/clerk-js/src/ui/customizables/parseAppearance.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/use-revalidate-environment.tspackages/shared/src/types/devtools.tspackages/shared/src/organization.tspackages/clerk-js/src/ui/Components.tsxpackages/shared/src/types/index.tspackages/react/src/isomorphicClerk.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsxpackages/clerk-js/src/ui/lazyModules/providers.tsxpackages/shared/src/types/clerk.tspackages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsxpackages/shared/src/types/appearance.tspackages/clerk-js/src/core/clerk.tspackages/vue/src/composables/useOrganization.tspackages/shared/src/react/hooks/useCheckout.ts
packages/**/src/**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
packages/**/src/**/*.{ts,tsx,js,jsx}: Maintain comprehensive JSDoc comments for public APIs
Use tree-shaking friendly exports
Validate all inputs and sanitize outputs
All public APIs must be documented with JSDoc
Use dynamic imports for optional features
Provide meaningful error messages to developers
Include error recovery suggestions where applicable
Log errors appropriately for debugging
Lazy load components and features when possible
Implement proper caching strategies
Use efficient data structures and algorithms
Implement proper logging with different levels
Files:
packages/clerk-js/src/ui/customizables/parseAppearance.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/use-revalidate-environment.tspackages/shared/src/types/devtools.tspackages/shared/src/organization.tspackages/clerk-js/src/ui/Components.tsxpackages/shared/src/types/index.tspackages/react/src/isomorphicClerk.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsxpackages/clerk-js/src/ui/lazyModules/providers.tsxpackages/shared/src/types/clerk.tspackages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsxpackages/shared/src/types/appearance.tspackages/clerk-js/src/core/clerk.tspackages/vue/src/composables/useOrganization.tspackages/shared/src/react/hooks/useCheckout.ts
**/*.ts?(x)
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Use proper TypeScript error types
Files:
packages/clerk-js/src/ui/customizables/parseAppearance.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/use-revalidate-environment.tspackages/shared/src/types/devtools.tspackages/shared/src/organization.tspackages/clerk-js/src/ui/Components.tsxpackages/shared/src/types/index.tspackages/react/src/isomorphicClerk.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsxpackages/clerk-js/src/ui/lazyModules/providers.tsxpackages/shared/src/types/clerk.tspackages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsxpackages/shared/src/types/appearance.tspackages/clerk-js/src/core/clerk.tspackages/vue/src/composables/useOrganization.tspackages/shared/src/react/hooks/useCheckout.ts
**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/typescript.mdc)
**/*.{ts,tsx}: Always define explicit return types for functions, especially public APIs
Use proper type annotations for variables and parameters where inference isn't clear
Avoidanytype - preferunknownwhen type is uncertain, then narrow with type guards
Implement type guards forunknowntypes using the patternfunction isType(value: unknown): value is Type
Useinterfacefor object shapes that might be extended
Usetypefor unions, primitives, and computed types
Preferreadonlyproperties for immutable data structures
Useprivatefor internal implementation details in classes
Useprotectedfor inheritance hierarchies
Usepublicexplicitly for clarity in public APIs
Use mixins for shared behavior across unrelated classes in TypeScript
Use generic constraints with bounded type parameters like<T extends { id: string }>
Use utility types likeOmit,Partial, andPickfor data transformation instead of manual type construction
Use discriminated unions instead of boolean flags for state management and API responses
Use mapped types for transforming object types
Use conditional types for type-level logic
Leverage template literal types for string manipulation at the type level
Use ES6 imports/exports consistently
Use default exports sparingly, prefer named exports
Document functions with JSDoc comments including @param, @returns, @throws, and @example tags
Create custom error classes that extend Error for specific error types
Use the Result pattern for error handling instead of throwing exceptions
Use optional chaining (?.) and nullish coalescing (??) operators for safe property access
Let TypeScript infer obvious types to reduce verbosity
Useconst assertionswithas constfor literal types
Usesatisfiesoperator for type checking without widening types
Declare readonly arrays and objects for immutable data structures
Use spread operator and array spread for immutable updates instead of mutations
Use lazy loading for large types...
Files:
packages/clerk-js/src/ui/customizables/parseAppearance.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/use-revalidate-environment.tspackages/shared/src/types/devtools.tspackages/shared/src/organization.tspackages/clerk-js/src/ui/Components.tsxpackages/shared/src/types/index.tspackages/react/src/isomorphicClerk.tspackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsxpackages/clerk-js/src/ui/lazyModules/providers.tsxpackages/shared/src/types/clerk.tspackages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsxpackages/shared/src/types/appearance.tspackages/clerk-js/src/core/clerk.tspackages/vue/src/composables/useOrganization.tspackages/shared/src/react/hooks/useCheckout.ts
**/*.tsx
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
**/*.tsx: Use error boundaries in React components
Minimize re-renders in React components
**/*.tsx: Use proper type definitions for props and state in React components
Leverage TypeScript's type inference where possible in React components
Use proper event types for handlers in React components
Implement proper generic types for reusable React components
Use proper type guards for conditional rendering in React components
Files:
packages/clerk-js/src/ui/Components.tsxpackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsxpackages/clerk-js/src/ui/lazyModules/providers.tsxpackages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsx
**/*.{md,tsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Update documentation for API changes
Files:
packages/clerk-js/src/ui/Components.tsxpackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsxpackages/clerk-js/src/ui/lazyModules/providers.tsxpackages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsx
**/*.{jsx,tsx}
📄 CodeRabbit inference engine (.cursor/rules/react.mdc)
**/*.{jsx,tsx}: Always use functional components with hooks instead of class components
Follow PascalCase naming for components (e.g.,UserProfile,NavigationMenu)
Keep components focused on a single responsibility - split large components
Limit component size to 150-200 lines; extract logic into custom hooks
Use composition over inheritance - prefer smaller, composable components
Export components as named exports for better tree-shaking
One component per file with matching filename and component name
Separate UI components from business logic components
Use useState for simple state management in React components
Use useReducer for complex state logic in React components
Implement proper state initialization in React components
Use proper state updates with callbacks in React components
Implement proper state cleanup in React components
Use Context API for theme/authentication state management
Implement proper state persistence in React applications
Use React.memo for expensive components
Implement proper useCallback for handlers in React components
Use proper useMemo for expensive computations in React components
Implement proper virtualization for lists in React components
Use proper code splitting with React.lazy in React applications
Implement proper cleanup in useEffect hooks
Use proper refs for DOM access in React components
Implement proper event listener cleanup in React components
Use proper abort controllers for fetch in React components
Implement proper subscription cleanup in React components
Use proper HTML elements for semantic HTML in React components
Implement proper ARIA attributes for accessibility in React components
Use proper heading hierarchy in React components
Implement proper form labels in React components
Use proper button types in React components
Implement proper focus management for keyboard navigation in React components
Use proper keyboard shortcuts in React components
Implement proper tab order in React components
Use proper ...
Files:
packages/clerk-js/src/ui/Components.tsxpackages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsxpackages/clerk-js/src/ui/lazyModules/providers.tsxpackages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsx
**/index.ts
📄 CodeRabbit inference engine (.cursor/rules/typescript.mdc)
Avoid barrel files (index.ts re-exports) as they can cause circular dependencies
Files:
packages/shared/src/types/index.ts
🧬 Code graph analysis (4)
packages/clerk-js/src/ui/Components.tsx (4)
packages/shared/src/types/clerk.ts (2)
__internal_EnableOrganizationsPromptProps(1449-1459)UserProfileProps(1565-1603)packages/clerk-js/src/ui/lazyModules/providers.tsx (1)
LazyEnableOrganizationsPromptProvider(212-227)packages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsx (1)
EnableOrganizationsPrompt(278-284)packages/clerk-js/src/ui/lazyModules/components.ts (1)
EnableOrganizationsPrompt(49-51)
packages/react/src/isomorphicClerk.ts (1)
packages/shared/src/types/clerk.ts (3)
__internal_EnableOrganizationsPromptProps(1449-1459)__internal_AttemptToEnableEnvironmentSettingParams(1461-1472)__internal_AttemptToEnableEnvironmentSettingResult(1474-1476)
packages/clerk-js/src/ui/lazyModules/providers.tsx (3)
packages/shared/src/types/appearance.ts (1)
Appearance(1057-1131)packages/clerk-js/src/ui/router/VirtualRouter.tsx (1)
VirtualRouter(15-67)packages/clerk-js/src/ui/customizables/index.ts (1)
AppearanceProvider(9-9)
packages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsx (6)
packages/shared/src/types/clerk.ts (1)
__internal_EnableOrganizationsPromptProps(1449-1459)packages/shared/src/types/devtools.ts (1)
EnableEnvironmentSettingParams(3-6)packages/clerk-js/src/core/resources/DevTools.ts (1)
DevTools(8-21)packages/clerk-js/src/ui/elements/Modal.tsx (1)
Modal(26-111)packages/clerk-js/src/ui/components/devPrompts/shared.tsx (1)
PromptContainer(10-28)packages/clerk-js/src/ui/elements/Switch.tsx (1)
Switch(15-108)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (5)
- GitHub Check: Formatting | Dedupe | Changeset
- GitHub Check: Build Packages
- GitHub Check: Analyze (javascript-typescript)
- GitHub Check: semgrep-cloud-platform/scan
- GitHub Check: semgrep-cloud-platform/scan
🔇 Additional comments (10)
packages/clerk-js/bundlewatch.config.json (2)
4-6: Bundle size increases are reasonable for the new development modal feature.The modest increases (+2KB for browser variants, +4KB for the legacy variant) align with adding a new UI component and associated DevTools integration logic.
26-26: New entry follows established patterns.The new
enableOrganizationsPrompt*.jsentry is correctly named, placed near related prompt components (keylessPrompt), and sized consistently with similar modular UI components.packages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/index.tsx (1)
8-17: Imports now correctly rely on shared prompt primitivesSwitching to
PromptContainer,PromptSuccessIcon,ClerkLogoIcon,handleDashboardUrlParsing, andbasePromptElementStylesfrom../sharedkeeps this prompt aligned with the new shared dev-prompt system and avoids duplicating styling/utility logic. No issues spotted with these imports or their usage.packages/clerk-js/src/ui/components/devPrompts/KeylessPrompt/use-revalidate-environment.ts (1)
4-6: Import path and typing adjustments look correctSwitching to explicit
Clerk/Environmenttype imports from core and updating theuseEnvironmentpath are consistent with the existing usage and do not change runtime behavior. No issues here.packages/shared/src/types/index.ts (1)
15-15: DevTools types export is consistent with existing type barrelRe-exporting
./devtoolshere matches the established pattern in this file and correctly surfaces the new DevTools types to consumers of@clerk/shared/types. No issues.packages/shared/src/types/appearance.ts (1)
1038-1130: New enable-organizations appearance types follow existing pattern; ensure key alignmentAdding
EnableOrganizationsTheme = Themeand theenableOrganizations?: T;property onAppearance<T>is consistent with how other component‑specific themes are modeled (e.g.signIn,organizationList,taskChooseOrganization).Given this, the value passed as
appearanceKeyfor the new prompt should be'enableOrganizations'so thatglobalAppearance.enableOrganizationsis actually picked up in the appearance cascade. Right nowparseAppearanceand the lazy provider use'enableOrganizationsPrompt', which won’t match this property—see the comment inparseAppearance.tsfor the suggested alignment.packages/shared/src/organization.ts (1)
1-4: Internal React hook for attempting organizations enablement looks sound
useAttemptToEnableOrganizationscleanly wraps the internal__internal_attemptToEnableEnvironmentSettingcall with auseRefguard anduseEffect, ensuring the attempt runs at most once per hook instance and remains compatible with older clerk-js versions via optional chaining. This is a reasonable encapsulation for the React hooks (useOrganization,useOrganizationList) to share.Also applies to: 22-44
packages/shared/src/types/devtools.ts (1)
1-13: DevTools resource typings look correct; double‑check param naming with backend
EnableEnvironmentSettingParamsandDevToolsResource.__internal_enableEnvironmentSettingare modeled consistently with the rest of the shared types and DevTools resource patterns.One thing to confirm: the optional field is named
organization_allow_personal_accounts, whereas the PR description references anallow_personal_accountsfield coming from clerk-go. Please verify that this name matches the backend endpoint contract so the PATCH body is accepted as expected.packages/clerk-js/src/ui/components/devPrompts/EnableOrganizationsPrompt/index.tsx (1)
18-18: Verify dashboard URL with Clerk dashboard or team.The hardcoded URL uses
organizations-settings(plural). While web search indicates Clerk doesn't publish stable patterns for dashboard navigation URLs, the UI terminology uses "Organizations Settings page" (plural), which aligns with the current code. However, the exact path requires manual verification by accessing your Clerk dashboard directly or confirming with the Clerk team, as this pattern is not formally documented as a public stable API.packages/clerk-js/src/core/clerk.ts (1)
22-29: New internal type imports look consistentThe added
__internal_*types are correctly brought in via a type‑only import from@clerk/shared/typesand align with the new internal methods introduced in this file. No changes needed here.
| export type AppearanceCascade = { | ||
| globalAppearance?: Appearance; | ||
| appearance?: Appearance; | ||
| appearanceKey: PublicAppearanceTopLevelKey | 'impersonationFab'; | ||
| appearanceKey: PublicAppearanceTopLevelKey | 'impersonationFab' | 'enableOrganizationsPrompt'; | ||
| }; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🧩 Analysis chain
appearanceKey for enable-organizations prompt does not match Appearance property
AppearanceCascade.appearanceKey now allows 'enableOrganizationsPrompt', but Appearance defines the component-specific theme as enableOrganizations?: T;. In parseAppearance, we index globalAppearance?.[appearanceKey as PublicAppearanceTopLevelKey], so when appearanceKey === 'enableOrganizationsPrompt' we end up looking for a non‑existent property and ignore any appearance.enableOrganizations overrides.
To make theming for the new prompt work as expected, the appearanceKey used by the provider should match the Appearance property (or vice versa). One minimal option in this file is:
-export type AppearanceCascade = {
- globalAppearance?: Appearance;
- appearance?: Appearance;
- appearanceKey: PublicAppearanceTopLevelKey | 'impersonationFab' | 'enableOrganizationsPrompt';
-};
+export type AppearanceCascade = {
+ globalAppearance?: Appearance;
+ appearance?: Appearance;
+ // 'enableOrganizations' is already part of PublicAppearanceTopLevelKey
+ appearanceKey: PublicAppearanceTopLevelKey | 'impersonationFab';
+};and then in LazyEnableOrganizationsPromptProvider pass appearanceKey="enableOrganizations" instead of "enableOrganizationsPrompt" so globalAppearance.enableOrganizations is honored. Alternatively, rename the Appearance property to enableOrganizationsPrompt if that’s the intended public name, but the two must be consistent.
---
🏁 Script executed:
```shell
#!/bin/bash
# Examine parseAppearance.ts file
echo "=== parseAppearance.ts ==="
cat packages/clerk-js/src/ui/customizables/parseAppearance.ts
Length of output: 5585
🏁 Script executed:
#!/bin/bash
# Find Appearance type definition
echo "=== Searching for Appearance type definition ==="
rg -n "type Appearance\s*=" --type ts --type tsx -A 20Length of output: 76
🏁 Script executed:
#!/bin/bash
# Find PublicAppearanceTopLevelKey definition
echo "=== Searching for PublicAppearanceTopLevelKey ==="
rg -n "PublicAppearanceTopLevelKey" --type ts --type tsx -B 2 -A 10Length of output: 77
🏁 Script executed:
#!/bin/bash
# Search for LazyEnableOrganizationsPromptProvider and its usage
echo "=== Searching for LazyEnableOrganizationsPromptProvider ==="
rg -n "LazyEnableOrganizationsPromptProvider\|enableOrganizationsPrompt" --type ts --type tsx -B 3 -A 3Length of output: 87
🏁 Script executed:
#!/bin/bash
# Search for where appearanceKey is set to enableOrganizationsPrompt
echo "=== Searching for appearanceKey assignment ==="
rg -n "appearanceKey\s*=" --type ts --type tsx -B 2 -A 2Length of output: 74
---
🏁 Script executed:
```shell
#!/bin/bash
# Find Appearance type in @clerk/shared
echo "=== Searching for Appearance type definition ==="
rg -n "type Appearance\s*=" -A 20
Length of output: 48
🏁 Script executed:
#!/bin/bash
# Search for LazyEnableOrganizationsPromptProvider
echo "=== Searching for LazyEnableOrganizationsPromptProvider ==="
rg -n "LazyEnableOrganizationsPromptProvider" -B 3 -A 10Length of output: 3850
🏁 Script executed:
#!/bin/bash
# Search for enableOrganizationsPrompt usage
echo "=== Searching for enableOrganizationsPrompt ==="
rg -n "enableOrganizationsPrompt" -B 2 -A 2Length of output: 6305
🏁 Script executed:
#!/bin/bash
# Search for enableOrganizations property in Appearance or related code
echo "=== Searching for enableOrganizations ==="
rg -n "enableOrganizations" -B 2 -A 2Length of output: 7133
🏁 Script executed:
#!/bin/bash
# Check if @clerk/shared is in node_modules or source
fd -t f "appearance" --search-path . | head -20Length of output: 689
---
🏁 Script executed:
```shell
#!/bin/bash
# Check Appearance type definition
echo "=== Appearance type definition ==="
cat packages/shared/src/types/appearance.ts | grep -A 100 "type Appearance = " | head -150
Length of output: 34
🏁 Script executed:
#!/bin/bash
# Verify what PublicAppearanceTopLevelKey would include
echo "=== Check if enableOrganizations is in Appearance ==="
rg -n "enableOrganizations\s*\?" packages/shared/src/types/appearance.ts -B 2 -A 2Length of output: 196
appearanceKey for enable-organizations prompt does not match Appearance property
Verified: Appearance defines enableOrganizations?: T; (in packages/shared/src/types/appearance.ts line 1130), while AppearanceCascade (line 30) allows appearanceKey: 'enableOrganizationsPrompt'. In parseAppearance line 65, when indexing globalAppearance?.[appearanceKey as PublicAppearanceTopLevelKey] with 'enableOrganizationsPrompt', the property lookup returns undefined because Appearance has no such property. This means appearance.enableOrganizations theme overrides are never applied to the prompt.
The fix is to align the key with the actual Appearance property:
- Remove
'enableOrganizationsPrompt'fromAppearanceCascade.appearanceKeyunion (it's redundant since'enableOrganizations'is already part ofPublicAppearanceTopLevelKey) - In
LazyEnableOrganizationsPromptProvider(packages/clerk-js/src/ui/lazyModules/providers.tsx line 220), changeappearanceKey={'enableOrganizationsPrompt'}toappearanceKey={'enableOrganizations'}
🤖 Prompt for AI Agents
In packages/clerk-js/src/ui/customizables/parseAppearance.ts around lines 27-31,
the AppearanceCascade.appearanceKey union incorrectly includes
'enableOrganizationsPrompt' which does not match the actual Appearance property
name; remove 'enableOrganizationsPrompt' from the appearanceKey union so only
the real Appearance keys (including 'enableOrganizations') are allowed. Also
update packages/clerk-js/src/ui/lazyModules/providers.tsx around line 220 to
pass appearanceKey={'enableOrganizations'} instead of
appearanceKey={'enableOrganizationsPrompt'} so parseAppearance indexes the
correct Appearance property and theme overrides are applied.
| export const LazyEnableOrganizationsPromptProvider = ( | ||
| props: React.PropsWithChildren<{ globalAppearance: Appearance | undefined }>, | ||
| ) => { | ||
| return ( | ||
| <Suspense> | ||
| <VirtualRouter startPath=''> | ||
| <AppearanceProvider | ||
| globalAppearance={props.globalAppearance} | ||
| appearanceKey={'enableOrganizationsPrompt'} | ||
| > | ||
| {props.children} | ||
| </AppearanceProvider> | ||
| </VirtualRouter> | ||
| </Suspense> | ||
| ); | ||
| }; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Provider wiring is good; align appearanceKey with Appearance.enableOrganizations
The new LazyEnableOrganizationsPromptProvider mirrors the existing impersonation provider and the VirtualRouter usage looks fine. The only issue is the appearanceKey:
<AppearanceProvider
globalAppearance={props.globalAppearance}
appearanceKey={'enableOrganizationsPrompt'}
>Since the Appearance type exposes enableOrganizations?: T; as the theming slot for this surface, this key should be 'enableOrganizations' so that globalAppearance.enableOrganizations is actually picked up by the cascade:
- <AppearanceProvider
- globalAppearance={props.globalAppearance}
- appearanceKey={'enableOrganizationsPrompt'}
- >
+ <AppearanceProvider
+ globalAppearance={props.globalAppearance}
+ appearanceKey={'enableOrganizations'}
+ >Combined with the adjusted AppearanceCascade.appearanceKey in parseAppearance.ts, this will make theming for the enable-organizations prompt consistent with the other components.
🤖 Prompt for AI Agents
In packages/clerk-js/src/ui/lazyModules/providers.tsx around lines 212 to 227,
the AppearanceProvider is using appearanceKey 'enableOrganizationsPrompt' which
doesn't match the Appearance type's slot name enableOrganizations; change the
appearanceKey to 'enableOrganizations' so that
globalAppearance.enableOrganizations is cascaded correctly (i.e., replace the
current string key with 'enableOrganizations' in the AppearanceProvider props).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
♻️ Duplicate comments (1)
packages/clerk-js/src/core/clerk.ts (1)
787-799: Inconsistency: telemetry event still uses "Mounted" instead of "Opened".Line 793 uses
eventPrebuiltComponentMounted, but a previous review comment (marked "Addressed in commits 5966383 to 8fbc59c") flagged this exact line and recommended switching toeventPrebuiltComponentOpenedfor consistency with other modal methods likeopenSignIn,openCheckout, etc. The code hasn't been updated.Apply this diff to align with other modal telemetry:
- this.telemetry?.record(eventPrebuiltComponentMounted('EnableOrganizationsPrompt', props)); + this.telemetry?.record(eventPrebuiltComponentOpened('EnableOrganizationsPrompt', props));
🧹 Nitpick comments (1)
packages/clerk-js/src/core/clerk.ts (1)
872-885: Verify error-throwing pattern inonClosecallbacks is intentional.All modified organization methods (OrganizationProfile, CreateOrganization, OrganizationSwitcher, OrganizationList, TaskChooseOrganization) follow the same pattern: they call
__internal_attemptToEnableEnvironmentSettingwith anonClosecallback that throws aClerkRuntimeErrorwhen the prompt is dismissed.This means:
- If a developer calls e.g.
clerk.openOrganizationProfile()in development with organizations disabled, a prompt appears.- If the developer closes the prompt without enabling organizations, an error is thrown after the modal closes.
Confirm this is the intended UX. Typically, errors are thrown before opening a modal (to prevent it from opening), not after closing it. If this is intentional, consider adding a code comment explaining why the error is deferred to the
onClosecallback.Based on relevant code snippets and past review context.
Also applies to: 909-922, 1058-1071, 1105-1118, 1143-1156, 1189-1202, 1392-1404
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Disabled knowledge base sources:
- Linear integration is disabled by default for public repositories
You can enable these sources in your CodeRabbit configuration.
📒 Files selected for processing (1)
packages/clerk-js/src/core/clerk.ts(10 hunks)
🧰 Additional context used
📓 Path-based instructions (7)
**/*.{js,jsx,ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
All code must pass ESLint checks with the project's configuration
Files:
packages/clerk-js/src/core/clerk.ts
**/*.{js,jsx,ts,tsx,json,md,yml,yaml}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Use Prettier for consistent code formatting
Files:
packages/clerk-js/src/core/clerk.ts
packages/**/src/**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
TypeScript is required for all packages
Files:
packages/clerk-js/src/core/clerk.ts
**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Follow established naming conventions (PascalCase for components, camelCase for variables)
Prefer importing types from
@clerk/shared/typesinstead of the deprecated@clerk/typesalias
Files:
packages/clerk-js/src/core/clerk.ts
packages/**/src/**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
packages/**/src/**/*.{ts,tsx,js,jsx}: Maintain comprehensive JSDoc comments for public APIs
Use tree-shaking friendly exports
Validate all inputs and sanitize outputs
All public APIs must be documented with JSDoc
Use dynamic imports for optional features
Provide meaningful error messages to developers
Include error recovery suggestions where applicable
Log errors appropriately for debugging
Lazy load components and features when possible
Implement proper caching strategies
Use efficient data structures and algorithms
Implement proper logging with different levels
Files:
packages/clerk-js/src/core/clerk.ts
**/*.ts?(x)
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Use proper TypeScript error types
Files:
packages/clerk-js/src/core/clerk.ts
**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/typescript.mdc)
**/*.{ts,tsx}: Always define explicit return types for functions, especially public APIs
Use proper type annotations for variables and parameters where inference isn't clear
Avoidanytype - preferunknownwhen type is uncertain, then narrow with type guards
Implement type guards forunknowntypes using the patternfunction isType(value: unknown): value is Type
Useinterfacefor object shapes that might be extended
Usetypefor unions, primitives, and computed types
Preferreadonlyproperties for immutable data structures
Useprivatefor internal implementation details in classes
Useprotectedfor inheritance hierarchies
Usepublicexplicitly for clarity in public APIs
Use mixins for shared behavior across unrelated classes in TypeScript
Use generic constraints with bounded type parameters like<T extends { id: string }>
Use utility types likeOmit,Partial, andPickfor data transformation instead of manual type construction
Use discriminated unions instead of boolean flags for state management and API responses
Use mapped types for transforming object types
Use conditional types for type-level logic
Leverage template literal types for string manipulation at the type level
Use ES6 imports/exports consistently
Use default exports sparingly, prefer named exports
Document functions with JSDoc comments including @param, @returns, @throws, and @example tags
Create custom error classes that extend Error for specific error types
Use the Result pattern for error handling instead of throwing exceptions
Use optional chaining (?.) and nullish coalescing (??) operators for safe property access
Let TypeScript infer obvious types to reduce verbosity
Useconst assertionswithas constfor literal types
Usesatisfiesoperator for type checking without widening types
Declare readonly arrays and objects for immutable data structures
Use spread operator and array spread for immutable updates instead of mutations
Use lazy loading for large types...
Files:
packages/clerk-js/src/core/clerk.ts
🧬 Code graph analysis (1)
packages/clerk-js/src/core/clerk.ts (3)
packages/shared/src/types/clerk.ts (2)
__internal_AttemptToEnableEnvironmentSettingParams(1461-1472)__internal_AttemptToEnableEnvironmentSettingResult(1474-1476)packages/clerk-js/src/utils/componentGuards.ts (1)
disabledOrganizationsFeature(21-23)packages/shared/src/telemetry/events/component-mounted.ts (1)
eventPrebuiltComponentMounted(69-75)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
- GitHub Check: Build Packages
- GitHub Check: Formatting | Dedupe | Changeset
- GitHub Check: Analyze (javascript-typescript)
🔇 Additional comments (2)
packages/clerk-js/src/core/clerk.ts (2)
25-28: LGTM on new type imports.The new internal type imports for the environment setting enablement flow are correctly added and follow TypeScript naming conventions.
751-785: Add explicit return type and verify type safety of the cast.Three issues with this method:
Missing explicit return type annotation (Line 751-753): Per coding guidelines, "Always define explicit return types for functions, especially public APIs." Add
: __internal_AttemptToEnableEnvironmentSettingResultto the method signature.Unsafe type assertion (Line 777): The
as __internal_EnableOrganizationsPromptPropscast was flagged in a previous review but remains unaddressed. This cast bypasses TypeScript's type checking whencallerincludes union members like'CreateOrganization'or'TaskChooseOrganization'that may not be present in__internal_EnableOrganizationsPromptProps['caller']. If the types don't align, the prompt component could receive unexpected caller values.Silent failure in non-dev environments (Lines 770-780): When organizations are disabled in production/staging, the method returns
{ isEnabled: false }without any user-facing feedback. Confirm this is intentional—if developers expect production to guard against disabled organizations, document this behavior or consider adding a warning.Apply this fix for the return type:
- public __internal_attemptToEnableEnvironmentSetting = ( - params: __internal_AttemptToEnableEnvironmentSettingParams, - ): __internal_AttemptToEnableEnvironmentSettingResult => { + public __internal_attemptToEnableEnvironmentSetting = ( + params: __internal_AttemptToEnableEnvironmentSettingParams, + ): __internal_AttemptToEnableEnvironmentSettingResult => {For the type cast, verify that
__internal_EnableOrganizationsPromptProps['caller']includes all members from__internal_AttemptToEnableEnvironmentSettingParams['caller'], then remove theasassertion:- this.__internal_openEnableOrganizationsPrompt({ - caller, - // Reload current window to all invalidate all resources - // related to organizations, eg: roles - onSuccess: () => window.location.reload(), - onClose: params.onClose, - } as __internal_EnableOrganizationsPromptProps); + this.__internal_openEnableOrganizationsPrompt({ + caller, + // Reload current window to invalidate all resources + // related to organizations, eg: roles + onSuccess: () => window.location.reload(), + onClose: params.onClose, + });Likely an incorrect or invalid review comment.
a0c0716 to
21d53a9
Compare
|
!snapshot |
There was a problem hiding this 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 (1)
packages/clerk-js/src/core/clerk.ts (1)
773-773: Fix typo in comment.The comment reads "to all invalidate" but should be "to invalidate".
Apply this diff:
- // Reload current window to all invalidate all resources + // Reload current window to invalidate all resources
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Disabled knowledge base sources:
- Linear integration is disabled by default for public repositories
You can enable these sources in your CodeRabbit configuration.
📒 Files selected for processing (1)
packages/clerk-js/src/core/clerk.ts(9 hunks)
🧰 Additional context used
📓 Path-based instructions (7)
**/*.{js,jsx,ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
All code must pass ESLint checks with the project's configuration
Files:
packages/clerk-js/src/core/clerk.ts
**/*.{js,jsx,ts,tsx,json,md,yml,yaml}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Use Prettier for consistent code formatting
Files:
packages/clerk-js/src/core/clerk.ts
packages/**/src/**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
TypeScript is required for all packages
Files:
packages/clerk-js/src/core/clerk.ts
**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Follow established naming conventions (PascalCase for components, camelCase for variables)
Prefer importing types from
@clerk/shared/typesinstead of the deprecated@clerk/typesalias
Files:
packages/clerk-js/src/core/clerk.ts
packages/**/src/**/*.{ts,tsx,js,jsx}
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
packages/**/src/**/*.{ts,tsx,js,jsx}: Maintain comprehensive JSDoc comments for public APIs
Use tree-shaking friendly exports
Validate all inputs and sanitize outputs
All public APIs must be documented with JSDoc
Use dynamic imports for optional features
Provide meaningful error messages to developers
Include error recovery suggestions where applicable
Log errors appropriately for debugging
Lazy load components and features when possible
Implement proper caching strategies
Use efficient data structures and algorithms
Implement proper logging with different levels
Files:
packages/clerk-js/src/core/clerk.ts
**/*.ts?(x)
📄 CodeRabbit inference engine (.cursor/rules/development.mdc)
Use proper TypeScript error types
Files:
packages/clerk-js/src/core/clerk.ts
**/*.{ts,tsx}
📄 CodeRabbit inference engine (.cursor/rules/typescript.mdc)
**/*.{ts,tsx}: Always define explicit return types for functions, especially public APIs
Use proper type annotations for variables and parameters where inference isn't clear
Avoidanytype - preferunknownwhen type is uncertain, then narrow with type guards
Implement type guards forunknowntypes using the patternfunction isType(value: unknown): value is Type
Useinterfacefor object shapes that might be extended
Usetypefor unions, primitives, and computed types
Preferreadonlyproperties for immutable data structures
Useprivatefor internal implementation details in classes
Useprotectedfor inheritance hierarchies
Usepublicexplicitly for clarity in public APIs
Use mixins for shared behavior across unrelated classes in TypeScript
Use generic constraints with bounded type parameters like<T extends { id: string }>
Use utility types likeOmit,Partial, andPickfor data transformation instead of manual type construction
Use discriminated unions instead of boolean flags for state management and API responses
Use mapped types for transforming object types
Use conditional types for type-level logic
Leverage template literal types for string manipulation at the type level
Use ES6 imports/exports consistently
Use default exports sparingly, prefer named exports
Document functions with JSDoc comments including @param, @returns, @throws, and @example tags
Create custom error classes that extend Error for specific error types
Use the Result pattern for error handling instead of throwing exceptions
Use optional chaining (?.) and nullish coalescing (??) operators for safe property access
Let TypeScript infer obvious types to reduce verbosity
Useconst assertionswithas constfor literal types
Usesatisfiesoperator for type checking without widening types
Declare readonly arrays and objects for immutable data structures
Use spread operator and array spread for immutable updates instead of mutations
Use lazy loading for large types...
Files:
packages/clerk-js/src/core/clerk.ts
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (5)
- GitHub Check: Build Packages
- GitHub Check: Formatting | Dedupe | Changeset
- GitHub Check: Analyze (javascript-typescript)
- GitHub Check: semgrep-cloud-platform/scan
- GitHub Check: semgrep-cloud-platform/scan
🔇 Additional comments (2)
packages/clerk-js/src/core/clerk.ts (2)
766-768: Verify intended production behavior when organizations are disabled.When organizations are disabled in non-development environments, the method returns
{ isEnabled: true }and allows components to mount. This means production/staging apps with disabled organizations won't show the prompt and will silently proceed.Confirm this is intentional: does the system rely on backend guards or other component-level error handling in production when organizations are actually disabled?
751-753: Add explicit return type to the method signature.The method lacks an explicit return type in its declaration. Per coding guidelines, all functions (especially public/internal APIs) should have explicit return types.
Apply this diff:
- public __internal_attemptToEnableEnvironmentSetting = ( - params: __internal_AttemptToEnableEnvironmentSettingParams, - ): __internal_AttemptToEnableEnvironmentSettingResult => { + public __internal_attemptToEnableEnvironmentSetting( + params: __internal_AttemptToEnableEnvironmentSettingParams, + ): __internal_AttemptToEnableEnvironmentSettingResult {Likely an incorrect or invalid review comment.
| // related to organizations, eg: roles | ||
| onSuccess: () => window.location.reload(), | ||
| onClose: params.onClose, | ||
| } as __internal_EnableOrganizationsPromptProps); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Remove type assertion to maintain type safety.
The as __internal_EnableOrganizationsPromptProps cast was flagged in past reviews but remains unaddressed. This assertion bypasses TypeScript's type checking and can hide incompatibilities between __internal_AttemptToEnableEnvironmentSettingParams['caller'] and __internal_EnableOrganizationsPromptProps['caller'].
From the past review context: the caller union in the params includes values like 'CreateOrganization' and 'TaskChooseOrganization', which may not be present in the prompt props type. The cast hides this mismatch.
Based on relevant code snippets and past reviews.
Apply this approach:
- Ensure
__internal_EnableOrganizationsPromptProps['caller']accepts all values that__internal_AttemptToEnableEnvironmentSettingParams['caller']can have - Remove the type assertion so the compiler enforces compatibility:
- } as __internal_EnableOrganizationsPromptProps);
+ });Committable suggestion skipped: line range outside the PR's diff.
🤖 Prompt for AI Agents
In packages/clerk-js/src/core/clerk.ts around line 777, remove the unsafe "as
__internal_EnableOrganizationsPromptProps" type assertion and make the compiler
enforce compatibility by ensuring the prompt props' caller type includes every
member of __internal_AttemptToEnableEnvironmentSettingParams['caller']; update
__internal_EnableOrganizationsPromptProps to reference or extend the same union
type (or create a shared alias) so the assignment is directly assignable without
a cast, then delete the assertion on that line.
| .ensureMounted({ preloadHint: 'EnableOrganizationsPrompt' }) | ||
| .then(controls => controls.openModal('enableOrganizationsPrompt', props || {})); | ||
|
|
||
| this.telemetry?.record(eventPrebuiltComponentMounted('EnableOrganizationsPrompt', props)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Telemetry event type is inconsistent despite past review being marked as addressed.
A past review identified that this line should use eventPrebuiltComponentOpened instead of eventPrebuiltComponentMounted for consistency with other modal methods like openSignIn, openCheckout, etc. The review was marked as "Addressed in commits 5966383 to 8fbc59c", but the code still shows eventPrebuiltComponentMounted.
This inconsistency means analytics will report "component mounted" rather than "prompt shown", which doesn't match the semantics of opening a modal.
Apply this diff:
- this.telemetry?.record(eventPrebuiltComponentMounted('EnableOrganizationsPrompt', props));
+ this.telemetry?.record(eventPrebuiltComponentOpened('EnableOrganizationsPrompt', props));📝 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.
| this.telemetry?.record(eventPrebuiltComponentMounted('EnableOrganizationsPrompt', props)); | |
| this.telemetry?.record(eventPrebuiltComponentOpened('EnableOrganizationsPrompt', props)); |
🤖 Prompt for AI Agents
In packages/clerk-js/src/core/clerk.ts around line 793, the telemetry call uses
eventPrebuiltComponentMounted but should use eventPrebuiltComponentOpened to
match semantics of showing/opening prompts; update the call to
this.telemetry?.record(eventPrebuiltComponentOpened('EnableOrganizationsPrompt',
props)) keeping the optional chaining and same props argument so analytics
report "prompt opened" consistently with other modal methods.
|
Hey @LauraBeatris - the snapshot version command generated the following package versions:
Tip: Use the snippet copy button below to quickly install the required packages. npm i @clerk/agent-toolkit@0.2.5-snapshot.v20251124170822 --save-exact
npm i @clerk/astro@2.16.3-snapshot.v20251124170822 --save-exact
npm i @clerk/backend@2.24.0-snapshot.v20251124170822 --save-exact
npm i @clerk/chrome-extension@2.8.5-snapshot.v20251124170822 --save-exact
npm i @clerk/clerk-js@5.110.0-snapshot.v20251124170822 --save-exact
npm i @clerk/elements@0.23.86-snapshot.v20251124170822 --save-exact
npm i @clerk/clerk-expo@2.19.5-snapshot.v20251124170822 --save-exact
npm i @clerk/expo-passkeys@0.4.22-snapshot.v20251124170822 --save-exact
npm i @clerk/express@1.7.53-snapshot.v20251124170822 --save-exact
npm i @clerk/fastify@2.6.5-snapshot.v20251124170822 --save-exact
npm i @clerk/localizations@3.28.4-snapshot.v20251124170822 --save-exact
npm i @clerk/nextjs@6.35.5-snapshot.v20251124170822 --save-exact
npm i @clerk/nuxt@1.13.3-snapshot.v20251124170822 --save-exact
npm i @clerk/clerk-react@5.57.0-snapshot.v20251124170822 --save-exact
npm i @clerk/react-router@2.2.5-snapshot.v20251124170822 --save-exact
npm i @clerk/remix@4.13.20-snapshot.v20251124170822 --save-exact
npm i @clerk/shared@3.36.0-snapshot.v20251124170822 --save-exact
npm i @clerk/tanstack-react-start@0.27.5-snapshot.v20251124170822 --save-exact
npm i @clerk/testing@1.13.19-snapshot.v20251124170822 --save-exact
npm i @clerk/themes@2.4.40-snapshot.v20251124170822 --save-exact
npm i @clerk/types@4.101.3-snapshot.v20251124170822 --save-exact
npm i @clerk/vue@1.17.0-snapshot.v20251124170822 --save-exact |
Description
This PR allows developers to enable the organization's featureset in-app instead of having to go to the Clerk Dashboard, decreasing friction to build B2B apps.
The prompt only appears for development instances only.
Checklist
pnpm testruns as expected.pnpm buildruns as expected.Type of change
Summary by CodeRabbit
New Features
Chores
Accessibility
Tests
✏️ Tip: You can customize this high-level summary in your review settings.