From 053a8739aa6c26685691a4ea5ea4acfe40b784d6 Mon Sep 17 00:00:00 2001 From: Dylan Staley <88163+dstaley@users.noreply.github.com> Date: Mon, 18 Aug 2025 16:06:53 -0500 Subject: [PATCH 1/2] feat(clerk-js,types): Signal SignUp APIs --- .changeset/big-queens-tap.md | 6 +++ .../clerk-js/src/core/resources/SignUp.ts | 48 +++++++++++++++++++ packages/types/src/signUp.ts | 8 ++++ 3 files changed, 62 insertions(+) create mode 100644 .changeset/big-queens-tap.md diff --git a/.changeset/big-queens-tap.md b/.changeset/big-queens-tap.md new file mode 100644 index 00000000000..6f1221845b4 --- /dev/null +++ b/.changeset/big-queens-tap.md @@ -0,0 +1,6 @@ +--- +'@clerk/clerk-js': minor +'@clerk/types': minor +--- + +[Experimental] Signal SignUp APIs diff --git a/packages/clerk-js/src/core/resources/SignUp.ts b/packages/clerk-js/src/core/resources/SignUp.ts index df9a24f8afd..8388348bfc5 100644 --- a/packages/clerk-js/src/core/resources/SignUp.ts +++ b/packages/clerk-js/src/core/resources/SignUp.ts @@ -13,6 +13,7 @@ import type { PreparePhoneNumberVerificationParams, PrepareVerificationParams, PrepareWeb3WalletVerificationParams, + SetActiveNavigate, SignUpAuthenticateWithWeb3Params, SignUpCreateParams, SignUpField, @@ -48,6 +49,7 @@ import { } from '../errors'; import { eventBus } from '../events'; import { BaseResource, ClerkRuntimeError, SignUpVerifications } from './internal'; +import { runAsyncResourceTask } from '../../utils/runAsyncResourceTask'; declare global { interface Window { @@ -470,9 +472,55 @@ export class SignUp extends BaseResource implements SignUpResource { } class SignUpFuture implements SignUpFutureResource { + verifications = { + sendEmailCode: this.sendEmailCode.bind(this), + verifyEmailCode: this.verifyEmailCode.bind(this), + }; + constructor(readonly resource: SignUp) {} get status() { return this.resource.status; } + + get unverifiedFields() { + return this.resource.unverifiedFields; + } + + async password({ emailAddress, password }: { emailAddress: string; password: string }): Promise<{ error: unknown }> { + return runAsyncResourceTask(this.resource, async () => { + await this.resource.__internal_basePost({ + path: this.resource.pathRoot, + body: { emailAddress, password }, + }); + }); + } + + async sendEmailCode(): Promise<{ error: unknown }> { + return runAsyncResourceTask(this.resource, async () => { + await this.resource.__internal_basePost({ + body: { strategy: 'email_code' }, + action: 'prepare_verification', + }); + }); + } + + async verifyEmailCode({ code }: { code: string }): Promise<{ error: unknown }> { + return runAsyncResourceTask(this.resource, async () => { + await this.resource.__internal_basePost({ + body: { strategy: 'email_code', code }, + action: 'attempt_verification', + }); + }); + } + + async finalize({ navigate }: { navigate?: SetActiveNavigate }): Promise<{ error: unknown }> { + return runAsyncResourceTask(this.resource, async () => { + if (!this.resource.createdSessionId) { + throw new Error('Cannot finalize sign-up without a created session.'); + } + + await SignUp.clerk.setActive({ session: this.resource.createdSessionId, navigate }); + }); + } } diff --git a/packages/types/src/signUp.ts b/packages/types/src/signUp.ts index d559c90a041..eded9a32f1d 100644 --- a/packages/types/src/signUp.ts +++ b/packages/types/src/signUp.ts @@ -1,6 +1,7 @@ import type { PhoneCodeChannel } from 'phoneCodeChannel'; import type { FirstNameAttribute, LastNameAttribute, LegalAcceptedAttribute, PasswordAttribute } from './attributes'; +import type { SetActiveNavigate } from './clerk'; import type { AttemptEmailAddressVerificationParams, PrepareEmailAddressVerificationParams } from './emailAddress'; import type { EmailAddressIdentifier, @@ -120,6 +121,13 @@ export interface SignUpResource extends ClerkResource { export interface SignUpFutureResource { status: SignUpStatus | null; + unverifiedFields: SignUpIdentificationField[]; + verifications: { + sendEmailCode: () => Promise<{ error: unknown }>; + verifyEmailCode: (params: { code: string }) => Promise<{ error: unknown }>; + }; + password: (params: { emailAddress: string; password: string }) => Promise<{ error: unknown }>; + finalize: (params: { navigate?: SetActiveNavigate }) => Promise<{ error: unknown }>; } export type SignUpStatus = 'missing_requirements' | 'complete' | 'abandoned'; From 2b25101864c56aae01e7dcbed90c615e539a42ef Mon Sep 17 00:00:00 2001 From: Dylan Staley <88163+dstaley@users.noreply.github.com> Date: Mon, 18 Aug 2025 16:20:48 -0500 Subject: [PATCH 2/2] fix(clerk-js): Lint --- packages/clerk-js/src/core/resources/SignUp.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/clerk-js/src/core/resources/SignUp.ts b/packages/clerk-js/src/core/resources/SignUp.ts index 8388348bfc5..3f1f5626129 100644 --- a/packages/clerk-js/src/core/resources/SignUp.ts +++ b/packages/clerk-js/src/core/resources/SignUp.ts @@ -41,6 +41,7 @@ import { _authenticateWithPopup } from '../../utils/authenticateWithPopup'; import { CaptchaChallenge } from '../../utils/captcha/CaptchaChallenge'; import { createValidatePassword } from '../../utils/passwords/password'; import { normalizeUnsafeMetadata } from '../../utils/resourceParams'; +import { runAsyncResourceTask } from '../../utils/runAsyncResourceTask'; import { clerkInvalidFAPIResponse, clerkMissingOptionError, @@ -49,7 +50,6 @@ import { } from '../errors'; import { eventBus } from '../events'; import { BaseResource, ClerkRuntimeError, SignUpVerifications } from './internal'; -import { runAsyncResourceTask } from '../../utils/runAsyncResourceTask'; declare global { interface Window {