@agentuity/auth 0.0.96
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AGENTS.md +594 -0
- package/README.md +360 -0
- package/dist/clerk/client.d.ts +42 -0
- package/dist/clerk/client.d.ts.map +1 -0
- package/dist/clerk/client.js +65 -0
- package/dist/clerk/client.js.map +1 -0
- package/dist/clerk/index.d.ts +37 -0
- package/dist/clerk/index.d.ts.map +1 -0
- package/dist/clerk/index.js +35 -0
- package/dist/clerk/index.js.map +1 -0
- package/dist/clerk/server.d.ts +56 -0
- package/dist/clerk/server.d.ts.map +1 -0
- package/dist/clerk/server.js +110 -0
- package/dist/clerk/server.js.map +1 -0
- package/dist/index.d.ts +18 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +18 -0
- package/dist/index.js.map +1 -0
- package/dist/types.d.ts +32 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +7 -0
- package/dist/types.js.map +1 -0
- package/package.json +48 -0
- package/src/clerk/client.tsx +86 -0
- package/src/clerk/index.ts +37 -0
- package/src/clerk/server.ts +168 -0
- package/src/index.ts +18 -0
- package/src/types.ts +38 -0
- package/test/clerk-client.test.tsx +21 -0
- package/test/clerk-server.test.ts +34 -0
- package/tsconfig.json +12 -0
- package/tsconfig.test.json +11 -0
- package/tsconfig.tsbuildinfo +1 -0
package/README.md
ADDED
|
@@ -0,0 +1,360 @@
|
|
|
1
|
+
# @agentuity/auth
|
|
2
|
+
|
|
3
|
+
Drop-in authentication helpers for popular identity providers (Clerk, WorkOS, Auth0, Better Auth, etc.).
|
|
4
|
+
|
|
5
|
+
## Features
|
|
6
|
+
|
|
7
|
+
- ✅ **Zero Configuration**: Drop-in components that work out of the box
|
|
8
|
+
- ✅ **Provider Agnostic**: Generic interfaces allow routes to be provider-independent
|
|
9
|
+
- ✅ **Tree Shakeable**: Import only the providers you use (`@agentuity/auth/clerk`)
|
|
10
|
+
- ✅ **Type Safe**: Full TypeScript support with proper type inference
|
|
11
|
+
- ✅ **Automatic Token Injection**: Seamless integration with `useAPI` and `useWebsocket`
|
|
12
|
+
- ✅ **Server Validation**: Easy middleware for token validation and user context
|
|
13
|
+
|
|
14
|
+
## Installation
|
|
15
|
+
|
|
16
|
+
```bash
|
|
17
|
+
bun add @agentuity/auth
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
## Supported Providers
|
|
21
|
+
|
|
22
|
+
- **Clerk** - `@agentuity/auth/clerk`
|
|
23
|
+
- WorkOS - Coming soon
|
|
24
|
+
- Auth0 - Coming soon
|
|
25
|
+
- Better Auth - Coming soon
|
|
26
|
+
|
|
27
|
+
## Quick Start
|
|
28
|
+
|
|
29
|
+
### Clerk Integration
|
|
30
|
+
|
|
31
|
+
#### 1. Install Clerk
|
|
32
|
+
|
|
33
|
+
```bash
|
|
34
|
+
bun add @clerk/clerk-react @clerk/backend
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
#### 2. Client Setup (React)
|
|
38
|
+
|
|
39
|
+
```tsx
|
|
40
|
+
import React from 'react';
|
|
41
|
+
import ReactDOM from 'react-dom/client';
|
|
42
|
+
import { ClerkProvider, useAuth } from '@clerk/clerk-react';
|
|
43
|
+
import { AgentuityProvider } from '@agentuity/react';
|
|
44
|
+
import { AgentuityClerk } from '@agentuity/auth/clerk';
|
|
45
|
+
import { App } from './App';
|
|
46
|
+
|
|
47
|
+
ReactDOM.createRoot(document.getElementById('root')!).render(
|
|
48
|
+
<React.StrictMode>
|
|
49
|
+
<ClerkProvider publishableKey={process.env.AGENTUITY_PUBLIC_CLERK_PUBLISHABLE_KEY!}>
|
|
50
|
+
<AgentuityProvider>
|
|
51
|
+
<AgentuityClerk useAuth={useAuth}>
|
|
52
|
+
<App />
|
|
53
|
+
</AgentuityClerk>
|
|
54
|
+
</AgentuityProvider>
|
|
55
|
+
</ClerkProvider>
|
|
56
|
+
</React.StrictMode>
|
|
57
|
+
);
|
|
58
|
+
```
|
|
59
|
+
|
|
60
|
+
#### 3. Server Setup (Hono)
|
|
61
|
+
|
|
62
|
+
```typescript
|
|
63
|
+
import { createRouter } from '@agentuity/runtime';
|
|
64
|
+
import { createMiddleware } from '@agentuity/auth/clerk';
|
|
65
|
+
|
|
66
|
+
const router = createRouter();
|
|
67
|
+
|
|
68
|
+
// Protected route
|
|
69
|
+
router.get('/profile', createMiddleware(), async (c) => {
|
|
70
|
+
const user = await c.var.auth.requireUser();
|
|
71
|
+
return c.json({
|
|
72
|
+
id: user.id,
|
|
73
|
+
name: user.name,
|
|
74
|
+
email: user.email,
|
|
75
|
+
});
|
|
76
|
+
});
|
|
77
|
+
|
|
78
|
+
export default router;
|
|
79
|
+
```
|
|
80
|
+
|
|
81
|
+
#### 4. Environment Variables
|
|
82
|
+
|
|
83
|
+
Create a `.env` file:
|
|
84
|
+
|
|
85
|
+
```env
|
|
86
|
+
# Client-side (bundled into frontend)
|
|
87
|
+
AGENTUITY_PUBLIC_CLERK_PUBLISHABLE_KEY=pk_test_...
|
|
88
|
+
|
|
89
|
+
# Server-side (kept secret)
|
|
90
|
+
CLERK_SECRET_KEY=sk_test_...
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
Get your keys from [Clerk Dashboard](https://dashboard.clerk.com).
|
|
94
|
+
|
|
95
|
+
## Usage
|
|
96
|
+
|
|
97
|
+
### Client Side
|
|
98
|
+
|
|
99
|
+
Once you wrap your app with `AgentuityClerk`, all `useAPI` and `useWebsocket` calls automatically include the auth token:
|
|
100
|
+
|
|
101
|
+
```tsx
|
|
102
|
+
import { useAPI, useAgentuity } from '@agentuity/react';
|
|
103
|
+
|
|
104
|
+
function MyComponent() {
|
|
105
|
+
const { isAuthenticated, authLoading } = useAgentuity();
|
|
106
|
+
const { data, invoke } = useAPI('POST /api/users');
|
|
107
|
+
|
|
108
|
+
if (authLoading) {
|
|
109
|
+
return <div>Loading...</div>;
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
if (!isAuthenticated) {
|
|
113
|
+
return <div>Please sign in</div>;
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
return <button onClick={() => invoke({ name: 'Alice' })}>Create User</button>;
|
|
117
|
+
}
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
### Server Side
|
|
121
|
+
|
|
122
|
+
#### Basic Protection
|
|
123
|
+
|
|
124
|
+
```typescript
|
|
125
|
+
import { createMiddleware } from '@agentuity/auth/clerk';
|
|
126
|
+
|
|
127
|
+
// Protect a single route
|
|
128
|
+
router.post('/admin', createMiddleware(), async (c) => {
|
|
129
|
+
const user = await c.var.auth.requireUser();
|
|
130
|
+
return c.json({ admin: true, userId: user.id });
|
|
131
|
+
});
|
|
132
|
+
```
|
|
133
|
+
|
|
134
|
+
#### Global Middleware
|
|
135
|
+
|
|
136
|
+
```typescript
|
|
137
|
+
// Protect all routes under /api
|
|
138
|
+
router.use('/api/*', createMiddleware());
|
|
139
|
+
|
|
140
|
+
router.get('/api/profile', async (c) => {
|
|
141
|
+
const user = await c.var.auth.requireUser();
|
|
142
|
+
return c.json({ email: user.email });
|
|
143
|
+
});
|
|
144
|
+
```
|
|
145
|
+
|
|
146
|
+
#### Access Provider-Specific Data
|
|
147
|
+
|
|
148
|
+
```typescript
|
|
149
|
+
router.get('/profile', createMiddleware(), async (c) => {
|
|
150
|
+
const user = await c.var.auth.requireUser();
|
|
151
|
+
|
|
152
|
+
// Access generic fields
|
|
153
|
+
console.log(user.id, user.email, user.name);
|
|
154
|
+
|
|
155
|
+
// Access Clerk-specific fields (fully typed)
|
|
156
|
+
const clerkUser = user.raw; // Type: User from @clerk/backend
|
|
157
|
+
console.log(clerkUser.imageUrl);
|
|
158
|
+
console.log(clerkUser.publicMetadata);
|
|
159
|
+
|
|
160
|
+
// Access JWT payload
|
|
161
|
+
const payload = c.var.auth.raw; // Type: ClerkJWTPayload
|
|
162
|
+
console.log(payload.sub);
|
|
163
|
+
|
|
164
|
+
return c.json({ user });
|
|
165
|
+
});
|
|
166
|
+
```
|
|
167
|
+
|
|
168
|
+
#### Custom Middleware Options
|
|
169
|
+
|
|
170
|
+
```typescript
|
|
171
|
+
import { createMiddleware } from '@agentuity/auth/clerk';
|
|
172
|
+
|
|
173
|
+
router.use(
|
|
174
|
+
'/api/*',
|
|
175
|
+
createMiddleware({
|
|
176
|
+
secretKey: 'custom-secret',
|
|
177
|
+
publishableKey: 'custom-publishable',
|
|
178
|
+
getToken: (authHeader) => authHeader.replace('Custom ', ''),
|
|
179
|
+
})
|
|
180
|
+
);
|
|
181
|
+
```
|
|
182
|
+
|
|
183
|
+
## API Reference
|
|
184
|
+
|
|
185
|
+
### Client Components
|
|
186
|
+
|
|
187
|
+
#### `AgentuityClerk`
|
|
188
|
+
|
|
189
|
+
React component that integrates Clerk with Agentuity context.
|
|
190
|
+
|
|
191
|
+
**Props:**
|
|
192
|
+
|
|
193
|
+
- `useAuth: UseAuth` - Clerk's `useAuth` hook from `@clerk/clerk-react`
|
|
194
|
+
- `children: React.ReactNode` - Your app components
|
|
195
|
+
- `refreshInterval?: number` - Token refresh interval in ms (default: 60000)
|
|
196
|
+
|
|
197
|
+
**Example:**
|
|
198
|
+
|
|
199
|
+
```tsx
|
|
200
|
+
<AgentuityClerk useAuth={useAuth} refreshInterval={30000}>
|
|
201
|
+
<App />
|
|
202
|
+
</AgentuityClerk>
|
|
203
|
+
```
|
|
204
|
+
|
|
205
|
+
### Server Middleware
|
|
206
|
+
|
|
207
|
+
#### `createMiddleware(options?)`
|
|
208
|
+
|
|
209
|
+
Creates Hono middleware for Clerk authentication.
|
|
210
|
+
|
|
211
|
+
**Options:**
|
|
212
|
+
|
|
213
|
+
- `secretKey?: string` - Clerk secret key (defaults to `process.env.CLERK_SECRET_KEY`)
|
|
214
|
+
- `publishableKey?: string` - Clerk publishable key (defaults to `process.env.AGENTUITY_PUBLIC_CLERK_PUBLISHABLE_KEY` or `process.env.CLERK_PUBLISHABLE_KEY`)
|
|
215
|
+
- `getToken?: (authHeader: string) => string` - Custom token extractor
|
|
216
|
+
|
|
217
|
+
**Returns:** Hono `MiddlewareHandler`
|
|
218
|
+
|
|
219
|
+
**Behavior:**
|
|
220
|
+
|
|
221
|
+
- Returns 401 if Authorization header is missing
|
|
222
|
+
- Returns 401 if token is invalid
|
|
223
|
+
- Sets `c.var.auth` with authenticated user context
|
|
224
|
+
|
|
225
|
+
### Context Hook
|
|
226
|
+
|
|
227
|
+
#### `useAgentuity()`
|
|
228
|
+
|
|
229
|
+
Hook to access Agentuity context (from `@agentuity/react`).
|
|
230
|
+
|
|
231
|
+
**Returns:**
|
|
232
|
+
|
|
233
|
+
```typescript
|
|
234
|
+
{
|
|
235
|
+
baseUrl: string;
|
|
236
|
+
authHeader?: string | null;
|
|
237
|
+
authLoading?: boolean;
|
|
238
|
+
isAuthenticated: boolean; // Convenience: !authLoading && authHeader !== null
|
|
239
|
+
setAuthHeader?: (token: string | null) => void;
|
|
240
|
+
setAuthLoading?: (loading: boolean) => void;
|
|
241
|
+
}
|
|
242
|
+
```
|
|
243
|
+
|
|
244
|
+
### Types
|
|
245
|
+
|
|
246
|
+
#### `AgentuityAuthUser<T>`
|
|
247
|
+
|
|
248
|
+
Generic authenticated user interface.
|
|
249
|
+
|
|
250
|
+
```typescript
|
|
251
|
+
interface AgentuityAuthUser<T = unknown> {
|
|
252
|
+
id: string;
|
|
253
|
+
name?: string;
|
|
254
|
+
email?: string;
|
|
255
|
+
raw: T; // Provider-specific user object
|
|
256
|
+
}
|
|
257
|
+
```
|
|
258
|
+
|
|
259
|
+
#### `AgentuityAuth<TUser, TRaw>`
|
|
260
|
+
|
|
261
|
+
Generic authentication interface exposed on Hono context.
|
|
262
|
+
|
|
263
|
+
```typescript
|
|
264
|
+
interface AgentuityAuth<TUser = unknown, TRaw = unknown> {
|
|
265
|
+
requireUser(): Promise<AgentuityAuthUser<TUser>>;
|
|
266
|
+
getToken(): Promise<string | null>;
|
|
267
|
+
raw: TRaw; // Provider-specific auth object (e.g., JWT payload)
|
|
268
|
+
}
|
|
269
|
+
```
|
|
270
|
+
|
|
271
|
+
## Templates
|
|
272
|
+
|
|
273
|
+
Get started quickly with the Clerk template:
|
|
274
|
+
|
|
275
|
+
```bash
|
|
276
|
+
bunx agentuity create my-app --template clerk
|
|
277
|
+
cd my-app
|
|
278
|
+
cp .env.example .env
|
|
279
|
+
# Add your Clerk keys to .env
|
|
280
|
+
bun dev
|
|
281
|
+
```
|
|
282
|
+
|
|
283
|
+
## Security Best Practices
|
|
284
|
+
|
|
285
|
+
1. **Never log tokens** - Avoid logging `authHeader` or JWT tokens
|
|
286
|
+
2. **Use HTTPS in production** - Always use TLS for production deployments
|
|
287
|
+
3. **Validate on every request** - Middleware validates tokens on each request
|
|
288
|
+
4. **Keep secrets secret** - Never commit `.env` files or expose `CLERK_SECRET_KEY`
|
|
289
|
+
5. **Use environment variables** - Store all keys in environment variables, not code
|
|
290
|
+
|
|
291
|
+
## Troubleshooting
|
|
292
|
+
|
|
293
|
+
### "Unauthorized" errors when signed in
|
|
294
|
+
|
|
295
|
+
**Check:**
|
|
296
|
+
|
|
297
|
+
1. Authorization header is present in request (browser DevTools → Network tab)
|
|
298
|
+
2. `CLERK_SECRET_KEY` is set in server environment
|
|
299
|
+
3. Token is being fetched (check console for "Failed to get Clerk token")
|
|
300
|
+
|
|
301
|
+
**Debug:**
|
|
302
|
+
|
|
303
|
+
```tsx
|
|
304
|
+
const { authHeader, authLoading, isAuthenticated } = useAgentuity();
|
|
305
|
+
console.log({ authHeader, authLoading, isAuthenticated });
|
|
306
|
+
```
|
|
307
|
+
|
|
308
|
+
### "Clerk secret key is required" error
|
|
309
|
+
|
|
310
|
+
Set `CLERK_SECRET_KEY` in your `.env` file:
|
|
311
|
+
|
|
312
|
+
```env
|
|
313
|
+
CLERK_SECRET_KEY=sk_test_...
|
|
314
|
+
```
|
|
315
|
+
|
|
316
|
+
### Token not being sent in requests
|
|
317
|
+
|
|
318
|
+
Ensure `AgentuityClerk` is a **child** of `AgentuityProvider`:
|
|
319
|
+
|
|
320
|
+
```tsx
|
|
321
|
+
// ✅ CORRECT
|
|
322
|
+
<AgentuityProvider>
|
|
323
|
+
<AgentuityClerk useAuth={useAuth}>
|
|
324
|
+
<App />
|
|
325
|
+
</AgentuityClerk>
|
|
326
|
+
</AgentuityProvider>
|
|
327
|
+
|
|
328
|
+
// ❌ WRONG
|
|
329
|
+
<AgentuityClerk useAuth={useAuth}>
|
|
330
|
+
<AgentuityProvider>
|
|
331
|
+
<App />
|
|
332
|
+
</AgentuityProvider>
|
|
333
|
+
</AgentuityClerk>
|
|
334
|
+
```
|
|
335
|
+
|
|
336
|
+
## Examples
|
|
337
|
+
|
|
338
|
+
See the [Clerk template](../../templates/clerk/) for a complete working example with:
|
|
339
|
+
|
|
340
|
+
- Sign-in/out UI
|
|
341
|
+
- Protected routes
|
|
342
|
+
- Public routes
|
|
343
|
+
- Conditional rendering based on auth state
|
|
344
|
+
|
|
345
|
+
## Contributing
|
|
346
|
+
|
|
347
|
+
This package follows the [Agentuity SDK contributing guidelines](../../AGENTS.md).
|
|
348
|
+
|
|
349
|
+
To add a new provider:
|
|
350
|
+
|
|
351
|
+
1. Create `src/<provider>/` directory
|
|
352
|
+
2. Implement `client.tsx` and `server.ts`
|
|
353
|
+
3. Export from `src/<provider>/index.ts`
|
|
354
|
+
4. Add export path to `package.json`
|
|
355
|
+
5. Add peer dependencies
|
|
356
|
+
6. Write tests in `test/<provider>-*.test.ts`
|
|
357
|
+
|
|
358
|
+
## License
|
|
359
|
+
|
|
360
|
+
MIT
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Clerk client-side authentication provider for React.
|
|
3
|
+
*
|
|
4
|
+
* @module clerk/client
|
|
5
|
+
*/
|
|
6
|
+
import React from 'react';
|
|
7
|
+
import type { useAuth as ClerkUseAuth } from '@clerk/clerk-react';
|
|
8
|
+
type UseAuth = typeof ClerkUseAuth;
|
|
9
|
+
export interface AgentuityClerkProps {
|
|
10
|
+
/** React children to render */
|
|
11
|
+
children: React.ReactNode;
|
|
12
|
+
/** Clerk's useAuth hook from @clerk/clerk-react */
|
|
13
|
+
useAuth: UseAuth;
|
|
14
|
+
/** Token refresh interval in milliseconds (default: 60000 = 1 minute) */
|
|
15
|
+
refreshInterval?: number;
|
|
16
|
+
}
|
|
17
|
+
/**
|
|
18
|
+
* Agentuity authentication provider for Clerk.
|
|
19
|
+
*
|
|
20
|
+
* This component integrates Clerk authentication with Agentuity's context,
|
|
21
|
+
* automatically injecting auth tokens into API calls via useAPI and useWebsocket.
|
|
22
|
+
*
|
|
23
|
+
* Must be a child of both ClerkProvider and AgentuityProvider.
|
|
24
|
+
*
|
|
25
|
+
* @example
|
|
26
|
+
* ```tsx
|
|
27
|
+
* import { ClerkProvider, useAuth } from '@clerk/clerk-react';
|
|
28
|
+
* import { AgentuityProvider } from '@agentuity/react';
|
|
29
|
+
* import { AgentuityClerk } from '@agentuity/auth/clerk';
|
|
30
|
+
*
|
|
31
|
+
* <ClerkProvider publishableKey={key}>
|
|
32
|
+
* <AgentuityProvider>
|
|
33
|
+
* <AgentuityClerk useAuth={useAuth}>
|
|
34
|
+
* <App />
|
|
35
|
+
* </AgentuityClerk>
|
|
36
|
+
* </AgentuityProvider>
|
|
37
|
+
* </ClerkProvider>
|
|
38
|
+
* ```
|
|
39
|
+
*/
|
|
40
|
+
export declare function AgentuityClerk({ children, useAuth, refreshInterval, }: AgentuityClerkProps): import("react/jsx-runtime").JSX.Element;
|
|
41
|
+
export {};
|
|
42
|
+
//# sourceMappingURL=client.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../../src/clerk/client.tsx"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAoB,MAAM,OAAO,CAAC;AACzC,OAAO,KAAK,EAAE,OAAO,IAAI,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAGlE,KAAK,OAAO,GAAG,OAAO,YAAY,CAAC;AAEnC,MAAM,WAAW,mBAAmB;IACnC,+BAA+B;IAC/B,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;IAE1B,mDAAmD;IACnD,OAAO,EAAE,OAAO,CAAC;IAEjB,yEAAyE;IACzE,eAAe,CAAC,EAAE,MAAM,CAAC;CACzB;AAED;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,wBAAgB,cAAc,CAAC,EAC9B,QAAQ,EACR,OAAO,EACP,eAAuB,GACvB,EAAE,mBAAmB,2CAmCrB"}
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
import { Fragment as _Fragment, jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
/**
|
|
3
|
+
* Clerk client-side authentication provider for React.
|
|
4
|
+
*
|
|
5
|
+
* @module clerk/client
|
|
6
|
+
*/
|
|
7
|
+
import { useEffect } from 'react';
|
|
8
|
+
import { useAgentuity } from '@agentuity/react';
|
|
9
|
+
/**
|
|
10
|
+
* Agentuity authentication provider for Clerk.
|
|
11
|
+
*
|
|
12
|
+
* This component integrates Clerk authentication with Agentuity's context,
|
|
13
|
+
* automatically injecting auth tokens into API calls via useAPI and useWebsocket.
|
|
14
|
+
*
|
|
15
|
+
* Must be a child of both ClerkProvider and AgentuityProvider.
|
|
16
|
+
*
|
|
17
|
+
* @example
|
|
18
|
+
* ```tsx
|
|
19
|
+
* import { ClerkProvider, useAuth } from '@clerk/clerk-react';
|
|
20
|
+
* import { AgentuityProvider } from '@agentuity/react';
|
|
21
|
+
* import { AgentuityClerk } from '@agentuity/auth/clerk';
|
|
22
|
+
*
|
|
23
|
+
* <ClerkProvider publishableKey={key}>
|
|
24
|
+
* <AgentuityProvider>
|
|
25
|
+
* <AgentuityClerk useAuth={useAuth}>
|
|
26
|
+
* <App />
|
|
27
|
+
* </AgentuityClerk>
|
|
28
|
+
* </AgentuityProvider>
|
|
29
|
+
* </ClerkProvider>
|
|
30
|
+
* ```
|
|
31
|
+
*/
|
|
32
|
+
export function AgentuityClerk({ children, useAuth, refreshInterval = 60000, }) {
|
|
33
|
+
const { getToken, isLoaded } = useAuth();
|
|
34
|
+
const { setAuthHeader, setAuthLoading } = useAgentuity();
|
|
35
|
+
// Fetch and update token in AgentuityContext
|
|
36
|
+
useEffect(() => {
|
|
37
|
+
if (!isLoaded || !setAuthHeader || !setAuthLoading) {
|
|
38
|
+
if (setAuthLoading) {
|
|
39
|
+
setAuthLoading(true);
|
|
40
|
+
}
|
|
41
|
+
return;
|
|
42
|
+
}
|
|
43
|
+
const fetchToken = async () => {
|
|
44
|
+
try {
|
|
45
|
+
setAuthLoading(true);
|
|
46
|
+
const token = await getToken();
|
|
47
|
+
setAuthHeader(token ? `Bearer ${token}` : null);
|
|
48
|
+
}
|
|
49
|
+
catch (error) {
|
|
50
|
+
console.error('Failed to get Clerk token:', error);
|
|
51
|
+
setAuthHeader(null);
|
|
52
|
+
}
|
|
53
|
+
finally {
|
|
54
|
+
setAuthLoading(false);
|
|
55
|
+
}
|
|
56
|
+
};
|
|
57
|
+
fetchToken();
|
|
58
|
+
// Clerk handles token expiry internally, we refresh periodically
|
|
59
|
+
const interval = setInterval(fetchToken, refreshInterval);
|
|
60
|
+
return () => clearInterval(interval);
|
|
61
|
+
}, [getToken, isLoaded, setAuthHeader, setAuthLoading, refreshInterval]);
|
|
62
|
+
// Render children directly - auth header is now in AgentuityContext
|
|
63
|
+
return _jsx(_Fragment, { children: children });
|
|
64
|
+
}
|
|
65
|
+
//# sourceMappingURL=client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"client.js","sourceRoot":"","sources":["../../src/clerk/client.tsx"],"names":[],"mappings":";AAAA;;;;GAIG;AAEH,OAAc,EAAE,SAAS,EAAE,MAAM,OAAO,CAAC;AAEzC,OAAO,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAehD;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,MAAM,UAAU,cAAc,CAAC,EAC9B,QAAQ,EACR,OAAO,EACP,eAAe,GAAG,KAAK,GACF;IACrB,MAAM,EAAE,QAAQ,EAAE,QAAQ,EAAE,GAAG,OAAO,EAAE,CAAC;IACzC,MAAM,EAAE,aAAa,EAAE,cAAc,EAAE,GAAG,YAAY,EAAE,CAAC;IAEzD,6CAA6C;IAC7C,SAAS,CAAC,GAAG,EAAE;QACd,IAAI,CAAC,QAAQ,IAAI,CAAC,aAAa,IAAI,CAAC,cAAc,EAAE,CAAC;YACpD,IAAI,cAAc,EAAE,CAAC;gBACpB,cAAc,CAAC,IAAI,CAAC,CAAC;YACtB,CAAC;YACD,OAAO;QACR,CAAC;QAED,MAAM,UAAU,GAAG,KAAK,IAAI,EAAE;YAC7B,IAAI,CAAC;gBACJ,cAAc,CAAC,IAAI,CAAC,CAAC;gBACrB,MAAM,KAAK,GAAG,MAAM,QAAQ,EAAE,CAAC;gBAC/B,aAAa,CAAC,KAAK,CAAC,CAAC,CAAC,UAAU,KAAK,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC;YACjD,CAAC;YAAC,OAAO,KAAK,EAAE,CAAC;gBAChB,OAAO,CAAC,KAAK,CAAC,4BAA4B,EAAE,KAAK,CAAC,CAAC;gBACnD,aAAa,CAAC,IAAI,CAAC,CAAC;YACrB,CAAC;oBAAS,CAAC;gBACV,cAAc,CAAC,KAAK,CAAC,CAAC;YACvB,CAAC;QACF,CAAC,CAAC;QAEF,UAAU,EAAE,CAAC;QAEb,iEAAiE;QACjE,MAAM,QAAQ,GAAG,WAAW,CAAC,UAAU,EAAE,eAAe,CAAC,CAAC;QAC1D,OAAO,GAAG,EAAE,CAAC,aAAa,CAAC,QAAQ,CAAC,CAAC;IACtC,CAAC,EAAE,CAAC,QAAQ,EAAE,QAAQ,EAAE,aAAa,EAAE,cAAc,EAAE,eAAe,CAAC,CAAC,CAAC;IAEzE,oEAAoE;IACpE,OAAO,4BAAG,QAAQ,GAAI,CAAC;AACxB,CAAC"}
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Clerk authentication provider for Agentuity.
|
|
3
|
+
*
|
|
4
|
+
* Provides both client-side (React) and server-side (Hono) authentication.
|
|
5
|
+
*
|
|
6
|
+
* @example Client-side
|
|
7
|
+
* ```tsx
|
|
8
|
+
* import { ClerkProvider, useAuth } from '@clerk/clerk-react';
|
|
9
|
+
* import { AgentuityProvider } from '@agentuity/react';
|
|
10
|
+
* import { AgentuityClerk } from '@agentuity/auth/clerk';
|
|
11
|
+
*
|
|
12
|
+
* <ClerkProvider publishableKey={key}>
|
|
13
|
+
* <AgentuityProvider>
|
|
14
|
+
* <AgentuityClerk useAuth={useAuth}>
|
|
15
|
+
* <App />
|
|
16
|
+
* </AgentuityClerk>
|
|
17
|
+
* </AgentuityProvider>
|
|
18
|
+
* </ClerkProvider>
|
|
19
|
+
* ```
|
|
20
|
+
*
|
|
21
|
+
* @example Server-side
|
|
22
|
+
* ```typescript
|
|
23
|
+
* import { createMiddleware } from '@agentuity/auth/clerk';
|
|
24
|
+
*
|
|
25
|
+
* router.get('/api/profile', createMiddleware(), async (c) => {
|
|
26
|
+
* const user = await c.var.auth.requireUser();
|
|
27
|
+
* return c.json({ email: user.email });
|
|
28
|
+
* });
|
|
29
|
+
* ```
|
|
30
|
+
*
|
|
31
|
+
* @module clerk
|
|
32
|
+
*/
|
|
33
|
+
export { AgentuityClerk } from './client';
|
|
34
|
+
export type { AgentuityClerkProps } from './client';
|
|
35
|
+
export { createMiddleware } from './server';
|
|
36
|
+
export type { ClerkMiddlewareOptions, ClerkJWTPayload } from './server';
|
|
37
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/clerk/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BG;AAEH,OAAO,EAAE,cAAc,EAAE,MAAM,UAAU,CAAC;AAC1C,YAAY,EAAE,mBAAmB,EAAE,MAAM,UAAU,CAAC;AACpD,OAAO,EAAE,gBAAgB,EAAE,MAAM,UAAU,CAAC;AAC5C,YAAY,EAAE,sBAAsB,EAAE,eAAe,EAAE,MAAM,UAAU,CAAC"}
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Clerk authentication provider for Agentuity.
|
|
3
|
+
*
|
|
4
|
+
* Provides both client-side (React) and server-side (Hono) authentication.
|
|
5
|
+
*
|
|
6
|
+
* @example Client-side
|
|
7
|
+
* ```tsx
|
|
8
|
+
* import { ClerkProvider, useAuth } from '@clerk/clerk-react';
|
|
9
|
+
* import { AgentuityProvider } from '@agentuity/react';
|
|
10
|
+
* import { AgentuityClerk } from '@agentuity/auth/clerk';
|
|
11
|
+
*
|
|
12
|
+
* <ClerkProvider publishableKey={key}>
|
|
13
|
+
* <AgentuityProvider>
|
|
14
|
+
* <AgentuityClerk useAuth={useAuth}>
|
|
15
|
+
* <App />
|
|
16
|
+
* </AgentuityClerk>
|
|
17
|
+
* </AgentuityProvider>
|
|
18
|
+
* </ClerkProvider>
|
|
19
|
+
* ```
|
|
20
|
+
*
|
|
21
|
+
* @example Server-side
|
|
22
|
+
* ```typescript
|
|
23
|
+
* import { createMiddleware } from '@agentuity/auth/clerk';
|
|
24
|
+
*
|
|
25
|
+
* router.get('/api/profile', createMiddleware(), async (c) => {
|
|
26
|
+
* const user = await c.var.auth.requireUser();
|
|
27
|
+
* return c.json({ email: user.email });
|
|
28
|
+
* });
|
|
29
|
+
* ```
|
|
30
|
+
*
|
|
31
|
+
* @module clerk
|
|
32
|
+
*/
|
|
33
|
+
export { AgentuityClerk } from './client';
|
|
34
|
+
export { createMiddleware } from './server';
|
|
35
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/clerk/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BG;AAEH,OAAO,EAAE,cAAc,EAAE,MAAM,UAAU,CAAC;AAE1C,OAAO,EAAE,gBAAgB,EAAE,MAAM,UAAU,CAAC"}
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Clerk server-side authentication middleware for Hono.
|
|
3
|
+
*
|
|
4
|
+
* @module clerk/server
|
|
5
|
+
*/
|
|
6
|
+
import type { MiddlewareHandler } from 'hono';
|
|
7
|
+
import type { User } from '@clerk/backend';
|
|
8
|
+
import type { AgentuityAuth } from '../types';
|
|
9
|
+
/**
|
|
10
|
+
* Clerk JWT payload structure.
|
|
11
|
+
*/
|
|
12
|
+
export interface ClerkJWTPayload {
|
|
13
|
+
/** Subject (user ID) */
|
|
14
|
+
sub: string;
|
|
15
|
+
/** Additional claims */
|
|
16
|
+
[key: string]: unknown;
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* Options for Clerk middleware.
|
|
20
|
+
*/
|
|
21
|
+
export interface ClerkMiddlewareOptions {
|
|
22
|
+
/** Clerk secret key (defaults to process.env.CLERK_SECRET_KEY) */
|
|
23
|
+
secretKey?: string;
|
|
24
|
+
/** Custom token extractor function */
|
|
25
|
+
getToken?: (authHeader: string) => string;
|
|
26
|
+
/** Clerk publishable key for token verification */
|
|
27
|
+
publishableKey?: string;
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* Create Hono middleware for Clerk authentication.
|
|
31
|
+
*
|
|
32
|
+
* This middleware:
|
|
33
|
+
* - Extracts and validates JWT tokens from Authorization header
|
|
34
|
+
* - Returns 401 if token is missing or invalid
|
|
35
|
+
* - Exposes authenticated user via c.var.auth
|
|
36
|
+
*
|
|
37
|
+
* @example
|
|
38
|
+
* ```typescript
|
|
39
|
+
* import { createMiddleware } from '@agentuity/auth/clerk';
|
|
40
|
+
*
|
|
41
|
+
* router.get('/api/profile', createMiddleware(), async (c) => {
|
|
42
|
+
* const user = await c.var.auth.requireUser();
|
|
43
|
+
* return c.json({ email: user.email });
|
|
44
|
+
* });
|
|
45
|
+
* ```
|
|
46
|
+
*/
|
|
47
|
+
export declare function createMiddleware(options?: ClerkMiddlewareOptions): MiddlewareHandler;
|
|
48
|
+
/**
|
|
49
|
+
* Augment Hono's context types to include auth.
|
|
50
|
+
*/
|
|
51
|
+
declare module 'hono' {
|
|
52
|
+
interface ContextVariableMap {
|
|
53
|
+
auth: AgentuityAuth<User, ClerkJWTPayload>;
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
//# sourceMappingURL=server.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"server.d.ts","sourceRoot":"","sources":["../../src/clerk/server.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,MAAM,CAAC;AAE9C,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,gBAAgB,CAAC;AAC3C,OAAO,KAAK,EAAE,aAAa,EAAqB,MAAM,UAAU,CAAC;AAEjE;;GAEG;AACH,MAAM,WAAW,eAAe;IAC/B,wBAAwB;IACxB,GAAG,EAAE,MAAM,CAAC;IACZ,wBAAwB;IACxB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;CACvB;AAED;;GAEG;AACH,MAAM,WAAW,sBAAsB;IACtC,kEAAkE;IAClE,SAAS,CAAC,EAAE,MAAM,CAAC;IAEnB,sCAAsC;IACtC,QAAQ,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,KAAK,MAAM,CAAC;IAE1C,mDAAmD;IACnD,cAAc,CAAC,EAAE,MAAM,CAAC;CACxB;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,gBAAgB,CAAC,OAAO,GAAE,sBAA2B,GAAG,iBAAiB,CA6FxF;AAcD;;GAEG;AACH,OAAO,QAAQ,MAAM,CAAC;IACrB,UAAU,kBAAkB;QAC3B,IAAI,EAAE,aAAa,CAAC,IAAI,EAAE,eAAe,CAAC,CAAC;KAC3C;CACD"}
|