Skip to content

Commit 600c648

Browse files
authored
feat(clerk-js,clerk-react): Support Base authentication (#6556)
1 parent 87b1b44 commit 600c648

19 files changed

Lines changed: 393 additions & 31 deletions

File tree

.changeset/silent-insects-cheat.md

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
---
2+
'@clerk/clerk-js': minor
3+
'@clerk/shared': minor
4+
'@clerk/clerk-react': minor
5+
'@clerk/types': minor
6+
---
7+
8+
Added support for authentication with Base

packages/clerk-js/bundlewatch.config.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,12 @@
11
{
22
"files": [
3-
{ "path": "./dist/clerk.js", "maxSize": "631KB" },
3+
{ "path": "./dist/clerk.js", "maxSize": "818KB" },
44
{ "path": "./dist/clerk.browser.js", "maxSize": "78KB" },
55
{ "path": "./dist/clerk.legacy.browser.js", "maxSize": "120KB" },
66
{ "path": "./dist/clerk.headless*.js", "maxSize": "61KB" },
77
{ "path": "./dist/ui-common*.js", "maxSize": "117.1KB" },
88
{ "path": "./dist/ui-common*.legacy.*.js", "maxSize": "118KB" },
9-
{ "path": "./dist/vendors*.js", "maxSize": "43.78KB" },
9+
{ "path": "./dist/vendors*.js", "maxSize": "45KB" },
1010
{ "path": "./dist/coinbase*.js", "maxSize": "38KB" },
1111
{ "path": "./dist/stripe-vendors*.js", "maxSize": "1KB" },
1212
{ "path": "./dist/createorganization*.js", "maxSize": "5KB" },

packages/clerk-js/package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -63,6 +63,7 @@
6363
},
6464
"browserslist": "last 2 years",
6565
"dependencies": {
66+
"@base-org/account": "2.0.1",
6667
"@clerk/localizations": "workspace:^",
6768
"@clerk/shared": "workspace:^",
6869
"@clerk/types": "workspace:^",

packages/clerk-js/rspack.config.js

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -96,6 +96,11 @@ const common = ({ mode, variant, disableRHC = false }) => {
9696
name: 'zxcvbn-common',
9797
chunks: 'all',
9898
},
99+
baseAccountSDKVendor: {
100+
test: /[\\/]node_modules[\\/](@base-org\/account|@noble\/curves|abitype|ox|preact|eventemitter3|viem|zustand)[\\/]/,
101+
name: 'base-account-sdk',
102+
chunks: 'all',
103+
},
99104
coinbaseWalletSDKVendor: {
100105
test: /[\\/]node_modules[\\/](@coinbase\/wallet-sdk|preact|eventemitter3|@noble\/hashes)[\\/]/,
101106
name: 'coinbase-wallet-sdk',

packages/clerk-js/src/core/clerk.ts

Lines changed: 25 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ import type {
2424
__internal_UserVerificationModalProps,
2525
APIKeysNamespace,
2626
APIKeysProps,
27+
AuthenticateWithBaseParams,
2728
AuthenticateWithCoinbaseWalletParams,
2829
AuthenticateWithGoogleOneTapParams,
2930
AuthenticateWithMetamaskParams,
@@ -42,6 +43,7 @@ import type {
4243
EnvironmentJSON,
4344
EnvironmentJSONSnapshot,
4445
EnvironmentResource,
46+
GenerateSignatureParams,
4547
GoogleOneTapProps,
4648
HandleEmailLinkVerificationParams,
4749
HandleOAuthCallbackParams,
@@ -100,6 +102,7 @@ import {
100102
disabledAPIKeysFeature,
101103
disabledOrganizationsFeature,
102104
errorThrower,
105+
generateSignatureWithBase,
103106
generateSignatureWithCoinbaseWallet,
104107
generateSignatureWithMetamask,
105108
generateSignatureWithOKXWallet,
@@ -2148,6 +2151,13 @@ export class Clerk implements ClerkInterface {
21482151
});
21492152
};
21502153

2154+
public authenticateWithBase = async (props: AuthenticateWithBaseParams = {}): Promise<void> => {
2155+
await this.authenticateWithWeb3({
2156+
...props,
2157+
strategy: 'web3_base_signature',
2158+
});
2159+
};
2160+
21512161
public authenticateWithOKXWallet = async (props: AuthenticateWithOKXWalletParams = {}): Promise<void> => {
21522162
await this.authenticateWithWeb3({
21532163
...props,
@@ -2172,12 +2182,21 @@ export class Clerk implements ClerkInterface {
21722182

21732183
const provider = strategy.replace('web3_', '').replace('_signature', '') as Web3Provider;
21742184
const identifier = await getWeb3Identifier({ provider });
2175-
const generateSignature =
2176-
provider === 'metamask'
2177-
? generateSignatureWithMetamask
2178-
: provider === 'coinbase_wallet'
2179-
? generateSignatureWithCoinbaseWallet
2180-
: generateSignatureWithOKXWallet;
2185+
let generateSignature: (params: GenerateSignatureParams) => Promise<string>;
2186+
switch (provider) {
2187+
case 'metamask':
2188+
generateSignature = generateSignatureWithMetamask;
2189+
break;
2190+
case 'base':
2191+
generateSignature = generateSignatureWithBase;
2192+
break;
2193+
case 'coinbase_wallet':
2194+
generateSignature = generateSignatureWithCoinbaseWallet;
2195+
break;
2196+
default:
2197+
generateSignature = generateSignatureWithOKXWallet;
2198+
break;
2199+
}
21812200

21822201
const makeNavigate = (to: string) => () =>
21832202
customNavigate && typeof customNavigate === 'function' ? customNavigate(to) : this.navigate(to);

packages/clerk-js/src/core/resources/SignIn.ts

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -44,9 +44,11 @@ import type {
4444
} from '@clerk/types';
4545

4646
import {
47+
generateSignatureWithBase,
4748
generateSignatureWithCoinbaseWallet,
4849
generateSignatureWithMetamask,
4950
generateSignatureWithOKXWallet,
51+
getBaseIdentifier,
5052
getCoinbaseWalletIdentifier,
5153
getMetamaskIdentifier,
5254
getOKXWalletIdentifier,
@@ -143,11 +145,8 @@ export class SignIn extends BaseResource implements SignInResource {
143145
} as PhoneCodeConfig;
144146
break;
145147
case 'web3_metamask_signature':
146-
config = { web3WalletId: factor.web3WalletId } as Web3SignatureConfig;
147-
break;
148+
case 'web3_base_signature':
148149
case 'web3_coinbase_wallet_signature':
149-
config = { web3WalletId: factor.web3WalletId } as Web3SignatureConfig;
150-
break;
151150
case 'web3_okx_wallet_signature':
152151
config = { web3WalletId: factor.web3WalletId } as Web3SignatureConfig;
153152
break;
@@ -361,6 +360,15 @@ export class SignIn extends BaseResource implements SignInResource {
361360
});
362361
};
363362

363+
public authenticateWithBase = async (): Promise<SignInResource> => {
364+
const identifier = await getBaseIdentifier();
365+
return this.authenticateWithWeb3({
366+
identifier,
367+
generateSignature: generateSignatureWithBase,
368+
strategy: 'web3_base_signature',
369+
});
370+
};
371+
364372
public authenticateWithOKXWallet = async (): Promise<SignInResource> => {
365373
const identifier = await getOKXWalletIdentifier();
366374
return this.authenticateWithWeb3({

packages/clerk-js/src/core/resources/SignUp.ts

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,9 +30,11 @@ import type {
3030
} from '@clerk/types';
3131

3232
import {
33+
generateSignatureWithBase,
3334
generateSignatureWithCoinbaseWallet,
3435
generateSignatureWithMetamask,
3536
generateSignatureWithOKXWallet,
37+
getBaseIdentifier,
3638
getCoinbaseWalletIdentifier,
3739
getMetamaskIdentifier,
3840
getOKXWalletIdentifier,
@@ -276,6 +278,21 @@ export class SignUp extends BaseResource implements SignUpResource {
276278
});
277279
};
278280

281+
public authenticateWithBase = async (
282+
params?: SignUpAuthenticateWithWeb3Params & {
283+
legalAccepted?: boolean;
284+
},
285+
): Promise<SignUpResource> => {
286+
const identifier = await getBaseIdentifier();
287+
return this.authenticateWithWeb3({
288+
identifier,
289+
generateSignature: generateSignatureWithBase,
290+
unsafeMetadata: params?.unsafeMetadata,
291+
strategy: 'web3_base_signature',
292+
legalAccepted: params?.legalAccepted,
293+
});
294+
};
295+
279296
public authenticateWithOKXWallet = async (
280297
params?: SignUpAuthenticateWithWeb3Params & {
281298
legalAccepted?: boolean;

packages/clerk-js/src/utils/web3.ts

Lines changed: 31 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ export async function getWeb3Identifier(params: GetWeb3IdentifierParams): Promis
2121
}
2222

2323
const identifiers = await ethereum.request({ method: 'eth_requestAccounts' });
24-
// @ts-ignore
24+
// @ts-ignore -- Provider SDKs may return unknown shape; use first address if present
2525
return (identifiers && identifiers[0]) || '';
2626
}
2727

@@ -58,6 +58,10 @@ export async function getOKXWalletIdentifier(): Promise<string> {
5858
return await getWeb3Identifier({ provider: 'okx_wallet' });
5959
}
6060

61+
export async function getBaseIdentifier(): Promise<string> {
62+
return await getWeb3Identifier({ provider: 'base' });
63+
}
64+
6165
type GenerateSignatureParams = {
6266
identifier: string;
6367
nonce: string;
@@ -75,6 +79,10 @@ export async function generateSignatureWithOKXWallet(params: GenerateSignaturePa
7579
return await generateWeb3Signature({ ...params, provider: 'okx_wallet' });
7680
}
7781

82+
export async function generateSignatureWithBase(params: GenerateSignatureParams): Promise<string> {
83+
return await generateWeb3Signature({ ...params, provider: 'base' });
84+
}
85+
7886
async function getEthereumProvider(provider: Web3Provider) {
7987
if (provider === 'coinbase_wallet') {
8088
if (__BUILD_DISABLE_RHC__) {
@@ -90,7 +98,27 @@ async function getEthereumProvider(provider: Web3Provider) {
9098
});
9199
return sdk.getProvider();
92100
}
101+
if (provider === 'base') {
102+
if (__BUILD_DISABLE_RHC__) {
103+
clerkUnsupportedEnvironmentWarning('Base');
104+
return null;
105+
}
106+
107+
try {
108+
const createBaseAccountSDK = await import('@base-org/account').then(mod => mod.createBaseAccountSDK);
109+
110+
const sdk = createBaseAccountSDK({
111+
appName:
112+
(typeof window !== 'undefined' &&
113+
(window.Clerk as any)?.__unstable__environment?.displayConfig?.applicationName) ||
114+
(typeof document !== 'undefined' && document.title) ||
115+
'Web3 Application',
116+
});
117+
return sdk.getProvider();
118+
} catch {
119+
return null;
120+
}
121+
}
93122

94-
const injectedWeb3Providers = getInjectedWeb3Providers();
95-
return injectedWeb3Providers.get(provider);
123+
return getInjectedWeb3Providers().get(provider);
96124
}

packages/clerk-js/vitest.config.mts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ function viteSvgMockPlugin() {
2424
export default defineConfig({
2525
plugins: [react({ jsxRuntime: 'automatic', jsxImportSource: '@emotion/react' }), viteSvgMockPlugin()],
2626
define: {
27+
__BUILD_DISABLE_RHC__: JSON.stringify(false),
2728
__BUILD_VARIANT_CHIPS__: JSON.stringify(false),
2829
__PKG_NAME__: JSON.stringify('@clerk/clerk-js'),
2930
__PKG_VERSION__: JSON.stringify('test'),

packages/elements/src/internals/machines/sign-in/start.machine.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,9 @@ export const SignInStartMachine = setup({
3636
if (strategy === 'web3_coinbase_wallet_signature') {
3737
return parent.getSnapshot().context.clerk.client.signIn.authenticateWithCoinbaseWallet();
3838
}
39+
if (strategy === 'web3_base_signature') {
40+
return parent.getSnapshot().context.clerk.client.signIn.authenticateWithBase();
41+
}
3942
if (strategy === 'web3_okx_wallet_signature') {
4043
return parent.getSnapshot().context.clerk.client.signIn.authenticateWithOKXWallet();
4144
}

0 commit comments

Comments
 (0)