Clerk Changelog

Official SDK for Astro

Category
SDK
Published

Our community SDK is all grown up 🧑‍🚀

Astro is one of the most loved web frameworks for the past couple of years, it's a modern framework for fast content-driven websites, while also making it trivial to create dynamic web applications.

Today, we're proud to announce @clerk/astro, a new official SDK that allows developers to add authentication and authorization into their Astro application in matter of minutes.

The SDK comes fully equiped with Clerk's UI components, middleware, and low level utilities for your custom flows.

Use Clerk UI components

Clerk's pre-built UI components give you a beautiful, fully-functional user and organization management experience in minutes. Here's an example on how to use the <SignIn /> component in Astro.

src/pages/sign-in/[...signIn].astro
---
import { SignIn } from '@clerk/astro/components'
---

<SignIn path="/sign-in" />

Protect routes with Clerk Middleware

Use clerkMiddleware and the auth function to restrict logged out users from accessing the /user routes.

src/middleware.ts
import { clerkMiddleware, createRouteMatcher } from '@clerk/astro/server'

const isProtectedPage = createRouteMatcher(['/user(.*)'])

export const onRequest = clerkMiddleware((auth, context, next) => {
  if (isProtectedPage(context.request) && !auth().userId) {
    return auth().redirectToSignIn()
  }

  return next()
})

Individual page protection

If the /me page is not protected by the middleware, you can still protect the page directly. The code below uses Astro.locals.auth() in order redirect the user the sign-in page or render their userId.

src/pages/me.astro
---
const { userId, redirectToSignIn } = Astro.locals.auth()

if (!userId) {
  return redirectToSignIn()
}
---

<p>My user id is {userId}</p>

Usage with React

Astro offers a way to use React inside your Astro application. @clerk/astro takes advantage of that and exposes components, hooks, and utilities for those cases.

src/components/Header.tsx
import { SignInButton, SignedIn, SignedOut, UserButton } from '@clerk/astro/react'

export default function Header() {
  return (
    <>
      <p>My App</p>
      <SignedOut>
        <SignInButton />
      </SignedOut>
      <SignedIn>
        <UserButton />
      </SignedIn>
    </>
  )
}

This is only a quick preview of all that @clerk/astro offers.

For more information on the available API and how to get started building Astro applications with Clerk, check out our Astro Quickstart guide.

And last but not least, we would like to acknowledge and thank all of the contributors of the previous community SDK for Astro, which was a great source of inspiration for us.

Contributors
Pantelis Eleftheriadis
Robert Soriano

Remix SPA mode

Category
SDK
Published

@clerk/remix now supports Remix SPA Mode

Starting with @clerk/remix@4.2.0 our Remix SDK now supports Remix SPA mode. This means that you can now use Clerk in your Remix app without server-side rendering.

After creating a Remix app with SPA mode enabled, install the latest @clerk/remix package:

terminal
npm install @clerk/remix@latest
terminal
yarn add @clerk/remix@latest
terminal
pnpm add @clerk/remix@latest

You can then use ClerkApp inside your root route and use Clerk's control components to protect your pages. Clerk will automatically detect that your Remix app is running in SPA mode and will take care of the rest.

To read the full guide and learn more about Clerk and Remix SPA Mode, head over to the Remix SPA mode reference guide.

Contributor
Stefanos Anagnostou

Next.js Dynamic Keys

Category
SDK
Published

Keys and options passed to clerkMiddleware() at runtime are available in Clerk’s server-side helpers.

Users building a multi-tenant application might need to provide different Clerk keys depending on the incoming request. Previously, you would need to pass these keys to all of Clerk’s Next.js server-side helpers. With Dynamic Keys support, keys passed to clerkMiddleware() are made available to auth() and other server-side helpers.

middleware.ts
import { clerkMiddleware } from '@clerk/nextjs/server'

export default clerkMiddleware({
  secretKey: '<YOUR_SECRET_KEY>',
  publishableKey: '<YOUR_PUBLISHABLE_KEY>',
  signInUrl: '/my-sign-in',
  signUpUrl: '/my-sign-up',
})

export const config = {
  matcher: ['/((?!.*\\..*|_next).*)', '/', '/(api|trpc)(.*)'],
}

