@softr/sdk 0.0.92-emailotc.0 → 0.0.93-alpha.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/dist/agent/agent-fns.d.ts +30 -0
- package/dist/agent/agent-fns.js +215 -0
- package/dist/agent/use-agent-chat.d.ts +106 -0
- package/dist/agent/use-agent-chat.js +486 -0
- package/dist/app-identity.js +25 -0
- package/dist/auth/isomorphic.d.ts +1 -1
- package/dist/auth/isomorphic.js +2 -0
- package/dist/auth/methods/password.d.ts +1 -4
- package/dist/auth/methods/password.js +1 -6
- package/dist/auth/platform.js +0 -25
- package/dist/auth/server.d.ts +0 -3
- package/dist/auth/server.js +1 -4
- package/dist/datasource/record.js +12 -3
- package/dist/default-error-overlay.d.ts +2 -2
- package/dist/formatting.d.ts +3 -3
- package/dist/index.d.ts +3 -1
- package/dist/index.js +3 -1
- package/dist/mcp.d.ts +17 -4
- package/dist/mcp.js +61 -18
- package/dist/package.js +1 -1
- package/dist/pwa.d.ts +2 -2
- package/package.json +10 -33
- package/skills/softr-sdk/SKILL.md +5 -1
- package/skills/softr-sdk/agent-chat/SKILL.md +110 -0
- package/skills/softr-sdk/ai/SKILL.md +1 -1
- package/skills/softr-sdk/auth/SKILL.md +3 -31
- package/skills/softr-sdk/charts-and-metrics/SKILL.md +1 -1
- package/skills/softr-sdk/current-user/SKILL.md +1 -1
- package/skills/softr-sdk/file-uploads/SKILL.md +1 -1
- package/skills/softr-sdk/formatting/SKILL.md +1 -1
- package/skills/softr-sdk/integrations/SKILL.md +1 -1
- package/skills/softr-sdk/mcp/SKILL.md +16 -1
- package/skills/softr-sdk/pwa/SKILL.md +1 -1
- package/skills/softr-sdk/record-mutations/SKILL.md +1 -1
- package/skills/softr-sdk/record-queries/SKILL.md +1 -1
- package/skills/softr-sdk/region-visibility/SKILL.md +1 -1
- package/skills/softr-sdk/routes-and-visibility/SKILL.md +4 -4
- package/skills/softr-sdk/workflows/SKILL.md +1 -1
- package/dist/auth/methods/emailCode2fa.d.ts +0 -34
- package/dist/auth/methods/emailCode2fa.js +0 -71
|
@@ -9,7 +9,7 @@ description: >-
|
|
|
9
9
|
metadata:
|
|
10
10
|
type: sub-skill
|
|
11
11
|
library: softr-sdk
|
|
12
|
-
library_version: 0.0.
|
|
12
|
+
library_version: 0.0.93-alpha.0
|
|
13
13
|
---
|
|
14
14
|
|
|
15
15
|
**Boundary.** `ds` lives on `@softr/sdk/server` and runs only inside a `createServerFn` handler or a server-side route hook — importing it into a component fails the build. `defineQuery` and every type come from `@softr/sdk` and can be imported anywhere.
|
|
@@ -7,7 +7,7 @@ description: >-
|
|
|
7
7
|
metadata:
|
|
8
8
|
type: sub-skill
|
|
9
9
|
library: softr-sdk
|
|
10
|
-
library_version: 0.0.
|
|
10
|
+
library_version: 0.0.93-alpha.0
|
|
11
11
|
---
|
|
12
12
|
|
|
13
13
|
**Boundary.** `upload` lives on `@softr/sdk/server` and runs inside server functions. `useFileUpload` and `FileItem` live on `@softr/sdk` and run in components. `FileAttachment` comes from `@softr/sdk` and can be imported anywhere.
|
|
@@ -7,7 +7,7 @@ description: >-
|
|
|
7
7
|
metadata:
|
|
8
8
|
type: sub-skill
|
|
9
9
|
library: softr-sdk
|
|
10
|
-
library_version: 0.0.
|
|
10
|
+
library_version: 0.0.93-alpha.0
|
|
11
11
|
---
|
|
12
12
|
|
|
13
13
|
**Boundary.** `integration` lives on `@softr/sdk/server` and runs only inside a `createServerFn` handler — importing it into a component fails the build. `defineIntegration` and every type come from `@softr/sdk` and can be imported anywhere.
|
|
@@ -9,7 +9,7 @@ description: >-
|
|
|
9
9
|
metadata:
|
|
10
10
|
type: sub-skill
|
|
11
11
|
library: softr-sdk
|
|
12
|
-
library_version: 0.0.
|
|
12
|
+
library_version: 0.0.93-alpha.0
|
|
13
13
|
---
|
|
14
14
|
|
|
15
15
|
**Boundary.** `softrMcpMiddleware` lives on `@softr/sdk` and is registered once, in `src/start.ts`. The actions you hand it are the same `defineQuery` / `defineMutation` values the app's own pages use — declared wherever they already live, not duplicated for MCP.
|
|
@@ -53,10 +53,25 @@ The list is the whole tool surface. Write it out:
|
|
|
53
53
|
|
|
54
54
|
- An action you leave out is invisible to the assistant, even where the app's pages use it freely.
|
|
55
55
|
- An action you list still obeys its own `permissions`. Listing it does not widen who may run it — the assistant runs as whoever signed in, with that user's groups.
|
|
56
|
+
- The assistant calls the action directly and skips server functions, so a row filter written in one does not apply. A listed read returns every row the user's data restrictions allow, and a listed update or delete takes any id that passes them. On a table whose rows belong to people, list an action only once a data restriction scopes the table to the user's own rows.
|
|
57
|
+
- A create on a table whose rows belong to a person gets its owner from `owner`, never from the assistant. See below.
|
|
56
58
|
- Two actions with the same `id` throw at startup. So does anything that is not a `defineQuery` or `defineMutation` value.
|
|
57
59
|
|
|
58
60
|
Reads first. Add a write only when the user asked for one, and name it back to them.
|
|
59
61
|
|
|
62
|
+
## The owner of a person's record
|
|
63
|
+
|
|
64
|
+
The assistant knows the caller's login, not their row in the people table. Left to fill an owner link, it writes the login id, which shows as a stray name, or anyone's row it likes. `owner` takes the field out of the tool and fills it with the caller's own row, found the way `auth.currentUserRow` finds it:
|
|
65
|
+
|
|
66
|
+
```ts
|
|
67
|
+
softrMcpMiddleware({
|
|
68
|
+
actions: [listRequests, requestTimeOff],
|
|
69
|
+
owner: { users: usersQuery, email: 'email', fields: { requestTimeOff: 'employee' } },
|
|
70
|
+
})
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
`fields` maps each create or update action id to its owner link. A caller with no row in the people table is refused, and nothing is created. On an update the field is only taken out, so nobody moves a record to someone else.
|
|
74
|
+
|
|
60
75
|
## The login round trip
|
|
61
76
|
|
|
62
77
|
Connecting starts with an approval page the app serves. Most people hit it signed out, and that page cannot sign anyone in. It sends them to the login page named in `softr.json` (`auth.routes.login.path`), with the approval page in the search param named there (`auth.routes.login.redirectParam`).
|
|
@@ -8,7 +8,7 @@ description: >-
|
|
|
8
8
|
metadata:
|
|
9
9
|
type: sub-skill
|
|
10
10
|
library: softr-sdk
|
|
11
|
-
library_version: 0.0.
|
|
11
|
+
library_version: 0.0.93-alpha.0
|
|
12
12
|
---
|
|
13
13
|
|
|
14
14
|
**Boundary.** `ds` lives on `@softr/sdk/server` and runs only inside a `createServerFn` handler — importing it into a component fails the build. `defineMutation` and every type come from `@softr/sdk` and can be imported anywhere.
|
|
@@ -9,7 +9,7 @@ description: >-
|
|
|
9
9
|
metadata:
|
|
10
10
|
type: sub-skill
|
|
11
11
|
library: softr-sdk
|
|
12
|
-
library_version: 0.0.
|
|
12
|
+
library_version: 0.0.93-alpha.0
|
|
13
13
|
---
|
|
14
14
|
|
|
15
15
|
**Boundary.** `ds` lives on `@softr/sdk/server` and runs only inside a `createServerFn` handler or a server-side route hook — importing it into a component fails the build. The same holds for any helper that calls `ds`: declare it inside the handler. A function at module level that calls `ds` keeps the server-only import in the browser bundle, and every page stops loading until it moves. `defineQuery` and every type come from `@softr/sdk` and can be imported anywhere.
|
|
@@ -3,13 +3,13 @@ name: routes-and-visibility
|
|
|
3
3
|
description: >-
|
|
4
4
|
Add a route file and declare its settings: definePage with its visibility
|
|
5
5
|
(LOGGED_IN_USERS, NON_LOGGED_IN_USERS and customGroups) and its title,
|
|
6
|
-
guardRoute or assertRouteAccess in beforeLoad, pageHead in head,
|
|
7
|
-
|
|
8
|
-
|
|
6
|
+
guardRoute or assertRouteAccess in beforeLoad, pageHead in head, isAuthorized
|
|
7
|
+
and checkAccess anywhere, rendering an access error, and the lint rules that
|
|
8
|
+
require the declaration.
|
|
9
9
|
metadata:
|
|
10
10
|
type: sub-skill
|
|
11
11
|
library: softr-sdk
|
|
12
|
-
library_version: 0.0.
|
|
12
|
+
library_version: 0.0.93-alpha.0
|
|
13
13
|
---
|
|
14
14
|
|
|
15
15
|
**Boundary.** `definePage`, `pageHead`, the access functions and the error predicates come from `@softr/sdk` and work anywhere.
|
|
@@ -9,7 +9,7 @@ description: >-
|
|
|
9
9
|
metadata:
|
|
10
10
|
type: sub-skill
|
|
11
11
|
library: softr-sdk
|
|
12
|
-
library_version: 0.0.
|
|
12
|
+
library_version: 0.0.93-alpha.0
|
|
13
13
|
---
|
|
14
14
|
|
|
15
15
|
**Boundary.** `workflow` lives on `@softr/sdk/server` and runs only inside a `createServerFn` handler — importing it into a component fails the build. `defineWorkflow` and every type come from `@softr/sdk` and can be imported anywhere.
|
|
@@ -1,34 +0,0 @@
|
|
|
1
|
-
import { User } from "../user.js";
|
|
2
|
-
import { AuthError, Result } from "./utils.js";
|
|
3
|
-
|
|
4
|
-
//#region src/auth/methods/emailCode2fa.d.ts
|
|
5
|
-
|
|
6
|
-
/**
|
|
7
|
-
* Finishes a sign-in that answered `emailCodeRequired`, with the code emailed
|
|
8
|
-
* to the visitor.
|
|
9
|
-
*
|
|
10
|
-
* A `signedIn` result means the visitor is signed in. An app that also asks for
|
|
11
|
-
* an authenticator app answers `authenticatorRequired` instead, naming the step
|
|
12
|
-
* to send them to next.
|
|
13
|
-
*/
|
|
14
|
-
declare function verifyEmailCode(details: {
|
|
15
|
-
code: string;
|
|
16
|
-
}): Promise<Result<{
|
|
17
|
-
status: "signedIn";
|
|
18
|
-
user: User;
|
|
19
|
-
} | {
|
|
20
|
-
status: "authenticatorRequired";
|
|
21
|
-
/**
|
|
22
|
-
* `verify`: they have an authenticator app and owe a code.
|
|
23
|
-
* `setup`: the app requires one and they have none yet.
|
|
24
|
-
* `setupOptional`: same, except they may skip it instead.
|
|
25
|
-
*/
|
|
26
|
-
step: "verify" | "setup" | "setupOptional";
|
|
27
|
-
}, AuthError>>;
|
|
28
|
-
/**
|
|
29
|
-
* Emails the code for {@link verifyEmailCode} again. Asking again within a
|
|
30
|
-
* short wait sends nothing and still succeeds.
|
|
31
|
-
*/
|
|
32
|
-
declare function resendEmailCode(): Promise<Result<null, AuthError>>;
|
|
33
|
-
//#endregion
|
|
34
|
-
export { resendEmailCode, verifyEmailCode };
|
|
@@ -1,71 +0,0 @@
|
|
|
1
|
-
import { assert, panic } from "../../assertions.js";
|
|
2
|
-
import { writeCookies } from "../../cookies.js";
|
|
3
|
-
import { sessionConfig } from "../config.js";
|
|
4
|
-
import { clearPendingAuth, makePendingAuthCookie, makeSessionDataCookie, makeSessionTokenCookie, readPendingAuthToken } from "../session.js";
|
|
5
|
-
import { makePlatform } from "../platform.js";
|
|
6
|
-
import { authError } from "./utils.js";
|
|
7
|
-
|
|
8
|
-
//#region src/auth/methods/emailCode2fa.ts
|
|
9
|
-
/**
|
|
10
|
-
* Finishes a sign-in that answered `emailCodeRequired`, with the code emailed
|
|
11
|
-
* to the visitor.
|
|
12
|
-
*
|
|
13
|
-
* A `signedIn` result means the visitor is signed in. An app that also asks for
|
|
14
|
-
* an authenticator app answers `authenticatorRequired` instead, naming the step
|
|
15
|
-
* to send them to next.
|
|
16
|
-
*/
|
|
17
|
-
async function verifyEmailCode(details) {
|
|
18
|
-
const result = await makePlatform(sessionConfig().applicationId).emailCodeVerify(readPendingAuthToken(), details.code);
|
|
19
|
-
if (!result.ok) {
|
|
20
|
-
if (result.status === 400 || result.status === 401) return authError("invalidCode", result.message);
|
|
21
|
-
if (result.status === 429) return authError("tooManyAttempts", result.message);
|
|
22
|
-
if (result.status >= 500) panic(`Expected to verify the emailed code, but got ${result.status}: ` + result.message);
|
|
23
|
-
throw new Error(`${result.message}. Check SOFTR_APPLICATION_ID and that the app asks for an emailed code at sign-in.`);
|
|
24
|
-
}
|
|
25
|
-
if (result.data.status === "MFA_REQUIRED") {
|
|
26
|
-
const { mfa } = result.data;
|
|
27
|
-
assert(mfa, "Expected a challenge from verification, but got none");
|
|
28
|
-
writeCookies([makePendingAuthCookie(mfa.challengeToken)]);
|
|
29
|
-
return {
|
|
30
|
-
success: true,
|
|
31
|
-
data: {
|
|
32
|
-
status: "authenticatorRequired",
|
|
33
|
-
step: mfa.action === "VERIFICATION_REQUIRED" ? "verify" : mfa.action === "SETUP_REQUIRED" ? "setup" : "setupOptional"
|
|
34
|
-
}
|
|
35
|
-
};
|
|
36
|
-
}
|
|
37
|
-
const { session } = result.data;
|
|
38
|
-
assert(session, "Expected a session from verification, but got none");
|
|
39
|
-
writeCookies([...makeSessionTokenCookie(session.jwt), makeSessionDataCookie({
|
|
40
|
-
user: session.user,
|
|
41
|
-
permissions: session.permissions
|
|
42
|
-
}, session.jwt)]);
|
|
43
|
-
clearPendingAuth();
|
|
44
|
-
return {
|
|
45
|
-
success: true,
|
|
46
|
-
data: {
|
|
47
|
-
status: "signedIn",
|
|
48
|
-
user: session.user
|
|
49
|
-
}
|
|
50
|
-
};
|
|
51
|
-
}
|
|
52
|
-
/**
|
|
53
|
-
* Emails the code for {@link verifyEmailCode} again. Asking again within a
|
|
54
|
-
* short wait sends nothing and still succeeds.
|
|
55
|
-
*/
|
|
56
|
-
async function resendEmailCode() {
|
|
57
|
-
const result = await makePlatform(sessionConfig().applicationId).emailCodeResend(readPendingAuthToken());
|
|
58
|
-
if (!result.ok) {
|
|
59
|
-
if (result.status === 401) return authError("notAuthenticated", result.message);
|
|
60
|
-
if (result.status === 429) return authError("tooManyAttempts", result.message);
|
|
61
|
-
if (result.status >= 500) panic(`Expected the code to be emailed again, but got ${result.status}: ` + result.message);
|
|
62
|
-
throw new Error(`${result.message}. Check SOFTR_APPLICATION_ID and that the app asks for an emailed code at sign-in.`);
|
|
63
|
-
}
|
|
64
|
-
return {
|
|
65
|
-
success: true,
|
|
66
|
-
data: null
|
|
67
|
-
};
|
|
68
|
-
}
|
|
69
|
-
|
|
70
|
-
//#endregion
|
|
71
|
-
export { resendEmailCode, verifyEmailCode };
|