Skip to content

Commit 2ff841c

Browse files
committed
merge origin/main into jrad/js-prop-bundling
2 parents 14df9f0 + 3983cf8 commit 2ff841c

43 files changed

Lines changed: 315 additions & 306 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.changeset/shiny-owls-dance.md

Lines changed: 2 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,11 @@
11
---
22
'@clerk/ui': minor
33
'@clerk/react': minor
4+
'@clerk/nextjs': minor
45
'@clerk/vue': minor
56
'@clerk/astro': minor
67
'@clerk/chrome-extension': minor
78
'@clerk/shared': minor
89
---
910

10-
Add `ui` prop to ClerkProvider for passing `@clerk/ui`
11-
12-
Usage:
13-
```tsx
14-
import { ui } from '@clerk/ui';
15-
16-
<ClerkProvider ui={ui}>
17-
...
18-
</ClerkProvider>
19-
```
20-
21-
**Migration note**: If you were previously using the internal `clerkUiCtor` prop, migrate to the new `ui` prop by importing `ui` from `@clerk/ui`.
11+
Add `ui` prop to `ClerkProvider` for passing `@clerk/ui`

integration/templates/express-vite/src/client/main.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,13 @@
11
import { Clerk } from '@clerk/clerk-js';
2-
import { ClerkUi } from '@clerk/ui/entry';
2+
import { ClerkUI } from '@clerk/ui/entry';
33

44
const publishableKey = import.meta.env.VITE_CLERK_PUBLISHABLE_KEY;
55

