create-relkit 0.7.2 → 0.7.6
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/create-capabilities.d.ts +34 -0
- package/dist/create-capabilities.d.ts.map +1 -0
- package/dist/create-capabilities.js +137 -0
- package/dist/create-capabilities.js.map +1 -0
- package/dist/create-capabilities.types.d.ts +55 -0
- package/dist/create-capabilities.types.d.ts.map +1 -0
- package/dist/create-capabilities.types.js +2 -0
- package/dist/create-capabilities.types.js.map +1 -0
- package/dist/create-resolver.d.ts.map +1 -1
- package/dist/create-resolver.js +28 -6
- package/dist/create-resolver.js.map +1 -1
- package/dist/domain-artifact.d.ts.map +1 -1
- package/dist/domain-artifact.js +11 -3
- package/dist/domain-artifact.js.map +1 -1
- package/dist/domain-planning.d.ts +5 -0
- package/dist/domain-planning.d.ts.map +1 -1
- package/dist/domain-planning.js +25 -16
- package/dist/domain-planning.js.map +1 -1
- package/dist/generate-deployment-manifest.d.ts +10 -0
- package/dist/generate-deployment-manifest.d.ts.map +1 -0
- package/dist/generate-deployment-manifest.js +56 -0
- package/dist/generate-deployment-manifest.js.map +1 -0
- package/dist/generate-deployment.d.ts +2 -3
- package/dist/generate-deployment.d.ts.map +1 -1
- package/dist/generate-deployment.js +6 -47
- package/dist/generate-deployment.js.map +1 -1
- package/dist/generate-examples.d.ts +11 -0
- package/dist/generate-examples.d.ts.map +1 -0
- package/dist/generate-examples.js +28 -0
- package/dist/generate-examples.js.map +1 -0
- package/dist/generate-files-utilities.d.ts +1 -8
- package/dist/generate-files-utilities.d.ts.map +1 -1
- package/dist/generate-files-utilities.js +5 -19
- package/dist/generate-files-utilities.js.map +1 -1
- package/dist/generate-output.d.ts +2 -1
- package/dist/generate-output.d.ts.map +1 -1
- package/dist/generate-output.js +19 -37
- package/dist/generate-output.js.map +1 -1
- package/dist/generate-output.schemas.d.ts +34 -0
- package/dist/generate-output.schemas.d.ts.map +1 -0
- package/dist/generate-output.schemas.js +33 -0
- package/dist/generate-output.schemas.js.map +1 -0
- package/dist/generate-output.types.d.ts +2 -0
- package/dist/generate-output.types.d.ts.map +1 -1
- package/dist/generate-preparation.d.ts +26 -0
- package/dist/generate-preparation.d.ts.map +1 -0
- package/dist/generate-preparation.js +83 -0
- package/dist/generate-preparation.js.map +1 -0
- package/dist/generate-result.d.ts +34 -0
- package/dist/generate-result.d.ts.map +1 -0
- package/dist/generate-result.js +41 -0
- package/dist/generate-result.js.map +1 -0
- package/dist/generate-stage.d.ts +21 -0
- package/dist/generate-stage.d.ts.map +1 -0
- package/dist/generate-stage.js +52 -0
- package/dist/generate-stage.js.map +1 -0
- package/dist/generate-stage.types.d.ts +11 -0
- package/dist/generate-stage.types.d.ts.map +1 -0
- package/dist/generate-stage.types.js +2 -0
- package/dist/generate-stage.types.js.map +1 -0
- package/dist/generate-workflow.d.ts +10 -7
- package/dist/generate-workflow.d.ts.map +1 -1
- package/dist/generate-workflow.js +22 -101
- package/dist/generate-workflow.js.map +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -1
- package/dist/project-discovery-artifacts.d.ts +15 -0
- package/dist/project-discovery-artifacts.d.ts.map +1 -0
- package/dist/project-discovery-artifacts.js +107 -0
- package/dist/project-discovery-artifacts.js.map +1 -0
- package/dist/project-discovery-artifacts.types.d.ts +22 -0
- package/dist/project-discovery-artifacts.types.d.ts.map +1 -0
- package/dist/project-discovery-artifacts.types.js +2 -0
- package/dist/project-discovery-artifacts.types.js.map +1 -0
- package/dist/project-discovery-facts.d.ts +8 -9
- package/dist/project-discovery-facts.d.ts.map +1 -1
- package/dist/project-discovery-facts.js +29 -135
- package/dist/project-discovery-facts.js.map +1 -1
- package/dist/project-discovery-members.d.ts +16 -0
- package/dist/project-discovery-members.d.ts.map +1 -0
- package/dist/project-discovery-members.js +57 -0
- package/dist/project-discovery-members.js.map +1 -0
- package/dist/project-discovery-types.d.ts +8 -0
- package/dist/project-discovery-types.d.ts.map +1 -1
- package/dist/render-auth-database.d.ts +33 -0
- package/dist/render-auth-database.d.ts.map +1 -0
- package/dist/render-auth-database.js +69 -0
- package/dist/render-auth-database.js.map +1 -0
- package/dist/render-auth-sources.d.ts +8 -2
- package/dist/render-auth-sources.d.ts.map +1 -1
- package/dist/render-auth-sources.js +9 -3
- package/dist/render-auth-sources.js.map +1 -1
- package/dist/render-auth.d.ts +14 -11
- package/dist/render-auth.d.ts.map +1 -1
- package/dist/render-auth.js +41 -108
- package/dist/render-auth.js.map +1 -1
- package/dist/render-database-sources.d.ts +7 -1
- package/dist/render-database-sources.d.ts.map +1 -1
- package/dist/render-database-sources.js +3 -2
- package/dist/render-database-sources.js.map +1 -1
- package/dist/render-database.d.ts +7 -10
- package/dist/render-database.d.ts.map +1 -1
- package/dist/render-database.js +12 -4
- package/dist/render-database.js.map +1 -1
- package/dist/render-database.types.d.ts +15 -0
- package/dist/render-database.types.d.ts.map +1 -0
- package/dist/render-database.types.js +2 -0
- package/dist/render-database.types.js.map +1 -0
- package/dist/render-route-sources.d.ts +3 -1
- package/dist/render-route-sources.d.ts.map +1 -1
- package/dist/render-route-sources.js +4 -2
- package/dist/render-route-sources.js.map +1 -1
- package/dist/render-routes.d.ts +1 -0
- package/dist/render-routes.d.ts.map +1 -1
- package/dist/render-routes.js +2 -1
- package/dist/render-routes.js.map +1 -1
- package/dist/render-service-members.d.ts +32 -0
- package/dist/render-service-members.d.ts.map +1 -0
- package/dist/render-service-members.js +61 -0
- package/dist/render-service-members.js.map +1 -0
- package/dist/render-service-requests.d.ts +35 -0
- package/dist/render-service-requests.d.ts.map +1 -0
- package/dist/render-service-requests.js +62 -0
- package/dist/render-service-requests.js.map +1 -0
- package/dist/render-service-support.d.ts +37 -0
- package/dist/render-service-support.d.ts.map +1 -0
- package/dist/render-service-support.js +74 -0
- package/dist/render-service-support.js.map +1 -0
- package/dist/render-service.d.ts +16 -13
- package/dist/render-service.d.ts.map +1 -1
- package/dist/render-service.js +33 -149
- package/dist/render-service.js.map +1 -1
- package/dist/render-service.types.d.ts +13 -0
- package/dist/render-service.types.d.ts.map +1 -0
- package/dist/render-service.types.js +2 -0
- package/dist/render-service.types.js.map +1 -0
- package/dist/scaffold-layout.d.ts +10 -0
- package/dist/scaffold-layout.d.ts.map +1 -0
- package/dist/scaffold-layout.js +29 -0
- package/dist/scaffold-layout.js.map +1 -0
- package/dist/templates/default/README.md +1 -1
- package/dist/templates/default/v1/agent/.agents/skills/relkit/SKILL.md +48 -0
- package/dist/templates/default/v1/agent/.agents/skills/relkit/references/agent-apis.md +59 -0
- package/dist/templates/default/v1/agent/.agents/skills/relkit/references/cli.md +63 -0
- package/dist/templates/default/v1/agent/.agents/skills/relkit/references/config-environments.md +96 -0
- package/dist/templates/default/v1/agent/.agents/skills/relkit/references/data-apis.md +74 -0
- package/dist/templates/default/v1/agent/.agents/skills/relkit/references/domain-apis.md +92 -0
- package/dist/templates/default/v1/agent/.agents/skills/relkit/references/http-apis.md +70 -0
- package/dist/templates/default/v1/agent/.agents/skills/relkit/references/jobs-apis.md +49 -0
- package/dist/templates/default/v1/agent/.agents/skills/relkit/references/layout-migration.md +35 -0
- package/dist/templates/default/v1/agent/.agents/skills/relkit/references/observability-apis.md +53 -0
- package/dist/templates/default/v1/agent/.agents/skills/relkit/references/realtime-apis.md +98 -0
- package/dist/templates/default/v1/agent/.agents/skills/relkit/references/streaming-apis.md +75 -0
- package/dist/templates/default/v1/agent/.agents/skills/relkit/references/testing-apis.md +71 -0
- package/dist/templates/default/v1/agent/README.md +9 -0
- package/dist/templates/default/v1/agent/package.json +5 -4
- package/dist/templates/default/v1/agent/src/routes/hello/route.ts +2 -1
- package/dist/templates/default/v1/agent/src/{hello → services/hello}/agents/assistant.agent.ts +3 -2
- package/dist/templates/default/v1/agent/src/{hello → services/hello}/agents/review.agent.ts +1 -0
- package/dist/templates/default/v1/agent/src/{hello → services/hello}/functions/hello.function.ts +7 -0
- package/dist/templates/default/v1/agent/src/services/hello/service.ts +5 -0
- package/dist/templates/default/v1/agent/src/{hello → services/hello}/tools/lookup.tool.ts +2 -1
- package/dist/templates/default/v1/agent/tests/fixtures/lookup.tool.ts +2 -1
- package/dist/templates/default/v1/agent/tests/fixtures/mcp-options.ts +2 -1
- package/dist/templates/default/v1/agent/tests/unit/assistant.agent.test.ts +3 -2
- package/dist/templates/default/v1/agent/tests/unit/hello.function.test.ts +2 -1
- package/dist/templates/default/v1/agent/tests/unit/lookup.tool.test.ts +2 -1
- package/dist/templates/default/v1/agent/tests/unit/review.agent.test.ts +2 -1
- package/dist/templates/default/v1/agent/tsconfig.json +1 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/SKILL.md +48 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/references/agent-apis.md +59 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/references/cli.md +63 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/references/config-environments.md +96 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/references/data-apis.md +74 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/references/domain-apis.md +92 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/references/http-apis.md +70 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/references/jobs-apis.md +49 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/references/layout-migration.md +35 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/references/observability-apis.md +53 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/references/realtime-apis.md +98 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/references/streaming-apis.md +75 -0
- package/dist/templates/default/v1/api/.agents/skills/relkit/references/testing-apis.md +71 -0
- package/dist/templates/default/v1/api/README.md +10 -0
- package/dist/templates/default/v1/api/package.json +4 -3
- package/dist/templates/default/v1/api/src/routes/echo/route.ts +2 -1
- package/dist/templates/default/v1/api/src/routes/hello/route.ts +2 -1
- package/dist/templates/default/v1/api/src/routes/orders/route.ts +2 -1
- package/dist/templates/default/v1/api/src/{echo → services/echo}/functions/echo.function.ts +1 -0
- package/dist/templates/default/v1/api/src/services/echo/service.ts +5 -0
- package/dist/templates/default/v1/api/src/{hello → services/hello}/functions/hello.function.ts +7 -0
- package/dist/templates/default/v1/api/src/services/hello/service.ts +5 -0
- package/dist/templates/default/v1/api/src/{orders → services/orders}/functions/create-order.function.ts +2 -1
- package/dist/templates/default/v1/api/src/{orders → services/orders}/functions/price-order.function.ts +1 -0
- package/dist/templates/default/v1/api/src/services/orders/service.ts +8 -0
- package/dist/templates/default/v1/api/tests/unit/echo.function.test.ts +2 -1
- package/dist/templates/default/v1/api/tests/unit/hello.function.test.ts +2 -1
- package/dist/templates/default/v1/api/tests/unit/orders.function.test.ts +2 -1
- package/dist/templates/default/v1/api/tsconfig.json +1 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/SKILL.md +48 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/references/agent-apis.md +59 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/references/cli.md +63 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/references/config-environments.md +96 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/references/data-apis.md +74 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/references/domain-apis.md +92 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/references/http-apis.md +70 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/references/jobs-apis.md +49 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/references/layout-migration.md +35 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/references/observability-apis.md +53 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/references/realtime-apis.md +98 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/references/streaming-apis.md +75 -0
- package/dist/templates/default/v1/fullstack/.agents/skills/relkit/references/testing-apis.md +71 -0
- package/dist/templates/default/v1/fullstack/README.md +16 -0
- package/dist/templates/default/v1/fullstack/package.json +7 -6
- package/dist/templates/default/v1/fullstack/src/routes/hello/route.ts +2 -1
- package/dist/templates/default/v1/fullstack/src/{hello → services/hello}/agents/assistant.agent.ts +3 -2
- package/dist/templates/default/v1/fullstack/src/{hello → services/hello}/agents/review.agent.ts +1 -0
- package/dist/templates/default/v1/fullstack/src/{hello → services/hello}/functions/hello.function.ts +1 -0
- package/dist/templates/default/v1/fullstack/src/services/hello/service.ts +5 -0
- package/dist/templates/default/v1/fullstack/src/{hello → services/hello}/tools/lookup.tool.ts +2 -1
- package/dist/templates/default/v1/fullstack/tests/unit/assistant.agent.test.ts +3 -2
- package/dist/templates/default/v1/fullstack/tests/unit/hello.function.test.ts +2 -1
- package/dist/templates/default/v1/fullstack/tests/unit/review.agent.test.ts +2 -1
- package/dist/templates/default/v1/fullstack/tsconfig.json +1 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/SKILL.md +48 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/references/agent-apis.md +59 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/references/cli.md +63 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/references/config-environments.md +96 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/references/data-apis.md +74 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/references/domain-apis.md +92 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/references/http-apis.md +70 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/references/jobs-apis.md +49 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/references/layout-migration.md +35 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/references/observability-apis.md +53 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/references/realtime-apis.md +98 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/references/streaming-apis.md +75 -0
- package/dist/templates/default/v1/minimal/.agents/skills/relkit/references/testing-apis.md +71 -0
- package/dist/templates/default/v1/minimal/README.md +10 -0
- package/dist/templates/default/v1/minimal/package.json +4 -3
- package/dist/templates/default/v1/minimal/src/routes/hello/route.ts +2 -1
- package/dist/templates/default/v1/minimal/src/{hello → services/hello}/functions/hello.function.ts +7 -0
- package/dist/templates/default/v1/minimal/src/services/hello/service.ts +5 -0
- package/dist/templates/default/v1/minimal/tests/unit/hello.function.test.ts +2 -1
- package/dist/templates/default/v1/minimal/tsconfig.json +1 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/SKILL.md +48 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/agent-apis.md +59 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/cli.md +63 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/config-environments.md +96 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/data-apis.md +74 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/domain-apis.md +92 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/http-apis.md +70 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/jobs-apis.md +49 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/layout-migration.md +35 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/observability-apis.md +53 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/realtime-apis.md +98 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/streaming-apis.md +75 -0
- package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/testing-apis.md +71 -0
- package/dist/templates/default/v1/tasks/README.md +8 -1
- package/dist/templates/default/v1/tasks/package.json +4 -3
- package/dist/templates/default/v1/tasks/src/routes/health/route.ts +2 -1
- package/dist/templates/default/v1/tasks/src/{orders → services/orders}/functions/health.function.ts +1 -0
- package/dist/templates/default/v1/tasks/src/{orders → services/orders}/jobs/export-orders.job.ts +2 -1
- package/dist/templates/default/v1/tasks/src/services/orders/service.ts +11 -0
- package/dist/templates/default/v1/tasks/src/{orders → services/orders}/tasks/export-orders.task.ts +1 -0
- package/dist/templates/default/v1/tasks/tests/unit/export-orders.task.test.ts +2 -1
- package/dist/templates/default/v1/tasks/tsconfig.json +2 -0
- package/package.json +3 -3
- package/dist/templates/default/v1/agent/src/hello/service.ts +0 -4
- package/dist/templates/default/v1/api/src/echo/service.ts +0 -4
- package/dist/templates/default/v1/api/src/hello/service.ts +0 -4
- package/dist/templates/default/v1/api/src/orders/service.ts +0 -7
- package/dist/templates/default/v1/fullstack/src/hello/service.ts +0 -4
- package/dist/templates/default/v1/minimal/src/hello/service.ts +0 -4
- package/dist/templates/default/v1/tasks/src/orders/service.ts +0 -10
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
# CLI commands in a generated project
|
|
2
|
+
|
|
3
|
+
These examples use the local binary through `bun run relkit`. The installed CLI's `--help` is authoritative if its version differs from the template.
|
|
4
|
+
|
|
5
|
+
## Service and HTTP scaffolding
|
|
6
|
+
|
|
7
|
+
| Goal | Command |
|
|
8
|
+
| ---------------------------------------------- | ---------------------------------------------------------------------------------------------- |
|
|
9
|
+
| Create a domain with a public example function | `bun run relkit add service Billing` |
|
|
10
|
+
| Select extra domain artifacts | `bun run relkit add service Billing --include function --include error` |
|
|
11
|
+
| Create the full domain bundle | `bun run relkit add service Billing --full` |
|
|
12
|
+
| Add a public callable function | `bun run relkit add function "Send Receipt" --service billing` |
|
|
13
|
+
| Add a standalone GET handler | `bun run relkit add route '/status' --mode route` |
|
|
14
|
+
| Map an existing public member to HTTP | `bun run relkit add route '/billing' --mode service-route --service billing --map GET=example` |
|
|
15
|
+
|
|
16
|
+
`--include` is repeatable and exclusive with `--full`. `--service` selects an existing generic domain; `--create-service` creates it while adding an artifact. Use `--internal` on a function or event that should stay out of the public service API. A service route needs one or more `--map METHOD=member` values in noninteractive use; the member must be a public callable function. Quote paths containing `*` or `?`.
|
|
17
|
+
|
|
18
|
+
## Database and auth
|
|
19
|
+
|
|
20
|
+
| Goal | Command |
|
|
21
|
+
| -------------------------------------------- | ------------------------------------------------------------------------- |
|
|
22
|
+
| Scaffold a SQLite Drizzle service | `bun run relkit add database --orm drizzle --dialect sqlite` |
|
|
23
|
+
| Scaffold Better Auth and its catch-all route | `bun run relkit add auth --adapter better-auth --database-dialect sqlite` |
|
|
24
|
+
|
|
25
|
+
Database `--dialect` and auth `--database-dialect` also accept `postgresql` and `mysql`. Auth's `--base-path` changes the default `/api/auth` mount. The CLI adds dependencies and an environment example as needed, but it does not apply database migrations or populate secrets. Follow the scaffold's reported next steps after reviewing the schema and environment values.
|
|
26
|
+
|
|
27
|
+
## Other add kinds
|
|
28
|
+
|
|
29
|
+
Run `bun run relkit add <kind> --help` for each kind's flags and requirements:
|
|
30
|
+
|
|
31
|
+
| Area | Kinds |
|
|
32
|
+
| --------------- | ---------------------------------------- |
|
|
33
|
+
| Domain behavior | `function`, `task`, `error`, `constants` |
|
|
34
|
+
| Events and work | `event`, `event-function`, `job` |
|
|
35
|
+
| Providers | `cache`, `bucket` |
|
|
36
|
+
| AI | `tool`, `prompt`, `agent` |
|
|
37
|
+
| HTTP | `middleware`, `transform`, `route` |
|
|
38
|
+
|
|
39
|
+
For example, jobs need a target task, tools need an existing or newly created function, and agents need a prompt or inline instructions. Check the existing service and profile before selecting one. `--no-install` skips installing newly required packages and may skip verification; `--project-root <directory>` targets another app. `bun run relkit --json add ...` disables prompts and emits structured results for automation.
|
|
40
|
+
|
|
41
|
+
There is no `relkit add channel` or `relkit add observability` kind. Author channels with `defineChannel` and configure observability in `defineApp({ telemetry })`; see the [realtime](realtime-apis.md) and [observability](observability-apis.md) references.
|
|
42
|
+
|
|
43
|
+
For streaming responses, scaffold a function and route, then edit the function's output to `streamOf(itemSchema)` and the route's `stream` option; see the [streaming reference](streaming-apis.md).
|
|
44
|
+
|
|
45
|
+
## Inspect and run the app
|
|
46
|
+
|
|
47
|
+
| Goal | Command |
|
|
48
|
+
| --------------------------------------- | ----------------------------------- |
|
|
49
|
+
| Validate the application graph | `bun run check` |
|
|
50
|
+
| Typecheck and test | `bun run typecheck`, `bun run test` |
|
|
51
|
+
| Start app, inspector, and API reference | `bun run dev` |
|
|
52
|
+
| Inspect the graph | `bun run relkit graph print` |
|
|
53
|
+
| Inspect environment value status | `bun run relkit env list` |
|
|
54
|
+
| Validate active environment values | `bun run relkit env check` |
|
|
55
|
+
| Explain one environment declaration | `bun run relkit env explain NAME` |
|
|
56
|
+
| Render a safe environment example | `bun run relkit env example` |
|
|
57
|
+
| Check local prerequisites | `bun run relkit doctor` |
|
|
58
|
+
| Inspect local service status | `bun run relkit local status` |
|
|
59
|
+
| Build or start a built app | `bun run build`, `bun run start` |
|
|
60
|
+
|
|
61
|
+
Use `bun run relkit --help` to discover additional `graph`, `env`, `local`, `jobs`, `client`, and deployment commands. Start Docker-backed local services with `bun run relkit local up --detach` only when the app actually declares and needs them. Deployment commands require a configured deployment target.
|
|
62
|
+
|
|
63
|
+
For optional flat-to-grouped migration, use `bun run relkit migrate layout` for preview, `--write` for validated publication, and `--rollback <receipt>` for guarded restoration. See [layout migration](layout-migration.md). After `--no-install`, install dependencies and run `bun run relkit dev --prepare` before evaluating prepared-start readiness.
|
package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/config-environments.md
ADDED
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
# Application configuration and environments
|
|
2
|
+
|
|
3
|
+
A generated application has two authoring files at its root: `relkit.config.ts` declares topology and runtime policy with `defineApp`, and `src/platform/env.ts` declares application environment values with `defineEnv`. Extend these existing files rather than creating a second application or environment contract.
|
|
4
|
+
|
|
5
|
+
## `defineEnv`: values for handlers
|
|
6
|
+
|
|
7
|
+
In `src/platform/env.ts`:
|
|
8
|
+
|
|
9
|
+
```ts
|
|
10
|
+
import { defineEnv, env } from "@relkit/app/config";
|
|
11
|
+
|
|
12
|
+
export default defineEnv({
|
|
13
|
+
LOG_LEVEL: env.literal("debug", "info", "warn", "error").default("info"),
|
|
14
|
+
DATABASE_PATH: env.string().default(".relkit/app.sqlite"),
|
|
15
|
+
BETTER_AUTH_SECRET: env.secret().requiredIn("production"),
|
|
16
|
+
PUBLIC_ORIGIN: env.url().optional(),
|
|
17
|
+
});
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
Builders include `string`, `secret`, `number`, `boolean`, `port`, `url`, `json`, and `literal(...)`. Use `.default(value)` only for intentional safe defaults, `.optional()` for absent values, `.requiredIn("production")` for environment-specific requirements, and `.description(text)` or `.example(value)` for safe metadata. A URL field resolves to a `URL`, a number field to a number, and a Boolean field to a boolean. Do not declare `PORT` or `RELKIT_ENV`; RELKIT reserves them.
|
|
21
|
+
|
|
22
|
+
Pass the definition into `defineApp({ env })`. Functions read the resolved, typed values through `context.env`:
|
|
23
|
+
|
|
24
|
+
```ts
|
|
25
|
+
import { defineFunction } from "@relkit/app/functions";
|
|
26
|
+
import { z } from "@relkit/app/schema";
|
|
27
|
+
|
|
28
|
+
export default defineFunction({
|
|
29
|
+
input: z.object({}),
|
|
30
|
+
output: z.object({ level: z.string() }),
|
|
31
|
+
handler: async (_input, context) => ({ level: context.env.LOG_LEVEL }),
|
|
32
|
+
});
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
Mark credentials with `env.secret()`; keep actual values outside source control. Secret metadata enables redaction in generated output, diagnostics, telemetry, and Inspector data. Avoid placeholder production secrets or logging resolved secrets.
|
|
36
|
+
|
|
37
|
+
## `defineApp`: topology and policy
|
|
38
|
+
|
|
39
|
+
In `relkit.config.ts`, the baseline application contains the environment contract, telemetry redaction, backend settings, and Inspector settings:
|
|
40
|
+
|
|
41
|
+
```ts
|
|
42
|
+
import { defineApp } from "@relkit/app/config";
|
|
43
|
+
import env from "@app/platform/env.js";
|
|
44
|
+
|
|
45
|
+
export default defineApp({
|
|
46
|
+
env,
|
|
47
|
+
telemetry: { redaction: { mode: "development-redacted", maxBytes: 65_536 } },
|
|
48
|
+
server: { port: 3000, maxBodyBytes: 1_048_576 },
|
|
49
|
+
inspector: { port: 3210 },
|
|
50
|
+
});
|
|
51
|
+
```
|
|
52
|
+
|
|
53
|
+
`defineApp` also accepts `id`, `defaults`, `deployment`, and provider capabilities `bucket`, `cache`, `jobs`, `event`, `model`, `realtime`, and `"agent-state"`. A capability can have one `default` profile or a named profile map. `defaults.<capability>` must name a configured profile. The `jobs` key is the public spelling for the job provider. Add only providers the app uses; the base template has none. Public creation currently certifies only the minimal starter with examples, no jobs, no cloud, and no deployment. API, agent, fullstack, jobs, and AWS/Pulumi creation tuples are internal candidates and must remain rejected until their exact release evidence is certified. Configure an existing app's optional integrations only when the installed version supports them and the task requires them.
|
|
54
|
+
|
|
55
|
+
For a one-machine realtime provider and a named Docker-backed cache profile, the complete configuration shape is:
|
|
56
|
+
|
|
57
|
+
```ts
|
|
58
|
+
import { defineApp, env as binding } from "@relkit/app/config";
|
|
59
|
+
import { docker } from "@relkit/docker";
|
|
60
|
+
import { localRealtime } from "@relkit/local";
|
|
61
|
+
import { redis } from "@relkit/redis";
|
|
62
|
+
import env from "@app/platform/env.js";
|
|
63
|
+
|
|
64
|
+
export default defineApp({
|
|
65
|
+
env,
|
|
66
|
+
cache: {
|
|
67
|
+
requests: docker(redis({ url: binding.secret("REQUESTS_REDIS_URL") })),
|
|
68
|
+
},
|
|
69
|
+
realtime: localRealtime(),
|
|
70
|
+
defaults: { cache: "requests", realtime: "default" },
|
|
71
|
+
telemetry: { redaction: { mode: "development-redacted", maxBytes: 65_536 } },
|
|
72
|
+
server: { port: 3000, maxBodyBytes: 1_048_576 },
|
|
73
|
+
inspector: { port: 3210 },
|
|
74
|
+
});
|
|
75
|
+
```
|
|
76
|
+
|
|
77
|
+
Merge only the needed capabilities into the existing `defineApp`, preserving its other settings. Install the optional integration packages before importing them. `binding.secret("REQUESTS_REDIS_URL")` is a value-free provider binding; it is not a `context.env` field unless `defineEnv` declares that name too. Stable topology belongs in source; machine, stack, and secret values belong in environment bindings.
|
|
78
|
+
|
|
79
|
+
Platform fragments may explicitly export server, Inspector, telemetry, deployment, or provider settings and be imported by `relkit.config.ts`. Unimported files are not autoloaded. Keep provider acquisition in supported lazy factories and compose one `defineApp`.
|
|
80
|
+
|
|
81
|
+
CLI `--environment` selects provider configuration; `RELKIT_ENV` selects the application environment. `.env` and `.env.local` supply runtime values according to existing CLI loading; `.env.example` is informational and is not loaded as credentials.
|
|
82
|
+
|
|
83
|
+
## Inspect and verify environment values
|
|
84
|
+
|
|
85
|
+
From the generated project root:
|
|
86
|
+
|
|
87
|
+
```sh
|
|
88
|
+
bun run relkit env check
|
|
89
|
+
bun run relkit env list
|
|
90
|
+
bun run relkit env explain BETTER_AUTH_SECRET
|
|
91
|
+
bun run relkit env example
|
|
92
|
+
```
|
|
93
|
+
|
|
94
|
+
`check` validates active values, `list` shows presence/status without printing secrets, `explain` describes one declaration, and `example` renders a safe template. `env example --write --path .env.example` writes it when requested. Use `--environment <name>` with environment-aware CLI commands to select provider configuration; it does not define an application env field. Run `bun run check` and `bun run typecheck` after changing the contract, then exercise the affected runtime path. Run `bun run relkit local status` before using Docker-backed providers.
|
|
95
|
+
|
|
96
|
+
For observability settings, see [Observability and tracing](observability-apis.md); for realtime provider behavior, see [Realtime channels](realtime-apis.md).
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
# Database, authentication, cache, and storage
|
|
2
|
+
|
|
3
|
+
For the full `defineApp`, `defineEnv`, provider profile, and environment binding workflow, read [Application configuration and environments](config-environments.md).
|
|
4
|
+
|
|
5
|
+
The database and auth integrations are specialized services, separate from `defineService` domain maps. `relkit add database` creates the Drizzle baseline in `src/services/database`; `relkit add auth` creates `src/services/auth` and its recognized `ALL` handler route. There should be one of each. Extend an existing one while preserving schema exports, environment fields, and routes.
|
|
6
|
+
|
|
7
|
+
## `defineEnv` and `defineDrizzleService`
|
|
8
|
+
|
|
9
|
+
```ts
|
|
10
|
+
import { defineEnv, env as envFactory } from "@relkit/app/config";
|
|
11
|
+
|
|
12
|
+
export default defineEnv({
|
|
13
|
+
DATABASE_PATH: envFactory.string().default(".relkit/app.sqlite"),
|
|
14
|
+
BETTER_AUTH_SECRET: envFactory.secret(),
|
|
15
|
+
});
|
|
16
|
+
```
|
|
17
|
+
|
|
18
|
+
```ts
|
|
19
|
+
import { Database } from "bun:sqlite";
|
|
20
|
+
import { defineDrizzleService } from "@relkit/drizzle";
|
|
21
|
+
import { drizzle } from "drizzle-orm/bun-sqlite";
|
|
22
|
+
import * as schema from "./schema/index.js";
|
|
23
|
+
|
|
24
|
+
export default defineDrizzleService({
|
|
25
|
+
schema,
|
|
26
|
+
client: ({ env }) => drizzle({ client: new Database(env.DATABASE_PATH, { create: true }) }),
|
|
27
|
+
dispose: (database) => database.$client.close(),
|
|
28
|
+
});
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
Open the native connection in the `client({ env })` factory and close it with `dispose` when needed. Discovery does not run the factory. Generate and review migrations with the installed Drizzle tooling; service creation does not create tables or apply migrations. After `bun run check`, generated context declarations provide typed `context.database`.
|
|
32
|
+
|
|
33
|
+
## `defineBetterAuthService`
|
|
34
|
+
|
|
35
|
+
```ts
|
|
36
|
+
import { defineBetterAuthService } from "@relkit/better-auth";
|
|
37
|
+
|
|
38
|
+
export default defineBetterAuthService({
|
|
39
|
+
baseURL: process.env.BETTER_AUTH_URL ?? "http://127.0.0.1:3000",
|
|
40
|
+
emailAndPassword: { enabled: true },
|
|
41
|
+
});
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
Better Auth uses the same Drizzle connection and needs its tables in that schema. Mount `auth.handler` directly with `export const ALL = defineRoute({ handler: auth.handler })` under the auth base path. Supply a stable server-side `BETTER_AUTH_SECRET` and correct public `BETTER_AUTH_URL`; the scaffold only adds environment examples. Protect application routes and enforce ownership separately from signing in.
|
|
45
|
+
|
|
46
|
+
## `defineCache` and `defineBucket`
|
|
47
|
+
|
|
48
|
+
```ts
|
|
49
|
+
import { defineCache } from "@relkit/app/cache";
|
|
50
|
+
import { z } from "@relkit/app/schema";
|
|
51
|
+
|
|
52
|
+
export default defineCache({
|
|
53
|
+
id: "orders.prices",
|
|
54
|
+
profile: "requests",
|
|
55
|
+
key: z.object({ sku: z.string() }),
|
|
56
|
+
value: z.number().int().nonnegative(),
|
|
57
|
+
defaultTtlMs: 60_000,
|
|
58
|
+
maxTtlMs: 300_000,
|
|
59
|
+
});
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
```ts
|
|
63
|
+
import { defineBucket } from "@relkit/app/buckets";
|
|
64
|
+
|
|
65
|
+
export default defineBucket({
|
|
66
|
+
id: "assets.objects",
|
|
67
|
+
profile: "assets",
|
|
68
|
+
visibility: "private",
|
|
69
|
+
maxObjectBytes: 5_000_000,
|
|
70
|
+
allowedContentTypes: ["application/json", "image/*"],
|
|
71
|
+
});
|
|
72
|
+
```
|
|
73
|
+
|
|
74
|
+
Configure compatible profiles in `relkit.config.ts` and declare each resource in a function's `dependencies` before using its checked context client. A profile selects a provider; the descriptor does not create Redis, S3, or credentials. Use `bun run relkit local status` to inspect Docker-backed resources.
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
# Functions, services, events, and errors
|
|
2
|
+
|
|
3
|
+
Generated projects map `@app/*` to `src/*`; keep the `.js` suffix on source imports. Use the installed package types when an exact signature matters, and run `bun run check` to validate the discovered graph.
|
|
4
|
+
|
|
5
|
+
## `defineFunction` and `defineService`
|
|
6
|
+
|
|
7
|
+
Put domain behavior in `src/services/<domain>/functions/*.function.ts`. A function validates input before its handler and validates the returned output:
|
|
8
|
+
|
|
9
|
+
```ts
|
|
10
|
+
import { defineFunction } from "@relkit/app/functions";
|
|
11
|
+
import { z } from "@relkit/app/schema";
|
|
12
|
+
|
|
13
|
+
const greet = defineFunction({
|
|
14
|
+
id: "hello.greet",
|
|
15
|
+
input: z.object({ name: z.string().min(1) }),
|
|
16
|
+
output: z.object({ message: z.string() }),
|
|
17
|
+
handler: async ({ name }) => ({ message: `Hello, ${name}!` }),
|
|
18
|
+
});
|
|
19
|
+
|
|
20
|
+
export default greet;
|
|
21
|
+
```
|
|
22
|
+
|
|
23
|
+
Expose selected functions from `src/services/<domain>/service.ts`:
|
|
24
|
+
|
|
25
|
+
```ts
|
|
26
|
+
import { defineService } from "@relkit/app/services";
|
|
27
|
+
import greet from "@app/services/hello/functions/greet.function.js";
|
|
28
|
+
|
|
29
|
+
export default defineService({ functions: { greet } });
|
|
30
|
+
```
|
|
31
|
+
|
|
32
|
+
The service also accepts `events`, `tasks`, and `jobs` maps. Its members appear directly as `service.greet`; there is no `service.functions.greet` namespace. Membership makes a function available across domains, but does not create an HTTP route or grant authorization.
|
|
33
|
+
|
|
34
|
+
Within a domain, import a sibling function directly. Across domains and from routes, import the other domain's `service.ts`. Invoke a function descriptor with `await service.greet.invoke(input)`; do not call its handler directly. Leave an internal function out of the service map. Tools, agents, caches, buckets, and event-only functions are not service members.
|
|
35
|
+
|
|
36
|
+
## `defineEvent` and `defineEventFunction`
|
|
37
|
+
|
|
38
|
+
Declare an event payload in `src/services/<domain>/events/*.event.ts`:
|
|
39
|
+
|
|
40
|
+
```ts
|
|
41
|
+
import { defineEvent } from "@relkit/app/events";
|
|
42
|
+
import { z } from "@relkit/app/schema";
|
|
43
|
+
|
|
44
|
+
const orderCreated = defineEvent({
|
|
45
|
+
id: "orders.created",
|
|
46
|
+
version: 1,
|
|
47
|
+
input: z.object({ orderId: z.string() }),
|
|
48
|
+
});
|
|
49
|
+
|
|
50
|
+
declare global {
|
|
51
|
+
namespace Relkit {
|
|
52
|
+
interface EventRegistry {
|
|
53
|
+
readonly "orders.created": typeof orderCreated;
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
export default orderCreated;
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
Expose it through `defineService({ events: { orderCreated } })` when other domains need it. A publisher declares the exact ID in `publishes: ["orders.created"]` and calls `await context.events["orders.created"].publish({ orderId })`.
|
|
62
|
+
|
|
63
|
+
An event-only consumer reacts without returning a result to its publisher:
|
|
64
|
+
|
|
65
|
+
```ts
|
|
66
|
+
import { defineEventFunction } from "@relkit/app/events";
|
|
67
|
+
|
|
68
|
+
export default defineEventFunction({
|
|
69
|
+
id: "orders.confirmation",
|
|
70
|
+
event: "orders.created",
|
|
71
|
+
handler: async ({ orderId }, context) => {
|
|
72
|
+
context.log.info("Order created", { orderId });
|
|
73
|
+
},
|
|
74
|
+
});
|
|
75
|
+
```
|
|
76
|
+
|
|
77
|
+
## `defineError`
|
|
78
|
+
|
|
79
|
+
```ts
|
|
80
|
+
import { defineError } from "@relkit/app/functions";
|
|
81
|
+
import { z } from "@relkit/app/schema";
|
|
82
|
+
|
|
83
|
+
export default defineError({
|
|
84
|
+
id: "orders.not-found",
|
|
85
|
+
data: z.object({ orderId: z.string() }),
|
|
86
|
+
message: ({ orderId }) => `Order ${orderId} was not found`,
|
|
87
|
+
http: { status: 404 },
|
|
88
|
+
retry: { kind: "later", afterMs: 1_000 },
|
|
89
|
+
});
|
|
90
|
+
```
|
|
91
|
+
|
|
92
|
+
Declare only expected failures callers should handle on a function. Use the route layer for HTTP-specific request mapping and middleware.
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
# HTTP routes and request policy
|
|
2
|
+
|
|
3
|
+
Routes live under `src/routes/**/route.ts`. The file path supplies the URL, and named exports supply methods. Import route APIs from `@relkit/app/routes`. Use a public service function as the target for ordinary application endpoints.
|
|
4
|
+
|
|
5
|
+
## `defineRoute`: one function-backed method
|
|
6
|
+
|
|
7
|
+
In `src/routes/hello/route.ts`, this exposes the service's public `hello` function as `GET /hello`:
|
|
8
|
+
|
|
9
|
+
```ts
|
|
10
|
+
import { defineRoute } from "@relkit/app/routes";
|
|
11
|
+
import hello from "@app/services/hello/service.js";
|
|
12
|
+
|
|
13
|
+
export const GET = defineRoute({ target: hello.hello });
|
|
14
|
+
```
|
|
15
|
+
|
|
16
|
+
A function-backed route can also set `successStatus`, `request`, `responses`, `rateLimit`, and `timeoutMs` when needed. The target must be a public callable function; jobs, events, agents, and tools are not route targets. Ordinary JSON request and response schemas are inferred from the target unless you supply explicit mapping.
|
|
17
|
+
|
|
18
|
+
## `defineRoute`: raw Web handler
|
|
19
|
+
|
|
20
|
+
Use `handler` instead of `target` for a standalone Web `Request`/`Response` handler:
|
|
21
|
+
|
|
22
|
+
```ts
|
|
23
|
+
import { defineRoute } from "@relkit/app/routes";
|
|
24
|
+
|
|
25
|
+
export const GET = defineRoute({
|
|
26
|
+
handler: async () => Response.json({ ok: true }),
|
|
27
|
+
});
|
|
28
|
+
```
|
|
29
|
+
|
|
30
|
+
A raw handler has a generic OpenAPI response. The recognized Better Auth mount also uses a raw route:
|
|
31
|
+
|
|
32
|
+
```ts
|
|
33
|
+
import { defineRoute } from "@relkit/app/routes";
|
|
34
|
+
import auth from "@app/services/auth/service.js";
|
|
35
|
+
|
|
36
|
+
export const ALL = defineRoute({ handler: auth.handler });
|
|
37
|
+
```
|
|
38
|
+
|
|
39
|
+
## `defineServiceRoutes`: methods on one service
|
|
40
|
+
|
|
41
|
+
```ts
|
|
42
|
+
import { defineServiceRoutes } from "@relkit/app/routes";
|
|
43
|
+
import orders from "@app/services/orders/service.js";
|
|
44
|
+
|
|
45
|
+
export const { GET, POST } = defineServiceRoutes(orders, {
|
|
46
|
+
GET: "listOrders",
|
|
47
|
+
POST: { member: "createOrder", successStatus: 201 },
|
|
48
|
+
});
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
`GET`, `POST`, `PUT`, `PATCH`, `DELETE`, `HEAD`, and `OPTIONS` are supported service-route exports. `ALL` is for raw handlers. Do not add a `path` or `method` option to `defineRoute`; the filesystem and export determine both. The CLI can scaffold either form through `add route --mode route` or `--mode service-route`. It will not overwrite an existing route file; edit it directly to add a method.
|
|
52
|
+
|
|
53
|
+
Use `request` mapping only when inference cannot express headers, cookies, names, or nesting; it replaces the inferred mapping. Use `responses` only when you need an explicit response contract. `defineMiddleware(path, handler)` is for HTTP policy, and `defineTransform({ schema })` is for request transforms:
|
|
54
|
+
|
|
55
|
+
```ts
|
|
56
|
+
import { defineMiddleware } from "@relkit/app/routes";
|
|
57
|
+
|
|
58
|
+
export default defineMiddleware("/orders/*", async (_context, next) => {
|
|
59
|
+
await next();
|
|
60
|
+
});
|
|
61
|
+
```
|
|
62
|
+
|
|
63
|
+
```ts
|
|
64
|
+
import { defineTransform } from "@relkit/app/routes";
|
|
65
|
+
import { z } from "@relkit/app/schema";
|
|
66
|
+
|
|
67
|
+
export default defineTransform({ schema: z.string() });
|
|
68
|
+
```
|
|
69
|
+
|
|
70
|
+
Application authorization must be enforced in the relevant route or function logic. After changing a route, run `bun run check` and `bun run typecheck`, exercise the HTTP endpoint, and inspect `/_relkit/v1/api-reference` while `bun run dev` is running.
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
# Tasks and jobs
|
|
2
|
+
|
|
3
|
+
Use a task for work that must outlive its initiating request; a function remains a request- or event-scoped operation.
|
|
4
|
+
|
|
5
|
+
## `defineTask`
|
|
6
|
+
|
|
7
|
+
```ts
|
|
8
|
+
import { defineTask } from "@relkit/app/tasks";
|
|
9
|
+
import { z } from "@relkit/app/schema";
|
|
10
|
+
|
|
11
|
+
export default defineTask({
|
|
12
|
+
id: "orders.export-orders",
|
|
13
|
+
version: "1",
|
|
14
|
+
execution: "durable",
|
|
15
|
+
input: z.object({ orderIds: z.array(z.string()) }),
|
|
16
|
+
output: z.object({ exported: z.number().int().nonnegative() }),
|
|
17
|
+
progress: z.object({ completed: z.number().int().nonnegative() }),
|
|
18
|
+
handler: async ({ orderIds }, context) => {
|
|
19
|
+
await context.progress.emit({ completed: orderIds.length });
|
|
20
|
+
return { exported: orderIds.length };
|
|
21
|
+
},
|
|
22
|
+
});
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
## `defineJob`
|
|
26
|
+
|
|
27
|
+
Bind the task to a public job name and an explicit client policy in `src/services/orders/jobs/export-orders.job.ts`:
|
|
28
|
+
|
|
29
|
+
```ts
|
|
30
|
+
import { defineJob } from "@relkit/app/jobs";
|
|
31
|
+
import exportOrders from "@app/services/orders/tasks/export-orders.task.js";
|
|
32
|
+
|
|
33
|
+
export default defineJob({
|
|
34
|
+
id: "orders.export-orders-job",
|
|
35
|
+
name: "exportOrders",
|
|
36
|
+
task: exportOrders,
|
|
37
|
+
client: {
|
|
38
|
+
public: true,
|
|
39
|
+
operations: ["trigger", "get", "list", "watch"],
|
|
40
|
+
fields: ["status", "progress", "output"],
|
|
41
|
+
},
|
|
42
|
+
});
|
|
43
|
+
```
|
|
44
|
+
|
|
45
|
+
Expose the task and job through the owning service's `tasks` and `jobs` maps. Keep the task ID and version stable; change the version for an intentional incompatible task contract. Make side effects idempotent because work may retry or resume.
|
|
46
|
+
|
|
47
|
+
The app's `relkit.config.ts` selects a compatible jobs provider. Run `bun run relkit jobs capabilities` to inspect its actual guarantees; a durable task needs a binding that supports durable execution. `relkit add task` and `relkit add job --target <task-id>` scaffold the pair without running a worker or provisioning a provider.
|
|
48
|
+
|
|
49
|
+
A trigger admits work and returns a run handle, not the task's output. Keep its `runId` and `operationId`, then read or watch the run; a typed client alone does not authorize a caller. A raw HTTP trigger can return the accepted handle with status `202`. Use `bun run relkit local status` to inspect local provider state before exercising a Docker-backed job.
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
# Optional flat layout migration
|
|
2
|
+
|
|
3
|
+
Flat `src/<name>/service.ts` applications remain supported. Migrate only when grouped placement helps the app. Preview from the application root:
|
|
4
|
+
|
|
5
|
+
```sh
|
|
6
|
+
bun run relkit migrate layout
|
|
7
|
+
bun run relkit --json migrate layout
|
|
8
|
+
```
|
|
9
|
+
|
|
10
|
+
The deterministic plan moves complete service roots to `src/services/<name>`, including helpers and assets. It reports import, test, tooling, documentation, and local guidance rewrites, conflicts, and references needing manual action. Preview leaves authored files, lockfiles, generated output, persistent state, migration history, and credentials unchanged.
|
|
11
|
+
|
|
12
|
+
Stop the app's active development session and resolve touched tracked changes, occupied destinations, mixed boundaries, symlinks, and ambiguous/computed references before applying:
|
|
13
|
+
|
|
14
|
+
```sh
|
|
15
|
+
bun run relkit migrate layout --write
|
|
16
|
+
```
|
|
17
|
+
|
|
18
|
+
Write stages the candidate with installed dependencies and requires baseline/candidate check, typecheck, logical graph, and offline deployment compatibility before publication. It does not install packages, run database migrations or seeds, provision providers, or edit global skills. Publication is coordinated across files; the restricted local receipt retains exact before/after bytes and permissions for failure or crash recovery. Keep that receipt private.
|
|
19
|
+
|
|
20
|
+
Rollback with the exact path returned by the write result:
|
|
21
|
+
|
|
22
|
+
```sh
|
|
23
|
+
bun run relkit migrate layout --rollback .relkit/migrations/RECEIPT_ID/receipt.json
|
|
24
|
+
```
|
|
25
|
+
|
|
26
|
+
Rollback refuses later edits or occupied original locations instead of overwriting them. Recovery conflicts preserve user bytes and require inspection of the retained receipt. Successful migration or restoration needs fresh preparation:
|
|
27
|
+
|
|
28
|
+
```sh
|
|
29
|
+
bun run check
|
|
30
|
+
bun run typecheck
|
|
31
|
+
bun run relkit dev --prepare
|
|
32
|
+
bun run dev
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
Compare actual application responses and durable runs after the move. Logical service/function/task/job/channel/agent IDs and versions remain unchanged; diagnostic and editor paths point at their real grouped sources.
|
package/dist/templates/default/v1/tasks/.agents/skills/relkit/references/observability-apis.md
ADDED
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
# Observability and tracing
|
|
2
|
+
|
|
3
|
+
RELKIT records HTTP requests and invocation spans automatically. Use `context.log` for structured application records and `context.trace` for application work inside an existing function that needs more detail.
|
|
4
|
+
|
|
5
|
+
## Log and trace inside a function
|
|
6
|
+
|
|
7
|
+
```ts
|
|
8
|
+
import { defineFunction } from "@relkit/app/functions";
|
|
9
|
+
import { z } from "@relkit/app/schema";
|
|
10
|
+
|
|
11
|
+
export default defineFunction({
|
|
12
|
+
id: "orders.total",
|
|
13
|
+
input: z.object({ quantity: z.number().int().positive() }),
|
|
14
|
+
output: z.object({ totalCents: z.number().int().nonnegative() }),
|
|
15
|
+
handler: async ({ quantity }, context) => {
|
|
16
|
+
const totalCents = await context.trace.span(
|
|
17
|
+
"pricing.calculate",
|
|
18
|
+
{ attributes: { "pricing.strategy": "catalog" } },
|
|
19
|
+
async () => quantity * 1_000,
|
|
20
|
+
);
|
|
21
|
+
context.trace.event("pricing.calculated", { "pricing.total_cents": totalCents });
|
|
22
|
+
context.trace.setAttributes({ "pricing.quantity": quantity });
|
|
23
|
+
context.log.info("orders.total.calculated", { quantity, totalCents });
|
|
24
|
+
return { totalCents };
|
|
25
|
+
},
|
|
26
|
+
});
|
|
27
|
+
```
|
|
28
|
+
|
|
29
|
+
`span(name, callback)` creates an internal child span; `span(name, { attributes, kind }, callback)` adds attributes and an `internal` or `client` kind. `event(name, attributes?)` adds an event to the active span, and `setAttributes` annotates it. RELKIT ends child spans on success or failure. Attribute values must be strings, finite numbers, or booleans. Do not log secrets or put payloads or random IDs in span attributes.
|
|
30
|
+
|
|
31
|
+
## Configure capture and export
|
|
32
|
+
|
|
33
|
+
Edit the existing `relkit.config.ts` and preserve its environment and provider settings:
|
|
34
|
+
|
|
35
|
+
```ts
|
|
36
|
+
import { defineApp } from "@relkit/app/config";
|
|
37
|
+
import env from "@app/platform/env.js";
|
|
38
|
+
|
|
39
|
+
export default defineApp({
|
|
40
|
+
env,
|
|
41
|
+
telemetry: {
|
|
42
|
+
redaction: { mode: "development-redacted", maxBytes: 65_536 },
|
|
43
|
+
localRetention: { maxRecords: 2_000, maxAgeMs: 3_600_000, maxBytes: 16_777_216 },
|
|
44
|
+
exportSampling: { traceRate: 0.25, minimumLogLevel: "info" },
|
|
45
|
+
},
|
|
46
|
+
server: { port: 3000 },
|
|
47
|
+
inspector: { port: 3210 },
|
|
48
|
+
});
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
The template already supplies redaction. `localRetention` bounds development history; `exportSampling` controls remote export independently of local capture. Add named Sentry or OTLP exporters only when those integrations and their secret environment bindings are configured. Redact before storage or export. No `relkit add observability` kind exists; configure `telemetry` in `defineApp`.
|
|
52
|
+
|
|
53
|
+
Run `bun run dev`, make one identifiable HTTP request, then inspect Requests, Traces, and Logs in the Inspector. Use `bun run dev -- --verbose` for DEBUG terminal output or `--json` for structured terminal records. Development history is stored in `.relkit/observability/observability.duckdb`; this is diagnostic history, not business storage.
|
|
@@ -0,0 +1,98 @@
|
|
|
1
|
+
# Realtime channels
|
|
2
|
+
|
|
3
|
+
Use a channel to notify connected clients about a change. Keep the authoritative state in a route or database query; use channel events to refresh or update that state. Application events deliver backend work, while channels deliver live client updates.
|
|
4
|
+
|
|
5
|
+
## `defineChannel`
|
|
6
|
+
|
|
7
|
+
Create `src/services/announcements/channels/announcements.channel.ts`:
|
|
8
|
+
|
|
9
|
+
```ts
|
|
10
|
+
import { defineChannel } from "@relkit/app/realtime";
|
|
11
|
+
import { z } from "@relkit/app/schema";
|
|
12
|
+
|
|
13
|
+
const announcements = defineChannel({
|
|
14
|
+
id: "announcements.feed",
|
|
15
|
+
params: z.object({}),
|
|
16
|
+
events: { posted: z.object({ message: z.string(), postedAt: z.string() }) },
|
|
17
|
+
client: { public: true },
|
|
18
|
+
replay: { retentionMs: 300_000, maxEvents: 1_000 },
|
|
19
|
+
});
|
|
20
|
+
|
|
21
|
+
export default announcements;
|
|
22
|
+
```
|
|
23
|
+
|
|
24
|
+
`params` selects a partition, `events` validates named payloads, and `client` controls browser exposure. Omit `client` for backend-only channels. Use `client: { authorize: async (params, context) => ... }` for protected partitions and verify access to the specific resource, not merely that a session exists. `presence: "count"` adds connection counts. A channel with no events must declare presence.
|
|
25
|
+
|
|
26
|
+
## Publish and subscribe
|
|
27
|
+
|
|
28
|
+
After the application change succeeds, publish one validated event from a backend function:
|
|
29
|
+
|
|
30
|
+
```ts
|
|
31
|
+
import { defineFunction } from "@relkit/app/functions";
|
|
32
|
+
import { z } from "@relkit/app/schema";
|
|
33
|
+
import announcements from "@app/services/announcements/channels/announcements.channel.js";
|
|
34
|
+
|
|
35
|
+
export default defineFunction({
|
|
36
|
+
id: "announcements.post",
|
|
37
|
+
input: z.object({ message: z.string().min(1) }),
|
|
38
|
+
output: z.object({ accepted: z.literal(true) }),
|
|
39
|
+
handler: async ({ message }) => {
|
|
40
|
+
await announcements.trigger({}, "posted", {
|
|
41
|
+
message,
|
|
42
|
+
postedAt: new Date().toISOString(),
|
|
43
|
+
});
|
|
44
|
+
return { accepted: true as const };
|
|
45
|
+
},
|
|
46
|
+
});
|
|
47
|
+
```
|
|
48
|
+
|
|
49
|
+
The `trigger()` receipt confirms the provider accepted the append; it does not prove delivery to every browser. If a database write and publication must be atomic, use an outbox in the database transaction. A retryable publish can pass a RELKIT-issued `idempotencyKey` as the fourth argument.
|
|
50
|
+
|
|
51
|
+
In a React client with `@relkit/client`, subscribe using the generated channel registry:
|
|
52
|
+
|
|
53
|
+
```tsx
|
|
54
|
+
"use client";
|
|
55
|
+
|
|
56
|
+
import { useChannel, useRoute } from "@relkit/client/react";
|
|
57
|
+
|
|
58
|
+
export default function Announcements() {
|
|
59
|
+
const announcements = useRoute("GET /announcements", { input: {} });
|
|
60
|
+
const channel = useChannel("announcements.feed", {
|
|
61
|
+
params: {},
|
|
62
|
+
on: { posted: () => void announcements.refetch() },
|
|
63
|
+
onCaughtUp: async () => {
|
|
64
|
+
await announcements.refetch();
|
|
65
|
+
},
|
|
66
|
+
onGap: async () => {
|
|
67
|
+
await announcements.refetch();
|
|
68
|
+
},
|
|
69
|
+
});
|
|
70
|
+
|
|
71
|
+
return <p>Channel: {channel.status}</p>;
|
|
72
|
+
}
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
Load authoritative state through a route before relying on updates. `onGap` must restore it when replay cannot bridge a disconnect. `channel.status` and `channel.caughtUp` report connection and recovery state. `useRealtime()` is the lower-level subscription manager; a channel descriptor's `getPresence(params)` reads presence when declared.
|
|
76
|
+
|
|
77
|
+
## Provider and verification
|
|
78
|
+
|
|
79
|
+
Configure a compatible `realtime` provider and `defaults.realtime` in `relkit.config.ts`. For a one-machine app with `@relkit/local` installed, the relevant configuration is:
|
|
80
|
+
|
|
81
|
+
```ts
|
|
82
|
+
import { defineApp } from "@relkit/app/config";
|
|
83
|
+
import { localRealtime } from "@relkit/local";
|
|
84
|
+
import env from "@app/platform/env.js";
|
|
85
|
+
|
|
86
|
+
export default defineApp({
|
|
87
|
+
env,
|
|
88
|
+
realtime: localRealtime(),
|
|
89
|
+
defaults: { realtime: "default" },
|
|
90
|
+
telemetry: { redaction: { mode: "development-redacted", maxBytes: 65_536 } },
|
|
91
|
+
server: { port: 3000 },
|
|
92
|
+
inspector: { port: 3210 },
|
|
93
|
+
});
|
|
94
|
+
```
|
|
95
|
+
|
|
96
|
+
Merge these fields into an existing `defineApp` while preserving its other providers and settings. Redis supports fanout across application instances. Provider storage, retention, and Redis persistence determine recovery guarantees. Run `bun run check`, `bun run typecheck`, then test publication, browser subscription, reconnect, and gap recovery. Inspect channels in the Inspector while `bun run dev` is running.
|
|
97
|
+
|
|
98
|
+
The current `relkit add` kinds do not include `channel`. Create the descriptor and provider configuration in the app source.
|