@docyrus/docyrus 0.0.30 → 0.0.32
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/agent-loader.js +36 -25
- package/agent-loader.js.map +4 -4
- package/main.js +4 -4
- package/main.js.map +1 -1
- package/package.json +3 -3
- package/resources/pi-agent/extensions/docyrus-web-browser.ts +31 -0
- package/resources/pi-agent/shared/docyrusWebBrowserProtocol.ts +169 -0
- package/resources/pi-agent/skills/diffity-diff/SKILL.md +1 -1
- package/resources/pi-agent/skills/diffity-resolve/SKILL.md +4 -4
- package/resources/pi-agent/skills/diffity-review/SKILL.md +5 -4
- package/resources/pi-agent/skills/docyrus-api-dev/SKILL.md +197 -0
- package/resources/pi-agent/skills/docyrus-api-dev/references/acl-endpoints-frontend.md +295 -0
- package/resources/pi-agent/skills/docyrus-api-dev/references/api-client.md +349 -0
- package/resources/pi-agent/skills/docyrus-api-dev/references/authentication.md +298 -0
- package/resources/pi-agent/skills/docyrus-api-dev/references/data-source-query-guide.md +2063 -0
- package/resources/pi-agent/skills/docyrus-api-dev/references/formula-design-guide-llm.md +312 -0
- package/resources/pi-agent/skills/docyrus-api-dev/references/query-and-formulas.md +592 -0
- package/resources/pi-agent/skills/docyrus-app-dev-react/SKILL.md +361 -0
- package/resources/pi-agent/skills/docyrus-app-dev-react/references/README.md +29 -0
- package/resources/pi-agent/skills/docyrus-app-dev-react/references/api-client-and-auth.md +326 -0
- package/resources/pi-agent/skills/docyrus-app-dev-react/references/collections-and-patterns.md +353 -0
- package/resources/pi-agent/skills/docyrus-app-dev-react/references/component-selection-guide.md +619 -0
- package/resources/pi-agent/skills/docyrus-app-dev-react/references/icon-usage-guide.md +463 -0
- package/resources/pi-agent/skills/docyrus-app-dev-react/references/preferred-components-catalog.md +242 -0
- package/resources/pi-agent/skills/docyrus-platform/SKILL.md +2 -2
- package/resources/pi-agent/skills/docyrus-platform/references/auth-and-multi-tenancy.md +9 -1
- package/resources/pi-agent/skills/docyrus-platform/references/developer-tools.md +3 -2
- package/server-loader.js +328 -87
- package/server-loader.js.map +4 -4
- package/resources/pi-agent/extensions/multi-edit.ts +0 -835
|
@@ -0,0 +1,298 @@
|
|
|
1
|
+
# @docyrus/signin — React Authentication Reference
|
|
2
|
+
|
|
3
|
+
## Table of Contents
|
|
4
|
+
|
|
5
|
+
1. [Overview](#overview)
|
|
6
|
+
2. [Installation](#installation)
|
|
7
|
+
3. [DocyrusAuthProvider](#docyrusauthprovider)
|
|
8
|
+
4. [Auth Hooks](#auth-hooks)
|
|
9
|
+
5. [Authorization (Roles & Permissions)](#authorization-roles--permissions)
|
|
10
|
+
6. [SignInButton](#signinbutton)
|
|
11
|
+
7. [Auth Modes](#auth-modes)
|
|
12
|
+
8. [Environment Variables](#environment-variables)
|
|
13
|
+
9. [App Integration Pattern](#app-integration-pattern)
|
|
14
|
+
10. [Advanced Usage](#advanced-usage)
|
|
15
|
+
|
|
16
|
+
---
|
|
17
|
+
|
|
18
|
+
## Overview
|
|
19
|
+
|
|
20
|
+
`@docyrus/signin` provides "Sign in with Docyrus" for React apps. Auto-detects environment:
|
|
21
|
+
- **Standalone**: OAuth2 Authorization Code + PKCE via page redirect
|
|
22
|
+
- **Iframe**: Receives tokens via `window.postMessage` from `*.docyrus.app` hosts
|
|
23
|
+
|
|
24
|
+
Peer dependencies: `react >= 18`, `@docyrus/api-client >= 0.0.10`
|
|
25
|
+
|
|
26
|
+
---
|
|
27
|
+
|
|
28
|
+
## Installation
|
|
29
|
+
|
|
30
|
+
```bash
|
|
31
|
+
pnpm add @docyrus/signin @docyrus/api-client
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
---
|
|
35
|
+
|
|
36
|
+
## DocyrusAuthProvider
|
|
37
|
+
|
|
38
|
+
Wrap application root:
|
|
39
|
+
|
|
40
|
+
```tsx
|
|
41
|
+
import { DocyrusAuthProvider } from '@docyrus/signin'
|
|
42
|
+
|
|
43
|
+
<DocyrusAuthProvider
|
|
44
|
+
apiUrl="https://alpha-api.docyrus.com"
|
|
45
|
+
clientId="your-oauth2-client-id"
|
|
46
|
+
redirectUri="http://localhost:3000/auth/callback"
|
|
47
|
+
scopes={['offline_access', 'Read.All', 'DS.ReadWrite.All', 'Users.Read']}
|
|
48
|
+
callbackPath="/auth/callback"
|
|
49
|
+
>
|
|
50
|
+
<App />
|
|
51
|
+
</DocyrusAuthProvider>
|
|
52
|
+
```
|
|
53
|
+
|
|
54
|
+
### Props
|
|
55
|
+
|
|
56
|
+
| Prop | Type | Default | Description |
|
|
57
|
+
|------|------|---------|-------------|
|
|
58
|
+
| `apiUrl` | `string` | `https://alpha-api.docyrus.com` | API base URL |
|
|
59
|
+
| `clientId` | `string` | Built-in default | OAuth2 client ID |
|
|
60
|
+
| `redirectUri` | `string` | `origin + callbackPath` | OAuth2 redirect URI |
|
|
61
|
+
| `scopes` | `string[]` | `['offline_access', 'Read.All', ...]` | OAuth2 scopes |
|
|
62
|
+
| `callbackPath` | `string` | `/auth/callback` | Path to detect OAuth callback |
|
|
63
|
+
| `forceMode` | `'standalone' \| 'iframe'` | Auto-detected | Force a specific auth mode |
|
|
64
|
+
| `storageKeyPrefix` | `string` | `docyrus_oauth2_` | localStorage key prefix |
|
|
65
|
+
| `allowedHostOrigins` | `string[]` | `undefined` | Extra trusted iframe origins |
|
|
66
|
+
|
|
67
|
+
---
|
|
68
|
+
|
|
69
|
+
## Auth Hooks
|
|
70
|
+
|
|
71
|
+
### useDocyrusAuth()
|
|
72
|
+
|
|
73
|
+
Full authentication context:
|
|
74
|
+
|
|
75
|
+
```typescript
|
|
76
|
+
import { useDocyrusAuth } from '@docyrus/signin'
|
|
77
|
+
|
|
78
|
+
const {
|
|
79
|
+
status, // 'loading' | 'authenticated' | 'unauthenticated'
|
|
80
|
+
mode, // 'standalone' | 'iframe'
|
|
81
|
+
client, // RestApiClient | null — configured API client with tokens
|
|
82
|
+
tokens, // { accessToken, refreshToken, ... } | null
|
|
83
|
+
user, // DocyrusUser | null — auto-fetched from /v1/users/me
|
|
84
|
+
signIn, // () => void — redirects to Docyrus login page
|
|
85
|
+
signOut, // () => void — logout and clear tokens
|
|
86
|
+
hasRole, // (role: string | string[]) => boolean — check role by slug or uid
|
|
87
|
+
hasPermission, // (operation: string, dataSourceId?: string) => boolean — check ACL permission
|
|
88
|
+
refreshUser, // () => Promise<void> — re-fetch user from API
|
|
89
|
+
error, // Error | null
|
|
90
|
+
} = useDocyrusAuth()
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
### useDocyrusClient()
|
|
94
|
+
|
|
95
|
+
Shorthand for just the API client:
|
|
96
|
+
|
|
97
|
+
```typescript
|
|
98
|
+
import { useDocyrusClient } from '@docyrus/signin'
|
|
99
|
+
|
|
100
|
+
const client = useDocyrusClient() // RestApiClient | null
|
|
101
|
+
|
|
102
|
+
if (client) {
|
|
103
|
+
const user = await client.get('/v1/users/me')
|
|
104
|
+
const items = await client.get('/v1/apps/base/data-sources/project/items', queryPayload)
|
|
105
|
+
}
|
|
106
|
+
```
|
|
107
|
+
|
|
108
|
+
---
|
|
109
|
+
|
|
110
|
+
## Authorization (Roles & Permissions)
|
|
111
|
+
|
|
112
|
+
The provider auto-fetches the current user from `/v1/users/me` after authentication and exposes `hasRole` and `hasPermission` helpers. The `user` object is `null` until the fetch completes (shortly after `status` becomes `'authenticated'`).
|
|
113
|
+
|
|
114
|
+
### Role Checking
|
|
115
|
+
|
|
116
|
+
```typescript
|
|
117
|
+
const { hasRole } = useDocyrusAuth()
|
|
118
|
+
|
|
119
|
+
hasRole(null) // true — no role requirement
|
|
120
|
+
hasRole('super_admin') // checks slug or uid match
|
|
121
|
+
hasRole(['editor', 'reviewer']) // true if user has any of these roles
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
Checks both `primaryRole` and all additional `roles` from the user object.
|
|
125
|
+
|
|
126
|
+
### Permission Checking
|
|
127
|
+
|
|
128
|
+
```typescript
|
|
129
|
+
const { hasPermission } = useDocyrusAuth()
|
|
130
|
+
|
|
131
|
+
hasPermission('view', dataSourceId) // can view this data source?
|
|
132
|
+
hasPermission('edit', dataSourceId) // can edit?
|
|
133
|
+
hasPermission('delete', dataSourceId) // can delete?
|
|
134
|
+
```
|
|
135
|
+
|
|
136
|
+
**Permission resolution order:**
|
|
137
|
+
1. `super_admin` role → always granted
|
|
138
|
+
2. `global_editor` role → granted for: view, create, edit, delete, create_bulk, export, import, print
|
|
139
|
+
3. `global_viewer` role → granted only for: view
|
|
140
|
+
4. Always-permitted system data sources (reports, todos, notes, etc.)
|
|
141
|
+
5. User's `aclRules` array (merged from all roles by the server)
|
|
142
|
+
|
|
143
|
+
### Pure Functions (Framework-Agnostic)
|
|
144
|
+
|
|
145
|
+
```typescript
|
|
146
|
+
import { hasRole, hasPermission } from '@docyrus/signin/core'
|
|
147
|
+
import type { DocyrusUser } from '@docyrus/signin/core'
|
|
148
|
+
|
|
149
|
+
// Use with any user object (e.g., server-side, tests)
|
|
150
|
+
hasRole(user, 'super_admin')
|
|
151
|
+
hasPermission(user, 'edit', 'some-ds-id')
|
|
152
|
+
```
|
|
153
|
+
|
|
154
|
+
### Refreshing User Data
|
|
155
|
+
|
|
156
|
+
```typescript
|
|
157
|
+
const { refreshUser } = useDocyrusAuth()
|
|
158
|
+
await refreshUser() // re-fetch after role/permission changes
|
|
159
|
+
```
|
|
160
|
+
|
|
161
|
+
---
|
|
162
|
+
|
|
163
|
+
## SignInButton
|
|
164
|
+
|
|
165
|
+
Unstyled button. Automatically hidden when authenticated or in iframe mode.
|
|
166
|
+
|
|
167
|
+
```tsx
|
|
168
|
+
import { SignInButton } from '@docyrus/signin'
|
|
169
|
+
|
|
170
|
+
// Basic
|
|
171
|
+
<SignInButton />
|
|
172
|
+
|
|
173
|
+
// Styled
|
|
174
|
+
<SignInButton className="btn btn-primary" label="Log in with Docyrus" />
|
|
175
|
+
|
|
176
|
+
// Render prop for full control
|
|
177
|
+
<SignInButton>
|
|
178
|
+
{({ signIn, isLoading }) => (
|
|
179
|
+
<button onClick={signIn} disabled={isLoading}>
|
|
180
|
+
{isLoading ? 'Redirecting...' : 'Sign in with Docyrus'}
|
|
181
|
+
</button>
|
|
182
|
+
)}
|
|
183
|
+
</SignInButton>
|
|
184
|
+
```
|
|
185
|
+
|
|
186
|
+
---
|
|
187
|
+
|
|
188
|
+
## Auth Modes
|
|
189
|
+
|
|
190
|
+
### Standalone (OAuth2 PKCE)
|
|
191
|
+
|
|
192
|
+
For apps running directly in the browser:
|
|
193
|
+
|
|
194
|
+
1. User clicks sign-in
|
|
195
|
+
2. Page redirects to Docyrus authorization endpoint
|
|
196
|
+
3. After login, redirects back with authorization code
|
|
197
|
+
4. Provider automatically exchanges code for tokens
|
|
198
|
+
5. Tokens stored in localStorage, auto-refreshed before expiry
|
|
199
|
+
|
|
200
|
+
### Iframe (postMessage)
|
|
201
|
+
|
|
202
|
+
For apps embedded in an iframe on `*.docyrus.app`:
|
|
203
|
+
|
|
204
|
+
1. Provider detects iframe environment and validates host origin
|
|
205
|
+
2. Host sends `{ type: 'signin', accessToken, refreshToken }` via `postMessage`
|
|
206
|
+
3. Provider creates API client with received tokens
|
|
207
|
+
4. When tokens expire, provider sends `{ type: 'token-refresh-request' }` to host
|
|
208
|
+
5. Host responds with fresh tokens
|
|
209
|
+
|
|
210
|
+
---
|
|
211
|
+
|
|
212
|
+
## Environment Variables
|
|
213
|
+
|
|
214
|
+
```bash
|
|
215
|
+
# .env
|
|
216
|
+
VITE_API_BASE_URL=https://localhost:3366
|
|
217
|
+
VITE_OAUTH2_CLIENT_ID=your-client-id
|
|
218
|
+
VITE_OAUTH2_REDIRECT_URI=http://localhost:3000/auth/callback
|
|
219
|
+
VITE_OAUTH2_SCOPES=openid profile offline_access Users.Read DS.ReadWrite.All
|
|
220
|
+
```
|
|
221
|
+
|
|
222
|
+
Access in code: `import.meta.env.VITE_API_BASE_URL`
|
|
223
|
+
|
|
224
|
+
---
|
|
225
|
+
|
|
226
|
+
## App Integration Pattern
|
|
227
|
+
|
|
228
|
+
### Minimal Setup (main.tsx)
|
|
229
|
+
|
|
230
|
+
```tsx
|
|
231
|
+
import { StrictMode } from 'react'
|
|
232
|
+
import { createRoot } from 'react-dom/client'
|
|
233
|
+
import { DocyrusAuthProvider } from '@docyrus/signin'
|
|
234
|
+
|
|
235
|
+
const scopes = (import.meta.env.VITE_OAUTH2_SCOPES || '').split(' ').filter(Boolean)
|
|
236
|
+
|
|
237
|
+
createRoot(document.getElementById('root')!).render(
|
|
238
|
+
<StrictMode>
|
|
239
|
+
<DocyrusAuthProvider
|
|
240
|
+
apiUrl={import.meta.env.VITE_API_BASE_URL}
|
|
241
|
+
clientId={import.meta.env.VITE_OAUTH2_CLIENT_ID}
|
|
242
|
+
redirectUri={import.meta.env.VITE_OAUTH2_REDIRECT_URI}
|
|
243
|
+
scopes={scopes}
|
|
244
|
+
callbackPath="/auth/callback"
|
|
245
|
+
>
|
|
246
|
+
<App />
|
|
247
|
+
</DocyrusAuthProvider>
|
|
248
|
+
</StrictMode>,
|
|
249
|
+
)
|
|
250
|
+
```
|
|
251
|
+
|
|
252
|
+
### Auth-Gated App (App.tsx)
|
|
253
|
+
|
|
254
|
+
```tsx
|
|
255
|
+
import { useDocyrusAuth, useDocyrusClient, SignInButton } from '@docyrus/signin'
|
|
256
|
+
|
|
257
|
+
function App() {
|
|
258
|
+
const { status, signOut } = useDocyrusAuth()
|
|
259
|
+
const client = useDocyrusClient()
|
|
260
|
+
|
|
261
|
+
if (status === 'loading') return <div>Loading...</div>
|
|
262
|
+
if (status === 'unauthenticated') return <SignInButton />
|
|
263
|
+
|
|
264
|
+
// client is guaranteed non-null when authenticated
|
|
265
|
+
return (
|
|
266
|
+
<div>
|
|
267
|
+
<p>Authenticated!</p>
|
|
268
|
+
<button onClick={() => client!.get('/v1/users/me').then(console.log)}>My Profile</button>
|
|
269
|
+
<button onClick={signOut}>Sign Out</button>
|
|
270
|
+
</div>
|
|
271
|
+
)
|
|
272
|
+
}
|
|
273
|
+
```
|
|
274
|
+
|
|
275
|
+
### Accessing the API Client
|
|
276
|
+
|
|
277
|
+
In React components, use `useDocyrusClient()` to get the authenticated client. Generated collections are hooks that call `useDocyrusClient()` internally, so no manual client syncing is needed:
|
|
278
|
+
|
|
279
|
+
```typescript
|
|
280
|
+
// Generated collections use useDocyrusClient() internally
|
|
281
|
+
const { list, get, create } = useBaseProjectCollection()
|
|
282
|
+
|
|
283
|
+
// For direct API access in React components
|
|
284
|
+
const client = useDocyrusClient()
|
|
285
|
+
const data = await client!.get('/v1/custom-endpoint')
|
|
286
|
+
```
|
|
287
|
+
|
|
288
|
+
---
|
|
289
|
+
|
|
290
|
+
## Advanced Usage
|
|
291
|
+
|
|
292
|
+
Core classes and permission functions exported for advanced scenarios:
|
|
293
|
+
|
|
294
|
+
```typescript
|
|
295
|
+
import { AuthManager, StandaloneOAuth2Auth, IframeAuth, detectAuthMode } from '@docyrus/signin'
|
|
296
|
+
import { hasRole, hasPermission, getAllRoles } from '@docyrus/signin/core'
|
|
297
|
+
import type { DocyrusUser, DocyrusRole, DocyrusAclRule, AclOperation, PermissionConfig } from '@docyrus/signin/core'
|
|
298
|
+
```
|