With a centralized place for passing server-side options, implementing a multi-tenant application that requires dynamic Clerk keys should be much more straightforward. This feature is available as of @clerk/nextjs@5.2.x.

Check out the documentation for additional details and happy building!

Contributor
Laura Beatris

Google One Tap

Category
Components
Published

Introducing support for Google One Tap for seamless, one-click user sign-ins and sign-ups!

By leveraging Google One Tap, users can effortlessly access your services without needing to remember passwords or undergo lengthy registration steps. This strategy aims to increase user engagement and conversion rates by simplifying the sign-in process, making it easier for users to get started with your application.

Our new component

To enable this feature, all you have to do is drop the new <GoogleOneTap /> component into your React application. For applications that don't have Google OAuth already set up with custom credentials, please read our guide in order to configure it.

/app/layout.tsx
import React from 'react'
import { ClerkProvider, GoogleOneTap } from '@clerk/nextjs'

export default function RootLayout({ children }: { children: React.ReactNode }) {
  return (
    <html lang="en">
      <head>
        <title>Google One Tap with Clerk and Next.js</title>
      </head>
      <ClerkProvider>
        <GoogleOneTap />
        <body>{children}</body>
      </ClerkProvider>
    </html>
  )
}

For those who are interested in custom flows or would like to use the component but whose application does not run in React, they can visit our documentation page to learn more about Google One Tap and its usage with clerk-js.

Contributors
Pantelis Eleftheriadis
Haris Chaniotakis

Clerk Elements (Beta)

Category
Components
Published

Introducing Clerk Elements, a new set of unstyled UI primitives that make it easy to build completely custom user interfaces on top of Clerk's API.

Our pre-built UI components are a phenomenal way to integrate Clerk's authentication and user management features into your applications, but we know that many of you are looking for even more customization. That has usually meant dropping down to our hooks to create custom flows. Clerk's hooks offer a ton of flexibility and control for creating flows exactly as you want, but we think we can make it easier for you to focus on building your UI while letting us handle the underlying logic.

This is why we're excited to introduce Clerk Elements (Beta). Clerk Elements is a collection of composable components for creating completely custom authentication and user management UIs on top of Clerk's APIs and business logic. We think the component is a great abstraction, and so we're taking it a step further and exposing an unstyled set of components that you can use to build your authentication UIs to completely match your brand and existing design system.

Clerk Elements is launching in beta today, with support for building fully custom sign-up and sign-in flows inside Next.js. Along with the release, we're also sharing documentation and examples to get you started with Clerk Elements.

Build with Clerk Elements

They say a picture is worth a thousand words (and a component is worth 1,000 APIs), so let's dive right in. Below are examples of unstyled sign-up and sign-in flows built with Clerk Elements. These snippets support authenticating with Google auth, or email and email code.

Build your sign-up

/app/sign-up/[[...sign-up]]/page.tsx
'use client'

import * as Clerk from '@clerk/elements/common'
import * as SignUp from '@clerk/elements/sign-up'

export default function SignUpPage() {
  return (
    <SignUp.Root>
      <SignUp.Step name="start">
        <h1>Create your account</h1>
        <p>Welcome! Fill in the fields below to get started.</p>
        <Clerk.GlobalError />

        <Clerk.Connection name="google">
          <Clerk.Icon name="google" /> Sign up with Google
        </Clerk.Connection>

        <div>or</div>

        <Clerk.Field name="identifier">
          <Clerk.Label>Email address</Clerk.Label>
          <Clerk.Input />
          <Clerk.FieldError />
        </Clerk.Field>

        <SignUp.Action submit>Continue</SignUp.Action>
      </SignUp.Step>
      <SignUp.Step name="continue">
        <h1>We need a few more details.</h1>
        <Clerk.GlobalError />

        <Clerk.Field name="firstName">
          <Clerk.Label>First name</Clerk.Label>
          <Clerk.Input />
          <Clerk.FieldError />
        </Clerk.Field>

        <Clerk.Field name="lastName">
          <Clerk.Label>Last name</Clerk.Label>
          <Clerk.Input />
          <Clerk.FieldError />
        </Clerk.Field>

        <SignUp.Action submit>Continue</SignUp.Action>
      </SignUp.Step>
      <SignUp.Step name="verifications">
        <Clerk.GlobalError />

        <SignUp.Strategy name="email_code">
          <h1>Check your email</h1>
          <p>We've sent a code to your email.</p>
          <Clerk.Field name="code">
            <Clerk.Label>Email code</Clerk.Label>
            <Clerk.Input />
            <Clerk.FieldError />
          </Clerk.Field>
          <SignUp.Action submit>Continue</SignUp.Action>
        </SignUp.Strategy>
      </SignUp.Step>
    </SignUp.Root>
  )
}

