关于 clerk-react-patterns
面向 Vite/CRA 单页应用的 Clerk React 认证技能,涵盖钩子、路由保护和自定义登录流程,并说明客户端认证状态与令牌的处理方式。
主要功能
- 01认证钩子用法
- 02React Router 路由保护
- 03自定义登录与注册流程
- 04会话 JWT 获取
- 05加载状态与常见问题说明
适用场景
- 01在 React 页面读取用户与认证状态
- 02限制未登录用户访问路由
- 03构建自定义登录或注册界面
- 04为 API 请求获取会话令牌
安装
复制下面的命令,在终端中运行。
$
npx skills add https:/ / github.com/ clerk/ skills --skill clerk-react-patterns安装后在 Claude Code 中输入/clerk-react-patterns确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
evals/evals.jsonreferences/custom-flows.mdhooks.mdprotected-routes.mdrouter-integration.mdtemplates/react-basic-auth/index.htmlpackage.jsontsconfig.jsonvite.config.tstemplates/react-basic-auth/src/App.tsxmain.tsx详细介绍
React SPA 模式
此技能适用于 Vite/CRA SPA 中的
@clerk/react。Next.js 请使用clerk-nextjs-patterns。TanStack Start 请使用clerk-tanstack-patterns。
你需要什么?
| 任务 | 参考 |
|---|---|
| useAuth / useUser / useClerk 钩子 | references/hooks.md |
| 使用 React Router 的受保护路由 | references/protected-routes.md |
| 自定义登录 / 注册表单 | references/custom-flows.md |
| React Router v6/v7 集成 | references/router-integration.md |
参考
| 参考 | 描述 |
|---|---|
references/hooks.md | useAuth、isLoaded 守卫 |
references/protected-routes.md | ProtectedRoute 模式 |
references/custom-flows.md | useSignIn、useSignUp 流程 |
references/router-integration.md | React Router v6/v7 设置 |
设置
npm install @clerk/react
.env:
VITE_CLERK_PUBLISHABLE_KEY=pk_...
src/main.tsx:
import { StrictMode } from 'react'
import { createRoot } from 'react-dom/client'
import { ClerkProvider } from '@clerk/react'
import App from './App.tsx'
const PUBLISHABLE_KEY = import.meta.env.VITE_CLERK_PUBLISHABLE_KEY
createRoot(document.getElementById('root')!).render(
<StrictMode>
<ClerkProvider publishableKey={PUBLISHABLE_KEY}>
<App />
</ClerkProvider>
</StrictMode>,
)
心智模型
@clerk/react 仅在客户端运行——没有服务端的 auth()。所有身份验证状态都来自钩子。
- 在信任
isSignedIn之前,isLoaded必须为true——始终先检查isLoaded useClerk()可用于访问signOut、openSignIn、openUserProfile等方法useAuth()中的getToken()会获取用于 API 调用的会话 JWT
最简模式
import { useAuth } from '@clerk/react'
export function Dashboard() {
const { isLoaded, isSignedIn, userId } = useAuth()
if (!isLoaded) return <div>Loading...</div>
if (!isSignedIn) return <div>Please sign in</div>
return <div>Hello {userId}</div>
}
受保护路由(React Router v6/v7)
import { Navigate, Outlet } from 'react-router-dom'
import { useAuth } from '@clerk/react'
export function ProtectedRoute() {
const { isLoaded, isSignedIn } = useAuth()
if (!isLoaded) return <div>Loading...</div>
if (!isSignedIn) return <Navigate to="/sign-in" replace />
return <Outlet />
}
<Routes>
<Route element={<ProtectedRoute />}>
<Route path="/dashboard" element={<Dashboard />} />
<Route path="/settings" element={<Settings />} />
</Route>
<Route path="/sign-in" element={<SignIn />} />
</Routes>
用于 API 调用的令牌
import { useAuth } from '@clerk/react'
export function DataFetcher() {
const { getToken } = useAuth()
async function fetchData() {
const token = await getToken()
if (!token) return
const res = await fetch('/api/data', {
headers: { Authorization: `Bearer ${token}` },
})
return res.json()
}
return <button onClick={fetchData}>Load</button>
}
常见问题
| 症状 | 原因 | 解决方法 |
|---|---|---|
isSignedIn 为 undefined | isLoaded 仍为 false | 始终先检查 isLoaded |
缺少 ClerkProvider | Provider 未位于根节点 | 在 main.tsx 中用 <App> 包裹 |
| 环境变量未定义 | Vite 前缀错误 | 使用 VITE_CLERK_PUBLISHABLE_KEY,通过 import.meta.env 访问 |
令牌为 null | 用户未登录 | 对 getToken() 的结果进行空值检查 |
| 登录组件显示空白 | Provider 上没有 publishableKey | 显式传入 publishableKey |
另请参阅
clerk-setup- Clerk 初始安装clerk-custom-ui- 自定义流程和外观clerk-orgs- B2B 组织
文档
评论
支持 Markdown