@zeyos/client 0.1.0
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/CHANGELOG.md +31 -0
- package/LICENSE +21 -0
- package/README.md +458 -0
- package/agents/README.md +66 -0
- package/agents/shared/business-app-benchmarks.md +111 -0
- package/agents/shared/zeyos-entity-map.md +142 -0
- package/agents/shared/zeyos-entity-reference.md +570 -0
- package/agents/shared/zeyos-query-patterns.md +89 -0
- package/agents/zeyos-account-intelligence/SKILL.md +34 -0
- package/agents/zeyos-account-intelligence/agents/openai.yaml +4 -0
- package/agents/zeyos-account-intelligence/references/workflows.md +84 -0
- package/agents/zeyos-billing-insights/SKILL.md +41 -0
- package/agents/zeyos-billing-insights/agents/openai.yaml +4 -0
- package/agents/zeyos-billing-insights/references/workflows.md +106 -0
- package/agents/zeyos-campaign-and-outreach/SKILL.md +44 -0
- package/agents/zeyos-campaign-and-outreach/agents/openai.yaml +4 -0
- package/agents/zeyos-campaign-and-outreach/references/workflows.md +100 -0
- package/agents/zeyos-collaboration-and-activity/SKILL.md +37 -0
- package/agents/zeyos-collaboration-and-activity/agents/openai.yaml +4 -0
- package/agents/zeyos-collaboration-and-activity/references/workflows.md +104 -0
- package/agents/zeyos-collections-and-dunning/SKILL.md +46 -0
- package/agents/zeyos-collections-and-dunning/agents/openai.yaml +4 -0
- package/agents/zeyos-collections-and-dunning/references/workflows.md +132 -0
- package/agents/zeyos-commerce-and-inventory/SKILL.md +38 -0
- package/agents/zeyos-commerce-and-inventory/agents/openai.yaml +4 -0
- package/agents/zeyos-commerce-and-inventory/references/workflows.md +101 -0
- package/agents/zeyos-mail-operations/SKILL.md +35 -0
- package/agents/zeyos-mail-operations/agents/openai.yaml +4 -0
- package/agents/zeyos-mail-operations/references/workflows.md +110 -0
- package/agents/zeyos-notes-and-sops/SKILL.md +31 -0
- package/agents/zeyos-notes-and-sops/agents/openai.yaml +4 -0
- package/agents/zeyos-notes-and-sops/references/workflows.md +85 -0
- package/agents/zeyos-platform-and-schema/SKILL.md +37 -0
- package/agents/zeyos-platform-and-schema/agents/openai.yaml +4 -0
- package/agents/zeyos-platform-and-schema/references/workflows.md +97 -0
- package/agents/zeyos-work-management/SKILL.md +45 -0
- package/agents/zeyos-work-management/agents/openai.yaml +4 -0
- package/agents/zeyos-work-management/references/workflows.md +148 -0
- package/docs/01-api-reference/01-data-retrieval.md +601 -0
- package/docs/01-api-reference/02-authentication.md +288 -0
- package/docs/01-api-reference/03-resources.md +270 -0
- package/docs/01-api-reference/04-schema.md +539 -0
- package/docs/01-api-reference/_category_.json +9 -0
- package/docs/02-javascript-client/01-getting-started.md +146 -0
- package/docs/02-javascript-client/02-authentication.md +287 -0
- package/docs/02-javascript-client/03-making-requests.md +572 -0
- package/docs/02-javascript-client/04-practical-guide.md +348 -0
- package/docs/02-javascript-client/_category_.json +9 -0
- package/docs/03-cli/01-getting-started.md +219 -0
- package/docs/03-cli/02-commands.md +407 -0
- package/docs/03-cli/03-configuration.md +220 -0
- package/docs/03-cli/_category_.json +9 -0
- package/docs/04-agent-workflows/00-coding-agents.md +35 -0
- package/docs/04-agent-workflows/01-agent-quickstart.md +147 -0
- package/docs/04-agent-workflows/02-agent-recipes.md +109 -0
- package/docs/04-agent-workflows/03-cli-coverage-and-escalation.md +65 -0
- package/docs/04-agent-workflows/_category_.json +9 -0
- package/docs/04-sample-apps/01-kanban.md +89 -0
- package/docs/04-sample-apps/02-crm.md +81 -0
- package/docs/04-sample-apps/03-dashboard.md +80 -0
- package/docs/04-sample-apps/_category_.json +9 -0
- package/docs/05-tutorials/00-application-developers.md +43 -0
- package/docs/05-tutorials/01-integration-architecture.md +60 -0
- package/docs/05-tutorials/02-build-your-own-zeyos-frontend.md +517 -0
- package/docs/05-tutorials/03-server-side-integrations.md +185 -0
- package/docs/05-tutorials/_category_.json +9 -0
- package/docs/intro.md +197 -0
- package/openapi/api.json +24308 -0
- package/openapi/auth.json +415 -0
- package/openapi/dbref.json +56223 -0
- package/openapi/oauth2.json +781 -0
- package/openapi/sdk.json +949 -0
- package/openapi/views.txt +642 -0
- package/package.json +49 -0
- package/samples/crm/README.md +28 -0
- package/samples/crm/index.html +327 -0
- package/samples/crm/js/api.js +208 -0
- package/samples/crm/js/auth.js +61 -0
- package/samples/crm/js/main.js +545 -0
- package/samples/crm/js/state.js +90 -0
- package/samples/crm/js/ui.js +51 -0
- package/samples/dashboard/README.md +28 -0
- package/samples/dashboard/index.html +280 -0
- package/samples/dashboard/js/api.js +197 -0
- package/samples/dashboard/js/auth.js +59 -0
- package/samples/dashboard/js/main.js +382 -0
- package/samples/dashboard/js/state.js +81 -0
- package/samples/dashboard/js/ui.js +48 -0
- package/samples/kanban/README.md +28 -0
- package/samples/kanban/index.html +263 -0
- package/samples/kanban/js/api.js +152 -0
- package/samples/kanban/js/auth.js +59 -0
- package/samples/kanban/js/constants.js +40 -0
- package/samples/kanban/js/kanban.js +246 -0
- package/samples/kanban/js/main.js +362 -0
- package/samples/kanban/js/modals.js +474 -0
- package/samples/kanban/js/settings.js +82 -0
- package/samples/kanban/js/state.js +118 -0
- package/samples/kanban/js/ui.js +49 -0
- package/scripts/generate-client.mjs +344 -0
- package/src/generated/operations.js +9772 -0
- package/src/generated/schema.js +8982 -0
- package/src/index.js +85 -0
- package/src/runtime/client.js +1208 -0
- package/src/runtime/error.js +29 -0
- package/src/runtime/http.js +174 -0
- package/src/runtime/request-shape.js +35 -0
- package/src/runtime/schema.js +206 -0
- package/src/runtime/suggest.js +74 -0
- package/src/runtime/token-store.js +105 -0
|
@@ -0,0 +1,146 @@
|
|
|
1
|
+
---
|
|
2
|
+
sidebar_label: Getting Started
|
|
3
|
+
---
|
|
4
|
+
|
|
5
|
+
# Getting Started
|
|
6
|
+
|
|
7
|
+
The ZeyOS JavaScript client provides a generated, dependency-light interface to the ZeyOS REST API. It works in both browser environments and Node.js 18+, with built-in support for OAuth 2.0, session-based authentication, and automatic token refresh.
|
|
8
|
+
|
|
9
|
+
Use the JavaScript client when:
|
|
10
|
+
|
|
11
|
+
- the CLI resource registry is not enough
|
|
12
|
+
- you are building a browser UI or a server-side integration
|
|
13
|
+
- you need request-level control through `client.request()`
|
|
14
|
+
- you want access to the full generated API surface instead of the CLI's curated subset
|
|
15
|
+
|
|
16
|
+
## Installation
|
|
17
|
+
|
|
18
|
+
:::info ESM only
|
|
19
|
+
`@zeyos/client` is an ES module (ESM) package. Use `import` (or dynamic `import()`) to load it. CommonJS `require()` is not supported.
|
|
20
|
+
:::
|
|
21
|
+
|
|
22
|
+
The client is distributed as an ES module source package. If you are working inside this repository, import it directly from the source tree:
|
|
23
|
+
|
|
24
|
+
```js
|
|
25
|
+
import { createZeyosClient } from './src/index.js';
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
If you are consuming it from another project, install the package and import it by name:
|
|
29
|
+
|
|
30
|
+
```bash
|
|
31
|
+
npm install @zeyos/client
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
```js
|
|
35
|
+
import { createZeyosClient } from '@zeyos/client';
|
|
36
|
+
```
|
|
37
|
+
|
|
38
|
+
The client has zero runtime dependencies and relies only on the standard `fetch` API available in modern browsers and Node.js 18+.
|
|
39
|
+
|
|
40
|
+
## Creating a Client
|
|
41
|
+
|
|
42
|
+
The `createZeyosClient` factory function returns a frozen client object with generated API methods, OAuth 2.0 helpers, and low-level request capabilities.
|
|
43
|
+
|
|
44
|
+
```js
|
|
45
|
+
import { createZeyosClient } from '@zeyos/client';
|
|
46
|
+
|
|
47
|
+
const client = createZeyosClient({
|
|
48
|
+
platform: 'https://cloud.zeyos.com/demo/',
|
|
49
|
+
auth: {
|
|
50
|
+
mode: 'session',
|
|
51
|
+
session: { enabled: true, credentials: 'include' },
|
|
52
|
+
},
|
|
53
|
+
});
|
|
54
|
+
|
|
55
|
+
const tickets = await client.api.listTickets({ limit: 10 });
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
The returned `client` object exposes:
|
|
59
|
+
|
|
60
|
+
- **`client.api`** -- Generated methods for all standard REST operations (e.g. `listTickets`, `createAccount`, `getTask`)
|
|
61
|
+
- **`client.oauth2`** -- OAuth 2.0 token operations and authorization URL helpers
|
|
62
|
+
- **`client.legacyAuth`** -- Legacy session authentication operations (`login`, `logout`, `verify`, `getUserInfo`)
|
|
63
|
+
- **`client.request()`** -- Low-level escape hatch for custom or advanced requests
|
|
64
|
+
- **`client.schema`** -- Runtime introspection and input validation (`describe`, `fields`, `resources`, `operations`, `validate`); see [Making Requests](./03-making-requests.md#schema-introspection-and-validation)
|
|
65
|
+
- **`client.auth`** -- Token management (`getTokenSet`, `setTokenSet`, `clearTokenSet`)
|
|
66
|
+
- **`client.metadata`** -- Read-only info about the generated client (`generatedAt` timestamp, `services` array)
|
|
67
|
+
|
|
68
|
+
## Platform Configuration
|
|
69
|
+
|
|
70
|
+
The `platform` option tells the client where your ZeyOS instance lives. There are three ways to specify it:
|
|
71
|
+
|
|
72
|
+
### URL String
|
|
73
|
+
|
|
74
|
+
Pass the full URL to your ZeyOS instance. The client extracts the origin and instance name automatically.
|
|
75
|
+
|
|
76
|
+
```js
|
|
77
|
+
const client = createZeyosClient({
|
|
78
|
+
platform: 'https://cloud.zeyos.com/demo/',
|
|
79
|
+
});
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
### Preset
|
|
83
|
+
|
|
84
|
+
Use a named preset for the ZeyOS cloud platform, combined with an `instance` name:
|
|
85
|
+
|
|
86
|
+
```js
|
|
87
|
+
const client = createZeyosClient({
|
|
88
|
+
platform: 'live',
|
|
89
|
+
instance: 'demo',
|
|
90
|
+
});
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
The `live` preset resolves to `https://cloud.zeyos.com`.
|
|
94
|
+
|
|
95
|
+
### Object
|
|
96
|
+
|
|
97
|
+
For full control, pass an object with `origin` and `instance`:
|
|
98
|
+
|
|
99
|
+
```js
|
|
100
|
+
const client = createZeyosClient({
|
|
101
|
+
platform: {
|
|
102
|
+
origin: 'https://cloud.zeyos.com',
|
|
103
|
+
instance: 'demo',
|
|
104
|
+
},
|
|
105
|
+
});
|
|
106
|
+
```
|
|
107
|
+
|
|
108
|
+
## Features
|
|
109
|
+
|
|
110
|
+
- **Zero dependencies** -- no external packages; only the standard `fetch` API is required
|
|
111
|
+
- **Browser + Node.js 18+** -- works in any environment with global `fetch`
|
|
112
|
+
- **Auto token refresh** -- transparently refreshes expired access tokens before requests or after bearer 401 responses
|
|
113
|
+
- **Generated API methods** -- the broader generated API surface is available as `client.api.<operationId>()`
|
|
114
|
+
- **Session + OAuth support** -- choose between cookie-based sessions, bearer tokens, or automatic fallback
|
|
115
|
+
- **Low-level escape hatch** -- `client.request()` for custom endpoints and advanced use cases
|
|
116
|
+
|
|
117
|
+
## Configuration Reference
|
|
118
|
+
|
|
119
|
+
| Option | Type | Description |
|
|
120
|
+
|--------|------|-------------|
|
|
121
|
+
| `platform` | `string \| { origin?: string, instance?: string, preset?: string, url?: string }` | ZeyOS instance URL, preset name (e.g. `'live'`), or object with `origin`/`instance` (and optionally `preset` or `url`) |
|
|
122
|
+
| `platform.origin` | `string` | Base origin URL (e.g. `'https://cloud.zeyos.com'`) |
|
|
123
|
+
| `platform.instance` | `string` | Instance name (e.g. `'demo'`) |
|
|
124
|
+
| `platform.preset` | `string` | Named preset (e.g. `'live'`) used when `origin` is omitted |
|
|
125
|
+
| `platform.url` | `string` | Full instance URL as an alternative to `origin`+`instance` |
|
|
126
|
+
| `instance` | `string` | Top-level instance name shortcut (used with preset-style `platform`) |
|
|
127
|
+
| `auth.mode` | `string` | Authentication mode: `'auto'` (default), `'oauth'`, `'session'`, or `'none'` |
|
|
128
|
+
| `auth.oauth.clientId` | `string` | OAuth 2.0 client ID for token operations |
|
|
129
|
+
| `auth.oauth.clientSecret` | `string` | OAuth 2.0 client secret for token operations |
|
|
130
|
+
| `auth.oauth.tokenStore` | `TokenStore` | Token storage backend (must implement `get()` and `set()`) |
|
|
131
|
+
| `auth.oauth.autoRefresh` | `boolean` | Automatically refresh access tokens before requests or after bearer 401 responses (default: `true`) |
|
|
132
|
+
| `auth.session.enabled` | `boolean` | Enable session-based authentication (default: `true`) |
|
|
133
|
+
| `auth.session.credentials` | `string` | Fetch credentials mode: `'include'`, `'same-origin'`, or `'omit'` |
|
|
134
|
+
| `auth.session.cookie` | `string \| () => string \| Promise<string>` | Explicit session cookie value or async function returning one (Node.js) |
|
|
135
|
+
| `headers` | `HeadersInit` | Default headers applied to every request |
|
|
136
|
+
| `fetch` | `typeof fetch` | Custom `fetch` implementation (defaults to `globalThis.fetch`) |
|
|
137
|
+
| `retry` | `{ maxRetries?: number, retryOn?: number[], baseDelayMs?: number, maxDelayMs?: number } \| false` | Transient-failure retry policy. Default retries `429`/`503` twice with exponential backoff, honoring `Retry-After`. Pass `false` to disable. See [Making Requests](./03-making-requests.md#retries-and-rate-limiting) |
|
|
138
|
+
| `validate` | `boolean` | When `true`, validate each request against the schema before sending and throw `ZeyosValidationError` on problems (default: `false`). See [Making Requests](./03-making-requests.md#schema-introspection-and-validation) |
|
|
139
|
+
|
|
140
|
+
## Next Steps
|
|
141
|
+
|
|
142
|
+
- **[Application Developers](../05-tutorials/00-application-developers.md)** -- choose the browser or server-side integration path
|
|
143
|
+
- **[Authentication](./02-authentication.md)** -- learn about session mode, OAuth 2.0 flows, and token management
|
|
144
|
+
- **[Making Requests](./03-making-requests.md)** -- explore CRUD operations, filtering, sorting, pagination, and error handling
|
|
145
|
+
- **[Practical Guide](./04-practical-guide.md)** -- real-world patterns and gotchas discovered during implementation
|
|
146
|
+
- **[Sample Application](../04-sample-apps/01-kanban.md)** -- run the included Kanban board demo to see the client in action
|
|
@@ -0,0 +1,287 @@
|
|
|
1
|
+
---
|
|
2
|
+
sidebar_label: Authentication
|
|
3
|
+
---
|
|
4
|
+
|
|
5
|
+
# Authentication
|
|
6
|
+
|
|
7
|
+
The ZeyOS client supports multiple authentication strategies that can be selected via the `auth.mode` configuration option. The client determines how to authenticate each request based on the chosen mode and the security requirements of the target API operation.
|
|
8
|
+
|
|
9
|
+
## Auth Modes
|
|
10
|
+
|
|
11
|
+
| Mode | Behavior |
|
|
12
|
+
|------|----------|
|
|
13
|
+
| `auto` (default) | Tries bearer token first, attempts token refresh on 401, then falls back to session cookies |
|
|
14
|
+
| `oauth` | Bearer token only; uses access tokens from the configured token store |
|
|
15
|
+
| `session` | Session cookies only; relies on browser session or an explicit cookie value |
|
|
16
|
+
| `none` | No authentication; requests are sent without any credentials |
|
|
17
|
+
|
|
18
|
+
## Session Mode
|
|
19
|
+
|
|
20
|
+
Session mode is the simplest option when the user is already logged into ZeyOS in the same browser. The client sends requests with `credentials: 'include'`, allowing the browser to attach the existing session cookie automatically.
|
|
21
|
+
|
|
22
|
+
```js
|
|
23
|
+
import { createZeyosClient } from '@zeyos/client';
|
|
24
|
+
|
|
25
|
+
const client = createZeyosClient({
|
|
26
|
+
platform: 'https://cloud.zeyos.com/demo/',
|
|
27
|
+
auth: {
|
|
28
|
+
mode: 'session',
|
|
29
|
+
session: { enabled: true, credentials: 'include' },
|
|
30
|
+
},
|
|
31
|
+
});
|
|
32
|
+
|
|
33
|
+
// Requests use the browser's session cookie
|
|
34
|
+
const tickets = await client.api.listTickets({ limit: 10 });
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
:::tip When to use session mode
|
|
38
|
+
Session mode is ideal for apps embedded inside the ZeyOS platform, browser extensions, or any scenario where the user has already authenticated with ZeyOS in the same browser. No tokens need to be stored or managed -- the browser handles everything.
|
|
39
|
+
:::
|
|
40
|
+
|
|
41
|
+
## Token Mode
|
|
42
|
+
|
|
43
|
+
For standalone applications, server-side scripts, or situations where you have pre-obtained tokens, use OAuth mode with a token store.
|
|
44
|
+
|
|
45
|
+
```js
|
|
46
|
+
import { createZeyosClient, MemoryTokenStore } from '@zeyos/client';
|
|
47
|
+
|
|
48
|
+
const tokenStore = new MemoryTokenStore({
|
|
49
|
+
accessToken: 'your-access-token',
|
|
50
|
+
refreshToken: 'your-refresh-token',
|
|
51
|
+
});
|
|
52
|
+
|
|
53
|
+
const client = createZeyosClient({
|
|
54
|
+
platform: 'https://cloud.zeyos.com/demo/',
|
|
55
|
+
auth: {
|
|
56
|
+
mode: 'oauth',
|
|
57
|
+
oauth: { tokenStore },
|
|
58
|
+
},
|
|
59
|
+
});
|
|
60
|
+
|
|
61
|
+
// Requests use the bearer token from the store
|
|
62
|
+
const accounts = await client.api.listAccounts({ limit: 25 });
|
|
63
|
+
```
|
|
64
|
+
|
|
65
|
+
This is the safest default when you already have a valid access token. When `autoRefresh` is enabled and the token has expired or a bearer request receives a 401 response, the client uses the refresh token to obtain a new access token. This requires `clientId` and `clientSecret` to be configured:
|
|
66
|
+
|
|
67
|
+
```js
|
|
68
|
+
const client = createZeyosClient({
|
|
69
|
+
platform: 'https://cloud.zeyos.com/demo/',
|
|
70
|
+
auth: {
|
|
71
|
+
mode: 'oauth',
|
|
72
|
+
oauth: {
|
|
73
|
+
tokenStore,
|
|
74
|
+
autoRefresh: true,
|
|
75
|
+
clientId: 'your-client-id',
|
|
76
|
+
clientSecret: 'your-client-secret',
|
|
77
|
+
},
|
|
78
|
+
},
|
|
79
|
+
});
|
|
80
|
+
```
|
|
81
|
+
|
|
82
|
+
## Token Store
|
|
83
|
+
|
|
84
|
+
The built-in `MemoryTokenStore` keeps tokens in memory. Tokens are lost when the process exits or the page is refreshed.
|
|
85
|
+
|
|
86
|
+
For persistent storage, implement a custom token store with `get()` and `set()` methods:
|
|
87
|
+
|
|
88
|
+
```js
|
|
89
|
+
class LocalStorageTokenStore {
|
|
90
|
+
async get() {
|
|
91
|
+
const raw = localStorage.getItem('zeyos_tokens');
|
|
92
|
+
return raw ? JSON.parse(raw) : null;
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
async set(tokenSet) {
|
|
96
|
+
if (tokenSet) {
|
|
97
|
+
localStorage.setItem('zeyos_tokens', JSON.stringify(tokenSet));
|
|
98
|
+
} else {
|
|
99
|
+
localStorage.removeItem('zeyos_tokens');
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
const client = createZeyosClient({
|
|
105
|
+
platform: 'https://cloud.zeyos.com/demo/',
|
|
106
|
+
auth: {
|
|
107
|
+
mode: 'oauth',
|
|
108
|
+
oauth: {
|
|
109
|
+
tokenStore: new LocalStorageTokenStore(),
|
|
110
|
+
},
|
|
111
|
+
},
|
|
112
|
+
});
|
|
113
|
+
```
|
|
114
|
+
|
|
115
|
+
If you want `autoRefresh: true`, add `clientId` and `clientSecret` in a trusted environment. For browser-only apps, prefer session mode or a backend-assisted token flow rather than embedding a client secret in shipped code.
|
|
116
|
+
|
|
117
|
+
A token set object contains the following fields:
|
|
118
|
+
|
|
119
|
+
| Field | Type | Description |
|
|
120
|
+
|-------|------|-------------|
|
|
121
|
+
| `accessToken` | `string` | The OAuth 2.0 access token |
|
|
122
|
+
| `refreshToken` | `string \| null` | The refresh token (if issued) |
|
|
123
|
+
| `tokenType` | `string` | Token type, typically `'Bearer'` |
|
|
124
|
+
| `expiresIn` | `number \| null` | Token lifetime in seconds from issuance |
|
|
125
|
+
| `expiresAt` | `number \| null` | Absolute expiry as a Unix timestamp (seconds) |
|
|
126
|
+
| `obtainedAt` | `number` | Unix timestamp when the token was obtained |
|
|
127
|
+
| `refreshTokenExpiresIn` | `number \| null` | Refresh token lifetime in seconds |
|
|
128
|
+
| `refreshTokenExpiresAt` | `number \| null` | Refresh token absolute expiry (Unix timestamp) |
|
|
129
|
+
|
|
130
|
+
### Token Set Helpers
|
|
131
|
+
|
|
132
|
+
Two helpers are exported for working with token sets directly — handy when persisting and re-hydrating tokens:
|
|
133
|
+
|
|
134
|
+
- **`normalizeTokenSet(input)`** — normalize a partial token set into the shape above, tolerating both camelCase and snake_case fields (`access_token`, `expires_in`, …). Returns `null` if the input has neither an access nor a refresh token.
|
|
135
|
+
- **`tokenResponseToTokenSet(response)`** — convert a raw OAuth 2.0 token-endpoint response into a normalized token set (an alias of `normalizeTokenSet`).
|
|
136
|
+
|
|
137
|
+
```js
|
|
138
|
+
import { normalizeTokenSet } from '@zeyos/client';
|
|
139
|
+
|
|
140
|
+
const stored = JSON.parse(localStorage.getItem('zeyos_tokens') ?? 'null');
|
|
141
|
+
const tokenSet = normalizeTokenSet(stored); // tolerant of snake_case, returns null if empty
|
|
142
|
+
```
|
|
143
|
+
|
|
144
|
+
## OAuth 2.0 Flow
|
|
145
|
+
|
|
146
|
+
For server-side or other trusted applications that can safely hold OAuth client credentials, use the standard OAuth 2.0 authorization code flow:
|
|
147
|
+
|
|
148
|
+
```js
|
|
149
|
+
import { createZeyosClient, MemoryTokenStore } from '@zeyos/client';
|
|
150
|
+
|
|
151
|
+
const tokenStore = new MemoryTokenStore();
|
|
152
|
+
|
|
153
|
+
const client = createZeyosClient({
|
|
154
|
+
platform: 'https://cloud.zeyos.com/demo/',
|
|
155
|
+
auth: {
|
|
156
|
+
mode: 'oauth',
|
|
157
|
+
oauth: {
|
|
158
|
+
tokenStore,
|
|
159
|
+
clientId: 'your-client-id',
|
|
160
|
+
clientSecret: 'your-client-secret',
|
|
161
|
+
},
|
|
162
|
+
},
|
|
163
|
+
});
|
|
164
|
+
|
|
165
|
+
// 1. Build the authorization URL and redirect the user
|
|
166
|
+
const url = client.oauth2.buildAuthorizationUrl({
|
|
167
|
+
redirectUri: 'https://myapp.com/callback',
|
|
168
|
+
state: crypto.randomUUID(),
|
|
169
|
+
});
|
|
170
|
+
|
|
171
|
+
// 2. After the user authorizes, exchange the code for tokens
|
|
172
|
+
const tokenSet = await client.oauth2.exchangeAuthorizationCode({
|
|
173
|
+
code: 'authorization-code-from-callback',
|
|
174
|
+
redirectUri: 'https://myapp.com/callback',
|
|
175
|
+
});
|
|
176
|
+
|
|
177
|
+
// 3. Tokens are automatically stored in the tokenStore
|
|
178
|
+
// All subsequent API calls use the new tokens
|
|
179
|
+
const user = await client.api.listAccounts({ limit: 1 });
|
|
180
|
+
```
|
|
181
|
+
|
|
182
|
+
You can also parse the callback URL to extract the authorization code and detect errors:
|
|
183
|
+
|
|
184
|
+
```js
|
|
185
|
+
const callback = client.oauth2.parseAuthorizationCallback(
|
|
186
|
+
'https://myapp.com/callback?code=abc123&state=xyz'
|
|
187
|
+
);
|
|
188
|
+
|
|
189
|
+
if (callback.isError) {
|
|
190
|
+
console.error(callback.error, callback.errorDescription);
|
|
191
|
+
} else {
|
|
192
|
+
const tokenSet = await client.oauth2.exchangeAuthorizationCode({
|
|
193
|
+
code: callback.code,
|
|
194
|
+
});
|
|
195
|
+
}
|
|
196
|
+
```
|
|
197
|
+
|
|
198
|
+
:::warning
|
|
199
|
+
The current OAuth helper expects `clientSecret` for authorization-code exchange and token refresh. Do not run that flow directly in shipped browser-only code. Use session mode in the browser or move the code exchange and refresh logic to a backend.
|
|
200
|
+
:::
|
|
201
|
+
|
|
202
|
+
## Token Operations
|
|
203
|
+
|
|
204
|
+
The `client.oauth2` namespace provides methods for managing tokens throughout their lifecycle:
|
|
205
|
+
|
|
206
|
+
```js
|
|
207
|
+
// Refresh the current access token
|
|
208
|
+
const newTokenSet = await client.oauth2.refreshToken();
|
|
209
|
+
|
|
210
|
+
// Revoke a token (access or refresh)
|
|
211
|
+
await client.oauth2.revokeToken({ token: 'token-to-revoke' });
|
|
212
|
+
|
|
213
|
+
// Introspect a token to check its validity and metadata
|
|
214
|
+
const info = await client.oauth2.introspectToken({ token: 'token-to-check' });
|
|
215
|
+
```
|
|
216
|
+
|
|
217
|
+
You can also manage the token set directly through the `client.auth` interface:
|
|
218
|
+
|
|
219
|
+
```js
|
|
220
|
+
// Read the current token set
|
|
221
|
+
const tokenSet = await client.auth.getTokenSet();
|
|
222
|
+
|
|
223
|
+
// Replace the stored token set
|
|
224
|
+
await client.auth.setTokenSet({
|
|
225
|
+
accessToken: 'new-access-token',
|
|
226
|
+
refreshToken: 'new-refresh-token',
|
|
227
|
+
});
|
|
228
|
+
|
|
229
|
+
// Clear all stored tokens
|
|
230
|
+
await client.auth.clearTokenSet();
|
|
231
|
+
```
|
|
232
|
+
|
|
233
|
+
## Auto Mode
|
|
234
|
+
|
|
235
|
+
The default `auto` mode implements an intelligent fallback chain:
|
|
236
|
+
|
|
237
|
+
1. **Bearer token** -- if the token store contains an access token, use it
|
|
238
|
+
2. **Token refresh** -- if the stored token is expired or the bearer request returns 401 and a refresh token is available (with `clientId`/`clientSecret`), refresh the access token
|
|
239
|
+
3. **Session fallback** -- if bearer authentication is unavailable or fails, fall back to session cookies (when `session.enabled` is `true`)
|
|
240
|
+
|
|
241
|
+
This makes `auto` mode the most flexible option. It works seamlessly when tokens are available and gracefully degrades to session authentication when they are not.
|
|
242
|
+
|
|
243
|
+
```js
|
|
244
|
+
const client = createZeyosClient({
|
|
245
|
+
platform: 'https://cloud.zeyos.com/demo/',
|
|
246
|
+
auth: {
|
|
247
|
+
mode: 'auto', // this is the default
|
|
248
|
+
oauth: {
|
|
249
|
+
tokenStore,
|
|
250
|
+
clientId: 'your-client-id',
|
|
251
|
+
clientSecret: 'your-client-secret',
|
|
252
|
+
autoRefresh: true,
|
|
253
|
+
},
|
|
254
|
+
session: { enabled: true, credentials: 'include' },
|
|
255
|
+
},
|
|
256
|
+
});
|
|
257
|
+
```
|
|
258
|
+
|
|
259
|
+
:::warning
|
|
260
|
+
Never embed `clientSecret` in browser-facing JavaScript for production applications. Client secrets should only be used in server-side code or trusted environments. For browser-only apps, use session mode or a backend proxy that handles token exchange.
|
|
261
|
+
:::
|
|
262
|
+
|
|
263
|
+
## Legacy Authentication (`client.legacyAuth`)
|
|
264
|
+
|
|
265
|
+
The `client.legacyAuth` namespace exposes the ZeyOS legacy session authentication API. These operations target a separate endpoint (`/{INSTANCE}/auth/v1/`) and are primarily used by ZeyOS platform apps that manage session lifecycle directly rather than through OAuth 2.0.
|
|
266
|
+
|
|
267
|
+
| Method | Description |
|
|
268
|
+
|--------|-------------|
|
|
269
|
+
| `client.legacyAuth.login(input)` | Start a session using username and password credentials |
|
|
270
|
+
| `client.legacyAuth.logout()` | Terminate the current session |
|
|
271
|
+
| `client.legacyAuth.verify()` | Check whether the current session is still valid (HEAD request) |
|
|
272
|
+
| `client.legacyAuth.getUserInfo()` | Retrieve information about the currently authenticated user |
|
|
273
|
+
|
|
274
|
+
```js
|
|
275
|
+
// Verify current session validity
|
|
276
|
+
await client.legacyAuth.verify();
|
|
277
|
+
|
|
278
|
+
// Get info about the logged-in user
|
|
279
|
+
const userInfo = await client.legacyAuth.getUserInfo();
|
|
280
|
+
|
|
281
|
+
// Log out
|
|
282
|
+
await client.legacyAuth.logout();
|
|
283
|
+
```
|
|
284
|
+
|
|
285
|
+
:::info
|
|
286
|
+
For most integrations, prefer OAuth 2.0 (via `client.oauth2`) or session cookie mode (via `auth.mode: 'session'`). The `legacyAuth` API is primarily intended for internal ZeyOS platform use and scripts that run within an already-authenticated ZeyOS session.
|
|
287
|
+
:::
|