Build your sign-in

/app/sign-in/[[...sign-in]]/page.tsx
'use client'

import * as Clerk from '@clerk/elements/common'
import * as SignIn from '@clerk/elements/sign-in'

export default function SignInPage() {
  return (
    <SignIn.Root>
      <SignIn.Step name="start">
        <h1>Sign in to Clover</h1>
        <p>Welcome back! Please sign in to continue.</p>

        <Clerk.GlobalError />

        <Clerk.Connection name="google">
          <Clerk.Icon name="google" /> Sign in with Google
        </Clerk.Connection>

        <div>or</div>

        <Clerk.Field name="identifier">
          <Clerk.Label>Email address</Clerk.Label>
          <Clerk.Input />
          <Clerk.FieldError />
        </Clerk.Field>

        <SignIn.Action submit>Continue</SignIn.Action>
      </SignIn.Step>
      <SignIn.Step name="verifications">
        <Clerk.GlobalError />

        <SignIn.Strategy name="email_code">
          <h1>Check your email</h1>
          <p>
            We've sent a code to <SignIn.SafeIdentifier />.
          </p>
          <Clerk.Field name="code">
            <Clerk.Label>Email code</Clerk.Label>
            <Clerk.Input />
            <Clerk.FieldError />
          </Clerk.Field>
          <SignIn.Action submit>Continue</SignIn.Action>
        </SignIn.Strategy>
      </SignIn.Step>
    </SignIn.Root>
  )
}

Customize Elements

As you can see from the above snippets, Clerk Elements gives you complete control over the markup rendered in your authentication flows, and everything is unstyled. We want to make it easy for you to integrate with your existing styling approach. To that end, any markup that is rendered can accept a className prop. Bring on those Tailwind classes!

<SignIn.Action submit className="bg-purple-500 px-4 py-2 text-white shadow-sm">
  Continue
</SignIn.Action>

Clerk Elements also support the asChild prop, popularized by component libraries like Radix. Bring your existing component library and it'll take care of the rest.

<SignUp.Action submit asChild>
  <CloverButton>Continue</CloverButton>
</SignUp.Action>

For more information on the available components and how to get started building fully custom flows with Clerk Elements, check out the Clerk Elements documentation.

Building towards GA

While we're not marking Elements as stable quite yet, we're currently dogfooding it internally by building our existing pre-built components with Elements. As we do this, we expect to continue to make refinements to the component APIs to make sure we support even the most complex use cases.

Once our pre-built components are built on Elements and it supports all major React frameworks (not only Next.js), we'll be ready to mark Elements as stable and fully ready for production.

Your feedback is critical during this beta period to making sure Clerk Elements is the best it can be. If you have questions or want to talk to other users who are testing out the Clerk Elements beta, join the Clerk Community on Discord.

We're already having fun internally dreaming up new authentication UIs made possible with Clerk Elements, and we can't wait to see what you build!

Contributors
Alex Carpenter
Bryce Kalow
Derek Briggs
Lennart Jörgens
Tom Milewski

Testing Tokens

Category
E2E
Published

Unlocking end-to-end testing in Clerk applications

Securing your application is one of our top priorities here at Clerk. To that end, we incorporate several protections against automated bot traffic, implemented in our Web Application Firewall running at edge.

These safeguards, while effective against malicious bots, have historically interfered with end-to-end test suites. If you ever encountered a "Bot traffic detected" error in your tests, it's those protections in action.

Today we are releasing Testing Tokens - a feature that allows testing suites to run uninhibited by such security measures.

For usage instructions and Playwright integration, visit the Testing Tokens docs and the Playwright guide. Additionally, we will be working on an integration for Cypress in the future.

Testing Tokens are currently available in development instances, but may be expanded to production instances in the future.

For further info, feedback or issues, refer to the docs and the @clerk/testing package.

Contributors
Agis Anastasopoulos
Stefanos Anagnostou