66
document.addEventListener('DOMContentLoaded', async function () {
77
const clerk = new Clerk(publishableKey);
88

99
await clerk.load({
10-
clerkUICtor: ClerkUi,
10+
ui: { ClerkUI },
1111
});
1212

1313
if (clerk.isSignedIn) {

integration/tests/next-build.test.ts

Lines changed: 30 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ import { expect, test } from '@playwright/test';
22

33
import type { Application } from '../models/application';
44
import { appConfigs } from '../presets';
5+
import { linkPackage } from '../presets/utils';
56

67
type RenderingModeTestCase = {
78
name: string;
@@ -29,7 +30,35 @@ test.describe('next build - bundled UI with react-server condition @nextjs', ()
2930

3031
test.beforeAll(async () => {
3132
test.setTimeout(90_000); // Wait for app to be ready
32-
app = await appConfigs.next.appRouter.clone().commit();
33+
app = await appConfigs.next.appRouter
34+
.clone()
35+
.addDependency('@clerk/ui', linkPackage('ui'))
36+
.addFile(
37+
'src/app/layout.tsx',
38+
() => `import './globals.css';
39+
import { Inter } from 'next/font/google';
40+
import { ClerkProvider } from '@clerk/nextjs';
41+
import { ui } from '@clerk/ui';
42+
43+
const inter = Inter({ subsets: ['latin'] });
44+
45+
export const metadata = {
46+
title: 'Create Next App',
47+
description: 'Generated by create next app',
48+
};
49+
50+
export default function RootLayout({ children }: { children: React.ReactNode }) {
51+
return (
52+
<ClerkProvider ui={ui}>
53+
<html lang='en'>
54+
<body className={inter.className}>{children}</body>
55+
</html>
56+
</ClerkProvider>
57+
);
58+
}
59+
`,
60+
)
61+
.commit();
3362
await app.setup();
3463
await app.withEnv(appConfigs.envs.withEmailCodes);
3564
await app.build();

packages/astro/src/env.d.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ interface InternalEnv {
66
readonly PUBLIC_CLERK_JS_URL?: string;
77
readonly PUBLIC_CLERK_JS_VERSION?: string;
88
readonly PUBLIC_CLERK_UI_URL?: string;
9+
readonly PUBLIC_CLERK_UI_VERSION?: string;
910
readonly PUBLIC_CLERK_PREFETCH_UI?: string;
1011
readonly CLERK_API_KEY?: string;
1112
readonly CLERK_API_URL?: string;

packages/astro/src/integration/create-integration.ts

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,9 @@ function createIntegration<Params extends HotloadAstroClerkIntegrationParams>()
2121
// These are not provided when the "bundled" integration is used
2222
const clerkJSUrl = (params as any)?.clerkJSUrl as string | undefined;
2323
const clerkJSVersion = (params as any)?.clerkJSVersion as string | undefined;
24+
const clerkUIVersion = (params as any)?.clerkUIVersion as string | undefined;
2425
const prefetchUI = (params as any)?.prefetchUI as boolean | undefined;
26+
const hasUI = !!(params as any)?.ui;
2527

2628
return {
2729
name: '@clerk/astro/integration',
@@ -57,7 +59,11 @@ function createIntegration<Params extends HotloadAstroClerkIntegrationParams>()
5759
...buildEnvVarFromOption(domain, 'PUBLIC_CLERK_DOMAIN'),
5860
...buildEnvVarFromOption(clerkJSUrl, 'PUBLIC_CLERK_JS_URL'),
5961
...buildEnvVarFromOption(clerkJSVersion, 'PUBLIC_CLERK_JS_VERSION'),
60-
...buildEnvVarFromOption(prefetchUI === false ? 'false' : undefined, 'PUBLIC_CLERK_PREFETCH_UI'),
62+
...buildEnvVarFromOption(clerkUIVersion, 'PUBLIC_CLERK_UI_VERSION'),
63+
...buildEnvVarFromOption(
64+
prefetchUI === false || hasUI ? 'false' : undefined,
65+
'PUBLIC_CLERK_PREFETCH_UI',
66+
),
6167
},
6268

6369
ssr: {
@@ -165,6 +171,7 @@ function createClerkEnvSchema() {
165171
PUBLIC_CLERK_DOMAIN: envField.string({ context: 'client', access: 'public', optional: true, url: true }),
166172
PUBLIC_CLERK_JS_URL: envField.string({ context: 'client', access: 'public', optional: true, url: true }),
167173
PUBLIC_CLERK_JS_VERSION: envField.string({ context: 'client', access: 'public', optional: true }),
174+
PUBLIC_CLERK_UI_VERSION: envField.string({ context: 'client', access: 'public', optional: true }),
168175
PUBLIC_CLERK_PREFETCH_UI: envField.string({ context: 'client', access: 'public', optional: true }),
169176
PUBLIC_CLERK_UI_URL: envField.string({ context: 'client', access: 'public', optional: true, url: true }),
170177
PUBLIC_CLERK_TELEMETRY_DISABLED: envField.boolean({ context: 'client', access: 'public', optional: true }),

packages/astro/src/internal/create-clerk-instance.ts

Lines changed: 9 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ import {
44
setClerkJSLoadingErrorPackageName,
55
} from '@clerk/shared/loadClerkJsScript';
66
import type { ClerkOptions } from '@clerk/shared/types';
7-
import type { ClerkUiConstructor } from '@clerk/shared/ui';
7+
import type { ClerkUIConstructor } from '@clerk/shared/ui';
88
import type { Ui } from '@clerk/ui/internal';
99

1010
import { $clerkStore } from '../stores/external';
@@ -40,7 +40,7 @@ async function createClerkInstanceInternal<TUi extends Ui = Ui>(options?: AstroC
4040
// Both functions return early if the scripts are already loaded
4141
// (e.g., via middleware-injected script tags in the HTML head).
4242
const clerkJsChunk = getClerkJsEntryChunk(options);
43-
const clerkUICtor = getClerkUIEntryChunk(options);
43+
const ClerkUI = getClerkUIEntryChunk(options);
4444

4545
await clerkJsChunk;
4646

@@ -59,7 +59,7 @@ async function createClerkInstanceInternal<TUi extends Ui = Ui>(options?: AstroC
5959
routerReplace: createNavigationHandler(window.history.replaceState.bind(window.history)),
6060
...options,
6161
// Pass the clerk-ui constructor promise to clerk.load()
62-
clerkUICtor,
62+
ui: { ...options?.ui, ClerkUI },
6363
} as unknown as ClerkOptions;
6464

6565
initOptions = clerkOptions;
@@ -115,13 +115,14 @@ async function getClerkJsEntryChunk<TUi extends Ui = Ui>(options?: AstroClerkCre
115115
*/
116116
async function getClerkUIEntryChunk<TUi extends Ui = Ui>(
117117
options?: AstroClerkCreateInstanceParams<TUi>,
118-
): Promise<ClerkUiConstructor | undefined> {
119-
// Honor explicit clerkUICtor even when prefetchUI=false
120-
if (options?.clerkUICtor) {
121-
return options.clerkUICtor;
118+
): Promise<ClerkUIConstructor | undefined> {
119+
// Support bundled UI via ui.ClerkUI prop
120+
if (options?.ui?.ClerkUI) {
121+
return options.ui.ClerkUI;
122122
}
123123

124-
if (options?.prefetchUI === false) {
124+
// Skip CDN prefetch when ui prop is passed (bundled UI) or prefetchUI is false
125+
if (options?.ui || options?.prefetchUI === false) {
125126
return undefined;
126127
}
127128

packages/astro/src/internal/merge-env-vars-with-params.ts

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,8 @@ const mergeEnvVarsWithParams = (params?: AstroClerkIntegrationParams & { publish
3636
telemetry: paramTelemetry,
3737
clerkJSUrl: paramClerkJSUrl,
3838
clerkJSVersion: paramClerkJSVersion,
39-
clerkUIUrl: paramClerkUiUrl,
39+
clerkUIUrl: paramClerkUIUrl,
40+
clerkUIVersion: paramClerkUIVersion,
4041
prefetchUI: paramPrefetchUI,
4142
...rest
4243
} = params || {};
@@ -50,7 +51,8 @@ const mergeEnvVarsWithParams = (params?: AstroClerkIntegrationParams & { publish
5051
publishableKey: paramPublishableKey || import.meta.env.PUBLIC_CLERK_PUBLISHABLE_KEY || '',
5152
clerkJSUrl: paramClerkJSUrl || import.meta.env.PUBLIC_CLERK_JS_URL,
5253
clerkJSVersion: paramClerkJSVersion || import.meta.env.PUBLIC_CLERK_JS_VERSION,
53-
clerkUIUrl: paramClerkUiUrl || import.meta.env.PUBLIC_CLERK_UI_URL,
54+
clerkUIUrl: paramClerkUIUrl || import.meta.env.PUBLIC_CLERK_UI_URL,
55+
clerkUIVersion: paramClerkUIVersion || import.meta.env.PUBLIC_CLERK_UI_VERSION,
5456
prefetchUI: mergePrefetchUIConfig(paramPrefetchUI),
5557
telemetry: paramTelemetry || {
5658
disabled: isTruthy(import.meta.env.PUBLIC_CLERK_TELEMETRY_DISABLED),

packages/astro/src/server/build-clerk-hotload-script.ts

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -34,8 +34,9 @@ function buildClerkHotloadScript(locals: APIContext['locals']) {
3434
return clerkJsScript + '\n';
3535
}
3636

37-
const clerkUiScriptSrc = clerkUIScriptUrl({
37+
const clerkUIScriptSrc = clerkUIScriptUrl({
3838
clerkUIUrl: env.clerkUIUrl,
39+
clerkUIVersion: env.clerkUIVersion,
3940
domain,
4041
proxyUrl,
4142
publishableKey,
@@ -47,14 +48,14 @@ function buildClerkHotloadScript(locals: APIContext['locals']) {
4748
// registration (which happens when React code runs @clerk/ui/register).
4849
// When loadClerkUIScript() later adds a <script> tag, the browser uses the
4950
// cached resource and executes it without re-downloading.
50-
const clerkUiPreload = `
51+
const clerkUIPreload = `
5152
<link rel="preload"
52-
href="${clerkUiScriptSrc}"
53+
href="${clerkUIScriptSrc}"
5354
as="script"
5455
crossOrigin="anonymous"
5556
/>`;
5657

57-
return clerkJsScript + clerkUiPreload + '\n';
58+
return clerkJsScript + clerkUIPreload + '\n';
5859
}
5960

6061
export { buildClerkHotloadScript };

packages/astro/src/server/get-safe-env.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@ function getSafeEnv(context: ContextOrLocals) {
3333
clerkJsUrl: getContextEnvVar('PUBLIC_CLERK_JS_URL', context),
3434
clerkJsVersion: getContextEnvVar('PUBLIC_CLERK_JS_VERSION', context),
3535
clerkUIUrl: getContextEnvVar('PUBLIC_CLERK_UI_URL', context),
36+
clerkUIVersion: getContextEnvVar('PUBLIC_CLERK_UI_VERSION', context),
3637
prefetchUI: getContextEnvVar('PUBLIC_CLERK_PREFETCH_UI', context) === 'false' ? false : undefined,
3738
apiVersion: getContextEnvVar('CLERK_API_VERSION', context),
3839
apiUrl: getContextEnvVar('CLERK_API_URL', context),

packages/astro/src/types.ts

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ import type {
77
ShowProps,
88
Without,
99
} from '@clerk/shared/types';
10-
import type { ClerkUiConstructor } from '@clerk/shared/ui';
10+
import type { ClerkUIConstructor } from '@clerk/shared/ui';
1111
import type { Appearance, Ui } from '@clerk/ui/internal';
1212

1313
type AstroClerkUpdateOptions<TUi extends Ui = Ui> = Pick<ClerkOptions, 'localization'> & {
@@ -35,6 +35,10 @@ type AstroClerkIntegrationParams<TUi extends Ui = Ui> = Without<
3535
* The URL that `@clerk/ui` should be hot-loaded from.
3636
*/
3737
clerkUIUrl?: string;
38+
/**
39+
* The npm version for `@clerk/ui`.
40+
*/
41+
clerkUIVersion?: string;
3842
/**
3943
* Controls prefetching of the `@clerk/ui` script.
4044
* - `false` - Skip prefetching the UI (for custom UIs using Control Components)
@@ -64,7 +68,7 @@ declare global {
6468
__astro_clerk_component_props: Map<string, Map<string, Record<string, unknown>>>;
6569
__astro_clerk_function_props: Map<string, Map<string, Record<string, unknown>>>;
6670
Clerk: BrowserClerk;
67-
__internal_ClerkUICtor?: ClerkUiConstructor;
71+
__internal_ClerkUICtor?: ClerkUIConstructor;
6872
}
6973
}
7074

0 commit comments

Comments
 (0)