@tailor-platform/sdk 2.3.0 → 2.5.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 +171 -0
- package/README.md +1 -1
- package/dist/aigateway-DsWDjzk4.mjs +2 -0
- package/dist/{aigateway-DR4Kwuik.mjs.map → aigateway-DsWDjzk4.mjs.map} +1 -1
- package/dist/application-DFOUovmN.mjs +1 -0
- package/dist/application-D_4vg1KR.mjs +192 -0
- package/dist/application-D_4vg1KR.mjs.map +1 -0
- package/dist/assert-WeXvmG4j.mjs +2 -0
- package/dist/{assert-DBxo8jPo.mjs.map → assert-WeXvmG4j.mjs.map} +1 -1
- package/dist/authconnection-CynFBIv8.mjs +2 -0
- package/dist/{authconnection-CZvi9ANm.mjs.map → authconnection-CynFBIv8.mjs.map} +1 -1
- package/dist/brand-C8nMKhJC.mjs +2 -0
- package/dist/{brand-Eo4pLXPJ.mjs.map → brand-C8nMKhJC.mjs.map} +1 -1
- package/dist/cli/commands/deploy/deploy.d.mts +2 -2
- package/dist/cli/commands/deploy/deployment-target.d.mts +2 -0
- package/dist/cli/commands/deploy/event-subscriptions.d.mts +3 -0
- package/dist/cli/commands/deploy/tailordb/apply.d.mts +3 -0
- package/dist/cli/commands/deploy/tailordb/index.d.mts +3 -10
- package/dist/cli/commands/deploy/tailordb/migration-validation.d.mts +5 -0
- package/dist/cli/commands/deploy/tailordb/plan.d.mts +8 -0
- package/dist/cli/commands/executor/jobs.d.mts +1 -1
- package/dist/cli/commands/generate/seed/bundler.d.mts +2 -2
- package/dist/cli/commands/show.d.mts +1 -1
- package/dist/cli/commands/tailordb/migrate/diff-calculator.d.mts +15 -15
- package/dist/cli/commands/tailordb/migrate/generate.d.mts +7 -3
- package/dist/cli/commands/tailordb/migrate/rename-detection.d.mts +1 -1
- package/dist/cli/commands/tailordb/migrate/snapshot-comparison.d.mts +43 -0
- package/dist/cli/commands/tailordb/migrate/snapshot-files.d.mts +62 -0
- package/dist/cli/commands/tailordb/migrate/snapshot-local.d.mts +12 -0
- package/dist/cli/commands/tailordb/migrate/snapshot-migrations.d.mts +12 -0
- package/dist/cli/commands/tailordb/migrate/snapshot-remote.d.mts +1 -0
- package/dist/cli/commands/tailordb/migrate/snapshot-types.d.mts +3 -1
- package/dist/cli/commands/tailordb/migrate/snapshot.d.mts +5 -117
- package/dist/cli/commands/tailordb/truncate.d.mts +2 -2
- package/dist/cli/lib.d.mts +8 -4
- package/dist/cli/lib.mjs +1 -9
- package/dist/cli/lib.mjs.map +1 -1
- package/dist/cli/main.mjs +1170 -7686
- package/dist/cli/main.mjs.map +1 -1
- package/dist/cli/shared/seed-chunker.d.mts +5 -5
- package/dist/cli/ts-hook.mjs +3 -1
- package/dist/completion/zsh-worker.zsh +99 -18
- package/dist/configure/config/index.d.mts +2 -2
- package/dist/configure/config/types.d.mts +2 -2
- package/dist/configure/index.d.mts +49 -12
- package/dist/configure/index.mjs +1 -1267
- package/dist/configure/index.mjs.map +1 -1
- package/dist/configure/services/aigateway/index.d.mts +5 -4
- package/dist/configure/services/aigateway/types.d.mts +6 -1
- package/dist/configure/services/auth/types.d.mts +3 -3
- package/dist/configure/services/idp/types.d.mts +1 -1
- package/dist/configure/services/tailordb/permission.d.mts +1 -1
- package/dist/configure/services/tailordb/schema.d.mts +5 -9
- package/dist/configure/services/tailordb/types.d.mts +8 -5
- package/dist/configure/services/workflow/execution-policy.d.mts +3 -3
- package/dist/configure/services/workflow/job.d.mts +12 -2
- package/dist/configure/types/auth-namespace-name.d.mts +18 -0
- package/dist/configure/types/field.types.d.mts +1 -1
- package/dist/configure/types/permission-operand.types.d.mts +1 -1
- package/dist/context-D0QjfxzD.mjs +2 -0
- package/dist/{context-DYQVYWqZ.mjs.map → context-D0QjfxzD.mjs.map} +1 -1
- package/dist/crashreport-B-_HTKLr.mjs +42 -0
- package/dist/{crashreport-CIIfLnoO.mjs.map → crashreport-B-_HTKLr.mjs.map} +1 -1
- package/dist/crashreport-BmsRIdpy.mjs +1 -0
- package/dist/errors-DSEXKRVD.mjs +2 -0
- package/dist/errors-DSEXKRVD.mjs.map +1 -0
- package/dist/file-COPYfju_.mjs +2 -0
- package/dist/file-COPYfju_.mjs.map +1 -0
- package/dist/globals-CMHSnj4w.mjs +2 -0
- package/dist/{globals-B2nlxBrz.mjs.map → globals-CMHSnj4w.mjs.map} +1 -1
- package/dist/iconv-DlFMt2gW.mjs +2 -0
- package/dist/{iconv-QWaZh0TT.mjs.map → iconv-DlFMt2gW.mjs.map} +1 -1
- package/dist/idp-G_ojPBB5.mjs +2 -0
- package/dist/{idp-RA_swu-h.mjs.map → idp-G_ojPBB5.mjs.map} +1 -1
- package/dist/interceptor-DQg3cR_9.mjs +2 -0
- package/dist/{interceptor-e33JtsC-.mjs.map → interceptor-DQg3cR_9.mjs.map} +1 -1
- package/dist/kysely/index.mjs +1 -31
- package/dist/kysely/index.mjs.map +1 -1
- package/dist/kysely-type-BTi3BMtL.mjs +43 -0
- package/dist/kysely-type-BTi3BMtL.mjs.map +1 -0
- package/dist/logger-BcGy-u7G.mjs +9 -0
- package/dist/{logger-DSdExfor.mjs.map → logger-BcGy-u7G.mjs.map} +1 -1
- package/dist/logger-DP2BjQ93.mjs +2 -0
- package/dist/{logger-BtX0suGY.mjs.map → logger-DP2BjQ93.mjs.map} +1 -1
- package/dist/multiline-EyzjEwn9.mjs +3 -0
- package/dist/{multiline-sfHpTZZK.mjs.map → multiline-EyzjEwn9.mjs.map} +1 -1
- package/dist/node-builtins-oBl7EbyV.mjs +2 -0
- package/dist/{node-builtins-CmaL2Cbq.mjs.map → node-builtins-oBl7EbyV.mjs.map} +1 -1
- package/dist/package-json-C690ceex.mjs +2 -0
- package/dist/{package-json-8b0O9TlX.mjs.map → package-json-C690ceex.mjs.map} +1 -1
- package/dist/package-json-CmqhDJ__.mjs +1 -0
- package/dist/parser/service/tailordb/type-source.d.mts +5 -5
- package/dist/parser/service/tailordb/types.d.mts +4 -4
- package/dist/platform-serialize-DkiTdHOt.mjs +2 -0
- package/dist/{platform-serialize-RoRtBS0v.mjs.map → platform-serialize-DkiTdHOt.mjs.map} +1 -1
- package/dist/plugin/builtin/enum-constants/index.d.mts +1 -1
- package/dist/plugin/builtin/enum-constants/index.mjs +5 -114
- package/dist/plugin/builtin/enum-constants/index.mjs.map +1 -1
- package/dist/plugin/builtin/file-utils/index.d.mts +1 -1
- package/dist/plugin/builtin/file-utils/index.mjs +22 -101
- package/dist/plugin/builtin/file-utils/index.mjs.map +1 -1
- package/dist/plugin/builtin/kysely-type/index.d.mts +9 -2
- package/dist/plugin/builtin/kysely-type/index.mjs +1 -275
- package/dist/plugin/builtin/seed/index.d.mts +5 -0
- package/dist/plugin/builtin/seed/index.mjs +1 -3
- package/dist/plugin/builtin/seed/seed-type-processor.d.mts +4 -6
- package/dist/plugin/get-generated-table.d.mts +16 -0
- package/dist/plugin/index.d.mts +3 -2
- package/dist/plugin/index.mjs +1 -251
- package/dist/plugin/index.mjs.map +1 -1
- package/dist/plugin/types.d.mts +32 -25
- package/dist/plugin/with-context.d.mts +4 -4
- package/dist/register-ts-hook-Drnaproy.mjs +640 -0
- package/dist/register-ts-hook-Drnaproy.mjs.map +1 -0
- package/dist/registry-HlEaGvl5.mjs +2 -0
- package/dist/{registry-BIGVUrMB.mjs.map → registry-HlEaGvl5.mjs.map} +1 -1
- package/dist/repl-editor-BG1aDOfH.mjs +2 -0
- package/dist/{repl-editor-BCozyiNq.mjs.map → repl-editor-BG1aDOfH.mjs.map} +1 -1
- package/dist/runtime/aigateway.mjs +1 -3
- package/dist/runtime/authconnection.mjs +1 -3
- package/dist/runtime/context.mjs +1 -3
- package/dist/runtime/file.d.mts +28 -28
- package/dist/runtime/file.mjs +1 -3
- package/dist/runtime/globals.mjs +1 -1
- package/dist/runtime/iconv.mjs +1 -3
- package/dist/runtime/idp.mjs +1 -3
- package/dist/runtime/index.mjs +1 -11
- package/dist/runtime/logger.mjs +1 -3
- package/dist/runtime/secretmanager.mjs +1 -3
- package/dist/runtime/types.d.mts +1 -1
- package/dist/runtime/workflow.mjs +1 -3
- package/dist/schema-Ze_dI5VX.mjs +2 -0
- package/dist/schema-Ze_dI5VX.mjs.map +1 -0
- package/dist/secret-file-C9wp_FCX.mjs +2 -0
- package/dist/{secret-file-C3J4Gy8r.mjs.map → secret-file-C9wp_FCX.mjs.map} +1 -1
- package/dist/secretmanager-5olfnI1b.mjs +2 -0
- package/dist/{secretmanager-IY4UvinW.mjs.map → secretmanager-5olfnI1b.mjs.map} +1 -1
- package/dist/secretmanager-vHQoXdQz.mjs +2 -0
- package/dist/{secretmanager-CYlpffsz.mjs.map → secretmanager-vHQoXdQz.mjs.map} +1 -1
- package/dist/seed/index.d.mts +4 -4
- package/dist/seed/index.mjs +8 -244
- package/dist/seed/index.mjs.map +1 -1
- package/dist/seed-DwqRFdqP.mjs +207 -0
- package/dist/seed-DwqRFdqP.mjs.map +1 -0
- package/dist/service-BVe9u2Rt.mjs +7 -0
- package/dist/service-BVe9u2Rt.mjs.map +1 -0
- package/dist/service-CpZELSBa.mjs +1 -0
- package/dist/service-DlgaUO4V.mjs +2 -0
- package/dist/{service-hZskxZmg.mjs.map → service-DlgaUO4V.mjs.map} +1 -1
- package/dist/service_pb-DGKCLuAs.mjs +2 -0
- package/dist/{service_pb-BEWj1pOV.mjs.map → service_pb-DGKCLuAs.mjs.map} +1 -1
- package/dist/service_pb-_aeFE-Nv.mjs +1 -0
- package/dist/telemetry-Bklv9kQY.mjs +2 -0
- package/dist/{telemetry-BRVdwh14.mjs.map → telemetry-Bklv9kQY.mjs.map} +1 -1
- package/dist/telemetry-DXHP3VVi.mjs +1 -0
- package/dist/type-source--ZNcV8RJ.mjs +2 -0
- package/dist/type-source--ZNcV8RJ.mjs.map +1 -0
- package/dist/types/aigateway.generated.d.mts +2 -2
- package/dist/types/auth.generated.d.mts +3 -3
- package/dist/types/executor.generated.d.mts +2 -2
- package/dist/types/tailordb.generated.d.mts +12 -12
- package/dist/user-agent-vdHYF3QL.mjs +2 -0
- package/dist/{user-agent-Bgsszb5I.mjs.map → user-agent-vdHYF3QL.mjs.map} +1 -1
- package/dist/utils/test/index.d.mts +4 -4
- package/dist/utils/test/index.mjs +1 -109
- package/dist/utils/test/index.mjs.map +1 -1
- package/dist/vitest/environment.mjs +1 -41
- package/dist/vitest/environment.mjs.map +1 -1
- package/dist/vitest/index.mjs +1 -1980
- package/dist/vitest/index.mjs.map +1 -1
- package/dist/vitest/mocks/file.d.mts +8 -8
- package/dist/vitest/setup.mjs +1 -140
- package/dist/vitest/setup.mjs.map +1 -1
- package/dist/wait-point-invoker-eiP-IIux.mjs +2 -0
- package/dist/wait-point-invoker-eiP-IIux.mjs.map +1 -0
- package/dist/wait-point-registry-BrkwfyjS.mjs +2 -0
- package/dist/{wait-point-registry-TL99zotw.mjs.map → wait-point-registry-BrkwfyjS.mjs.map} +1 -1
- package/dist/workflow-Cs9ISw6j.mjs +2 -0
- package/dist/{workflow-Bamae_Yc.mjs.map → workflow-Cs9ISw6j.mjs.map} +1 -1
- package/dist/workspace_resource_pb--GeYQPXu.mjs +2 -0
- package/dist/{workspace_resource_pb-HNIL_Vfj.mjs.map → workspace_resource_pb--GeYQPXu.mjs.map} +1 -1
- package/docs/cli/application.md +3 -1
- package/docs/cli/function.md +77 -13
- package/docs/cli/setup.md +24 -14
- package/docs/cli/tailordb.md +32 -30
- package/docs/cli/workspace.md +2 -2
- package/docs/cli-reference.md +23 -22
- package/docs/configuration.md +2 -2
- package/docs/github-actions.md +10 -9
- package/docs/migration/v2.md +16 -4
- package/docs/migration/v3.md +123 -0
- package/docs/plugin/custom.md +130 -85
- package/docs/plugin/index.md +3 -3
- package/docs/quickstart.md +1 -1
- package/docs/services/aigateway.md +33 -9
- package/docs/services/executor.md +5 -1
- package/docs/services/tailordb-migration.md +68 -54
- package/docs/services/tailordb.md +7 -7
- package/docs/services/workflow.md +10 -9
- package/docs/testing.md +1 -1
- package/package.json +16 -16
- package/postinstall.mjs +1 -1
- package/dist/aigateway-DR4Kwuik.mjs +0 -9
- package/dist/application-BZfk4HKm.mjs +0 -3
- package/dist/application-F-nl107y.mjs +0 -6019
- package/dist/application-F-nl107y.mjs.map +0 -1
- package/dist/assert-DBxo8jPo.mjs +0 -9
- package/dist/authconnection-CZvi9ANm.mjs +0 -9
- package/dist/brand-Eo4pLXPJ.mjs +0 -36
- package/dist/context-DYQVYWqZ.mjs +0 -23
- package/dist/crashreport-CIIfLnoO.mjs +0 -423
- package/dist/crashreport-CINZ5dVN.mjs +0 -3
- package/dist/errors-BVb6vYGy.mjs +0 -89
- package/dist/errors-BVb6vYGy.mjs.map +0 -1
- package/dist/file-BUcmVIH2.mjs +0 -58
- package/dist/file-BUcmVIH2.mjs.map +0 -1
- package/dist/globals-B2nlxBrz.mjs +0 -126
- package/dist/iconv-QWaZh0TT.mjs +0 -38
- package/dist/idp-RA_swu-h.mjs +0 -82
- package/dist/interceptor-e33JtsC-.mjs +0 -33
- package/dist/logger-BtX0suGY.mjs +0 -48
- package/dist/logger-DSdExfor.mjs +0 -358
- package/dist/multiline-sfHpTZZK.mjs +0 -38
- package/dist/node-builtins-CmaL2Cbq.mjs +0 -36
- package/dist/package-json-8b0O9TlX.mjs +0 -17
- package/dist/package-json-Cv2Z-TqQ.mjs +0 -3
- package/dist/platform-serialize-RoRtBS0v.mjs +0 -46
- package/dist/plugin/builtin/kysely-type/index.mjs.map +0 -1
- package/dist/plugin/builtin/seed/types.d.mts +0 -2
- package/dist/plugin/get-generated-type.d.mts +0 -16
- package/dist/register-ts-hook-ClI226n2.mjs +0 -25543
- package/dist/register-ts-hook-ClI226n2.mjs.map +0 -1
- package/dist/registry-BIGVUrMB.mjs +0 -54
- package/dist/repl-editor-BCozyiNq.mjs +0 -251
- package/dist/schema--xYWRGfe.mjs +0 -639
- package/dist/schema--xYWRGfe.mjs.map +0 -1
- package/dist/secret-file-C3J4Gy8r.mjs +0 -64
- package/dist/secretmanager-CYlpffsz.mjs +0 -13
- package/dist/secretmanager-IY4UvinW.mjs +0 -131
- package/dist/seed-xqM9WIHP.mjs +0 -483
- package/dist/seed-xqM9WIHP.mjs.map +0 -1
- package/dist/service-C_WpbKHu.mjs +0 -898
- package/dist/service-C_WpbKHu.mjs.map +0 -1
- package/dist/service-D1RCdzIL.mjs +0 -3
- package/dist/service-hZskxZmg.mjs +0 -131
- package/dist/service_pb-BEWj1pOV.mjs +0 -167
- package/dist/service_pb-BjlhvK9E.mjs +0 -3
- package/dist/telemetry-BRVdwh14.mjs +0 -84
- package/dist/telemetry-CkbkeJxl.mjs +0 -3
- package/dist/type-source-DH_LH20p.mjs +0 -13
- package/dist/type-source-DH_LH20p.mjs.map +0 -1
- package/dist/user-agent-Bgsszb5I.mjs +0 -28
- package/dist/wait-point-invoker-__oE88_P.mjs +0 -148
- package/dist/wait-point-invoker-__oE88_P.mjs.map +0 -1
- package/dist/wait-point-registry-TL99zotw.mjs +0 -47
- package/dist/workflow-Bamae_Yc.mjs +0 -34
- package/dist/workspace_resource_pb-HNIL_Vfj.mjs +0 -860
|
@@ -0,0 +1,123 @@
|
|
|
1
|
+
# Migrating to v3
|
|
2
|
+
|
|
3
|
+
<!-- Generated from the sdk-codemod registry. Run `pnpm codemod:docs:update` and edit `packages/sdk-codemod/src/registry.ts` instead of this file. -->
|
|
4
|
+
|
|
5
|
+
Run the codemods, then finish anything reported as not migrated automatically:
|
|
6
|
+
|
|
7
|
+
```sh
|
|
8
|
+
npx @tailor-platform/sdk-codemod --from <current-version> --to <target-version>
|
|
9
|
+
```
|
|
10
|
+
|
|
11
|
+
## workflow.execJobFunction (imported) removed — use job.start()
|
|
12
|
+
|
|
13
|
+
**Migration:** Manual
|
|
14
|
+
|
|
15
|
+
`execJobFunction` on the `workflow` value imported from @tailor-platform/sdk/runtime(/workflow) is removed in v3. Calling it directly from a workflow job body to reach another job is not detected as a build-time dependency and has no working use; the target job's own `.start()` method is the only supported way to call it. This does not affect the ambient `tailor.workflow.execJobFunction` global — that's what `.start()` itself compiles down to at build time, and it remains fully supported.
|
|
16
|
+
|
|
17
|
+
Before:
|
|
18
|
+
|
|
19
|
+
```ts
|
|
20
|
+
import { workflow } from "@tailor-platform/sdk/runtime";
|
|
21
|
+
|
|
22
|
+
await workflow.execJobFunction("worker", { id: 1 });
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
After:
|
|
26
|
+
|
|
27
|
+
```ts
|
|
28
|
+
import { worker } from "./jobs/worker";
|
|
29
|
+
|
|
30
|
+
await worker.start({ id: 1 });
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
<details>
|
|
34
|
+
<summary>Prompt for an AI agent (to perform this migration)</summary>
|
|
35
|
+
|
|
36
|
+
```text
|
|
37
|
+
workflow.execJobFunction — the value imported from
|
|
38
|
+
@tailor-platform/sdk/runtime or @tailor-platform/sdk/runtime/workflow — is
|
|
39
|
+
removed in v3. Replace each call with the target job's own .start() method:
|
|
40
|
+
import the WorkflowJob the call names and call <job>.start(args, options)
|
|
41
|
+
instead of workflow.execJobFunction("<job-name>", args, options).
|
|
42
|
+
|
|
43
|
+
This only removes the re-export from @tailor-platform/sdk/runtime. It does
|
|
44
|
+
not affect the ambient tailor.workflow.execJobFunction global, which stays
|
|
45
|
+
fully supported and is what .start() itself compiles down to at build time.
|
|
46
|
+
This codemod does not rewrite ambient tailor.workflow.execJobFunction(...)
|
|
47
|
+
call sites, since removing the import re-export does not affect them — but
|
|
48
|
+
if such a call site sits inside workflow job source and calls another job
|
|
49
|
+
by name, a separate build-time check already rejects it; migrate that call
|
|
50
|
+
to the target job's own .start() method too.
|
|
51
|
+
|
|
52
|
+
If the job name passed to execJobFunction is not a string literal (a truly
|
|
53
|
+
dynamic dispatch), there is currently no supported replacement — .start()
|
|
54
|
+
only targets a statically known job. Flag this case for a human instead of
|
|
55
|
+
guessing a rewrite.
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
</details>
|
|
59
|
+
|
|
60
|
+
## function test-run → function run
|
|
61
|
+
|
|
62
|
+
**Migration:** Partially automatic
|
|
63
|
+
|
|
64
|
+
Rename `tailor function test-run` invocations to `tailor function run`. `test-run` remains as a deprecated alias until it is removed in v3.
|
|
65
|
+
|
|
66
|
+
Before:
|
|
67
|
+
|
|
68
|
+
```sh
|
|
69
|
+
tailor function test-run resolvers/add.ts --arg '{"a":1,"b":2}'
|
|
70
|
+
```
|
|
71
|
+
|
|
72
|
+
After:
|
|
73
|
+
|
|
74
|
+
```sh
|
|
75
|
+
tailor function run resolvers/add.ts --arg '{"a":1,"b":2}'
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
<details>
|
|
79
|
+
<summary>Prompt for an AI agent (to finish the cases the codemod could not migrate)</summary>
|
|
80
|
+
|
|
81
|
+
```text
|
|
82
|
+
The `tailor function test-run` subcommand is renamed to `tailor function run`;
|
|
83
|
+
the old name is removed in v3. Replace any remaining `function test-run`
|
|
84
|
+
invocations the codemod did not rewrite (e.g. wrapped across lines or invoked
|
|
85
|
+
through a package runner such as `npx @tailor-platform/sdk`) with
|
|
86
|
+
`function run`. Leave prose that merely mentions the old subcommand name
|
|
87
|
+
unchanged unless it documents a command to type.
|
|
88
|
+
```
|
|
89
|
+
|
|
90
|
+
</details>
|
|
91
|
+
|
|
92
|
+
## setup branch --branch → --target
|
|
93
|
+
|
|
94
|
+
**Migration:** Partially automatic
|
|
95
|
+
|
|
96
|
+
Rename the `--branch` option of `tailor setup branch` invocations to `--target`. `--branch` remains as a deprecated alias until it is removed in v3. The `--branch` option of `setup tag`, `setup preview`, and `setup coordinate` is unchanged.
|
|
97
|
+
|
|
98
|
+
Before:
|
|
99
|
+
|
|
100
|
+
```sh
|
|
101
|
+
tailor setup branch --name my-app-stg --branch main
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
After:
|
|
105
|
+
|
|
106
|
+
```sh
|
|
107
|
+
tailor setup branch --name my-app-stg --target main
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
<details>
|
|
111
|
+
<summary>Prompt for an AI agent (to finish the cases the codemod could not migrate)</summary>
|
|
112
|
+
|
|
113
|
+
```text
|
|
114
|
+
The `--branch` option of `tailor setup branch` is renamed to `--target`;
|
|
115
|
+
the old spelling is removed in v3. Replace any remaining `--branch` options of
|
|
116
|
+
`setup branch` invocations the codemod did not rewrite (e.g. wrapped across
|
|
117
|
+
lines or invoked through a package runner such as `npx @tailor-platform/sdk`)
|
|
118
|
+
with `--target`. Do not touch the `--branch` option of `setup tag`,
|
|
119
|
+
`setup preview`, or `setup coordinate`, which keeps its name, and leave prose
|
|
120
|
+
that merely mentions the option unchanged unless it documents a command to type.
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
</details>
|
package/docs/plugin/custom.md
CHANGED
|
@@ -18,22 +18,22 @@ const myPlugin: Plugin = {
|
|
|
18
18
|
export default myPlugin; // Required: must be default export
|
|
19
19
|
```
|
|
20
20
|
|
|
21
|
-
This is required so that other plugins and generation-time hooks can use plugin-generated TailorDB tables via `
|
|
21
|
+
This is required so that other plugins and generation-time hooks can use plugin-generated TailorDB tables via `getGeneratedTable()`.
|
|
22
22
|
|
|
23
23
|
## Plugin Interface
|
|
24
24
|
|
|
25
25
|
```typescript
|
|
26
|
-
interface Plugin<
|
|
26
|
+
interface Plugin<TableConfig = unknown, PluginConfig = unknown> {
|
|
27
27
|
readonly id: string;
|
|
28
28
|
readonly description: string;
|
|
29
29
|
readonly importPath?: string;
|
|
30
|
-
readonly
|
|
30
|
+
readonly tableConfigRequired?: boolean | ((pluginConfig?: PluginConfig) => boolean);
|
|
31
31
|
readonly pluginConfig?: PluginConfig;
|
|
32
32
|
|
|
33
33
|
// Definition-time hooks
|
|
34
|
-
|
|
35
|
-
context:
|
|
36
|
-
):
|
|
34
|
+
onTableLoaded?(
|
|
35
|
+
context: PluginTableProcessContext<TableConfig, PluginConfig>,
|
|
36
|
+
): TablePluginOutput | Promise<TablePluginOutput>;
|
|
37
37
|
onNamespaceLoaded?(
|
|
38
38
|
context: PluginNamespaceProcessContext<PluginConfig>,
|
|
39
39
|
): PluginOutput | Promise<PluginOutput>;
|
|
@@ -51,34 +51,34 @@ interface Plugin<TypeConfig = unknown, PluginConfig = unknown> {
|
|
|
51
51
|
}
|
|
52
52
|
```
|
|
53
53
|
|
|
54
|
-
| Property
|
|
55
|
-
|
|
|
56
|
-
| `id`
|
|
57
|
-
| `description`
|
|
58
|
-
| `importPath`
|
|
59
|
-
| `
|
|
60
|
-
| `pluginConfig`
|
|
54
|
+
| Property | Required | Description |
|
|
55
|
+
| --------------------- | -------------------------------- | ------------------------------------------------------------------------------------------------ |
|
|
56
|
+
| `id` | Yes | Unique plugin identifier (e.g., `"@my-company/soft-delete"`) |
|
|
57
|
+
| `description` | Yes | Human-readable description |
|
|
58
|
+
| `importPath` | When using definition-time hooks | Path resolvable from `tailor.config.ts` directory. Used for import statements in generated code. |
|
|
59
|
+
| `tableConfigRequired` | No | Whether per-table config is required when attaching via `.plugin()`. Default: optional. |
|
|
60
|
+
| `pluginConfig` | No | Plugin-level config passed via `definePlugins()`. Set via factory function. |
|
|
61
61
|
|
|
62
62
|
## Hook Reference
|
|
63
63
|
|
|
64
|
-
###
|
|
64
|
+
### onTableLoaded
|
|
65
65
|
|
|
66
66
|
**Trigger**: Called once for each TailorDB table that has `.plugin({ pluginId: config })` attached.
|
|
67
67
|
|
|
68
|
-
**Context** (`
|
|
68
|
+
**Context** (`PluginTableProcessContext`):
|
|
69
69
|
|
|
70
70
|
| Field | Type | Description |
|
|
71
71
|
| -------------- | ----------------- | ------------------------------------------ |
|
|
72
|
-
| `
|
|
73
|
-
| `
|
|
72
|
+
| `table` | `TailorAnyDBType` | The TailorDB table being processed |
|
|
73
|
+
| `tableConfig` | `TableConfig` | Per-table config from `.plugin()` |
|
|
74
74
|
| `pluginConfig` | `PluginConfig` | Plugin-level config from `definePlugins()` |
|
|
75
75
|
| `namespace` | `string` | Namespace of the TailorDB table |
|
|
76
76
|
|
|
77
|
-
**Returns** (`
|
|
77
|
+
**Returns** (`TablePluginOutput`):
|
|
78
78
|
|
|
79
79
|
| Field | Type | Description |
|
|
80
80
|
| ----------- | ----------------------------------------------- | ------------------------------------------------------ |
|
|
81
|
-
| `
|
|
81
|
+
| `tables` | `Record<string, TailorAnyDBType>` | Additional TailorDB tables to generate (keyed by kind) |
|
|
82
82
|
| `resolvers` | `PluginGeneratedResolver[]` | Additional resolvers to generate |
|
|
83
83
|
| `executors` | `PluginGeneratedExecutor[]` | Additional executors to generate |
|
|
84
84
|
| `extends` | `{ fields?: Record<string, TailorAnyDBField> }` | Fields to add to the source table |
|
|
@@ -90,12 +90,12 @@ interface Plugin<TypeConfig = unknown, PluginConfig = unknown> {
|
|
|
90
90
|
- Generate executors triggered by record events on the source table
|
|
91
91
|
|
|
92
92
|
```typescript
|
|
93
|
-
|
|
94
|
-
const {
|
|
93
|
+
onTableLoaded(context) {
|
|
94
|
+
const { table, tableConfig, namespace } = context;
|
|
95
95
|
return {
|
|
96
|
-
|
|
96
|
+
tables: { archive: db.table(`Deleted_${table.name}`, { ... }) },
|
|
97
97
|
extends: { fields: { deletedAt: db.datetime({ optional: true }) } },
|
|
98
|
-
executors: [{ name: `${
|
|
98
|
+
executors: [{ name: `${table.name}-on-delete`, resolve: async () => await import("./on-delete"), context: { sourceTable: table, namespace } }],
|
|
99
99
|
};
|
|
100
100
|
},
|
|
101
101
|
```
|
|
@@ -113,7 +113,7 @@ onTypeLoaded(context) {
|
|
|
113
113
|
|
|
114
114
|
**Returns** (`PluginOutput`):
|
|
115
115
|
|
|
116
|
-
Same as `
|
|
116
|
+
Same as `TablePluginOutput` but without `extends` (namespace plugins cannot extend a source table).
|
|
117
117
|
|
|
118
118
|
**Use cases**:
|
|
119
119
|
|
|
@@ -122,7 +122,7 @@ Same as `TypePluginOutput` but without `extends` (namespace plugins cannot exten
|
|
|
122
122
|
```typescript
|
|
123
123
|
onNamespaceLoaded(context) {
|
|
124
124
|
return {
|
|
125
|
-
|
|
125
|
+
tables: { auditLog: db.table("AuditLog", { action: db.string(), ... }) },
|
|
126
126
|
};
|
|
127
127
|
},
|
|
128
128
|
```
|
|
@@ -146,7 +146,7 @@ onNamespaceLoaded(context) {
|
|
|
146
146
|
| Field | Type | Description |
|
|
147
147
|
| ------------------- | ------------------------------------------ | ------------------------------------- |
|
|
148
148
|
| `namespace` | `string` | Namespace name |
|
|
149
|
-
| `
|
|
149
|
+
| `tables` | `Record<string, TailorDBType>` | All finalized tables in the namespace |
|
|
150
150
|
| `sourceInfo` | `ReadonlyMap<string, TypeSourceInfoEntry>` | Source file info for each table |
|
|
151
151
|
| `pluginAttachments` | `ReadonlyMap<string, PluginAttachment[]>` | Plugin configs attached to each table |
|
|
152
152
|
|
|
@@ -165,11 +165,11 @@ onNamespaceLoaded(context) {
|
|
|
165
165
|
|
|
166
166
|
```typescript
|
|
167
167
|
onTailorDBReady(ctx) {
|
|
168
|
-
const
|
|
169
|
-
Object.values(ns.
|
|
168
|
+
const allTables = ctx.tailordb.flatMap((ns) =>
|
|
169
|
+
Object.values(ns.tables).map((table) => table.name),
|
|
170
170
|
);
|
|
171
171
|
return {
|
|
172
|
-
files: [{ path: `${ctx.baseDir}/
|
|
172
|
+
files: [{ path: `${ctx.baseDir}/tables.ts`, content: `export const tables = ${JSON.stringify(allTables)};\n` }],
|
|
173
173
|
};
|
|
174
174
|
},
|
|
175
175
|
```
|
|
@@ -233,7 +233,7 @@ All fields from `ResolverReadyContext`, plus:
|
|
|
233
233
|
```typescript
|
|
234
234
|
onExecutorReady(ctx) {
|
|
235
235
|
const summary = {
|
|
236
|
-
|
|
236
|
+
tables: ctx.tailordb.flatMap((ns) => Object.keys(ns.tables)),
|
|
237
237
|
resolvers: ctx.resolvers.flatMap((ns) => Object.keys(ns.resolvers)),
|
|
238
238
|
executors: Object.keys(ctx.executors),
|
|
239
239
|
};
|
|
@@ -262,8 +262,8 @@ All context and result types are exported from `@tailor-platform/sdk`:
|
|
|
262
262
|
```typescript
|
|
263
263
|
import type {
|
|
264
264
|
Plugin,
|
|
265
|
-
|
|
266
|
-
|
|
265
|
+
PluginTableProcessContext,
|
|
266
|
+
TablePluginOutput,
|
|
267
267
|
PluginOutput,
|
|
268
268
|
TailorDBReadyContext,
|
|
269
269
|
ResolverReadyContext,
|
|
@@ -274,34 +274,34 @@ import type {
|
|
|
274
274
|
} from "@tailor-platform/sdk";
|
|
275
275
|
```
|
|
276
276
|
|
|
277
|
-
##
|
|
277
|
+
## getGeneratedTable Helper
|
|
278
278
|
|
|
279
|
-
The SDK provides an async `
|
|
279
|
+
The SDK provides an async `getGeneratedTable()` helper function to retrieve plugin-generated TailorDB tables. This enables plugins and other tools to work with tables generated by plugins.
|
|
280
280
|
|
|
281
281
|
```typescript
|
|
282
282
|
import { join } from "node:path";
|
|
283
|
-
import {
|
|
283
|
+
import { getGeneratedTable } from "@tailor-platform/sdk/plugin";
|
|
284
284
|
import { customer } from "./tailordb/customer";
|
|
285
285
|
|
|
286
286
|
const configPath = join(import.meta.dirname, "./tailor.config.ts");
|
|
287
287
|
|
|
288
288
|
// Table-attached plugin
|
|
289
|
-
const DeletedCustomer = await
|
|
289
|
+
const DeletedCustomer = await getGeneratedTable(
|
|
290
290
|
configPath,
|
|
291
291
|
"@example/soft-delete",
|
|
292
292
|
customer,
|
|
293
293
|
"archive",
|
|
294
294
|
);
|
|
295
295
|
|
|
296
|
-
// Namespace plugin (pass null as
|
|
297
|
-
const AuditLog = await
|
|
296
|
+
// Namespace plugin (pass null as sourceTable)
|
|
297
|
+
const AuditLog = await getGeneratedTable(configPath, "@example/audit-log", null, "auditLog");
|
|
298
298
|
```
|
|
299
299
|
|
|
300
300
|
**Parameters:**
|
|
301
301
|
|
|
302
302
|
- `configPath`: Path to `tailor.config.ts` (absolute or relative to cwd)
|
|
303
303
|
- `pluginId`: The plugin's unique identifier (e.g., `"@example/soft-delete"`)
|
|
304
|
-
- `
|
|
304
|
+
- `sourceTable`: The TailorDB table that the plugin is attached to (`null` for namespace plugins)
|
|
305
305
|
- `kind`: The generated table kind (e.g., `"archive"`, `"auditLog"`)
|
|
306
306
|
|
|
307
307
|
**How it works:**
|
|
@@ -309,7 +309,7 @@ const AuditLog = await getGeneratedType(configPath, "@example/audit-log", null,
|
|
|
309
309
|
1. Loads and caches the config from the given path
|
|
310
310
|
2. Finds the plugin by ID from `definePlugins()` exports
|
|
311
311
|
3. Auto-resolves the namespace from config
|
|
312
|
-
4. Calls the plugin's `
|
|
312
|
+
4. Calls the plugin's `onTableLoaded()` or `onNamespaceLoaded()` method
|
|
313
313
|
5. Caches the result to avoid redundant processing
|
|
314
314
|
6. Returns the generated table matching the specified kind
|
|
315
315
|
|
|
@@ -317,14 +317,14 @@ const AuditLog = await getGeneratedType(configPath, "@example/audit-log", null,
|
|
|
317
317
|
|
|
318
318
|
### Definition-time Plugin (Soft Delete)
|
|
319
319
|
|
|
320
|
-
A plugin that adds soft delete functionality via `
|
|
320
|
+
A plugin that adds soft delete functionality via `onTableLoaded`:
|
|
321
321
|
|
|
322
322
|
```typescript
|
|
323
323
|
// plugins/soft-delete/plugin.ts
|
|
324
324
|
import { db } from "@tailor-platform/sdk";
|
|
325
|
-
import type { Plugin,
|
|
325
|
+
import type { Plugin, PluginTableProcessContext, TablePluginOutput } from "@tailor-platform/sdk";
|
|
326
326
|
|
|
327
|
-
interface
|
|
327
|
+
interface SoftDeleteTableConfig {
|
|
328
328
|
archiveReason?: boolean;
|
|
329
329
|
retentionDays?: number;
|
|
330
330
|
}
|
|
@@ -332,28 +332,28 @@ interface SoftDeleteConfig {
|
|
|
332
332
|
interface SoftDeletePluginConfig {
|
|
333
333
|
archiveTablePrefix?: string;
|
|
334
334
|
defaultRetentionDays?: number;
|
|
335
|
-
|
|
335
|
+
requireTableConfig?: boolean;
|
|
336
336
|
}
|
|
337
337
|
|
|
338
338
|
function processSoftDelete(
|
|
339
|
-
context:
|
|
340
|
-
):
|
|
341
|
-
const {
|
|
339
|
+
context: PluginTableProcessContext<SoftDeleteTableConfig, SoftDeletePluginConfig>,
|
|
340
|
+
): TablePluginOutput {
|
|
341
|
+
const { table, tableConfig, pluginConfig, namespace } = context;
|
|
342
342
|
const prefix = pluginConfig?.archiveTablePrefix ?? "Deleted_";
|
|
343
343
|
|
|
344
344
|
// Generate archive table
|
|
345
|
-
const
|
|
346
|
-
.table(`${prefix}${
|
|
345
|
+
const archiveTable = db
|
|
346
|
+
.table(`${prefix}${table.name}`, {
|
|
347
347
|
originalId: db.uuid().description("ID of the deleted record"),
|
|
348
348
|
originalData: db.string().description("JSON snapshot of deleted record"),
|
|
349
349
|
deletedAt: db.datetime().description("When the record was deleted"),
|
|
350
350
|
deletedBy: db.uuid().description("User who deleted the record"),
|
|
351
|
-
...(
|
|
351
|
+
...(tableConfig.archiveReason && {
|
|
352
352
|
reason: db.string({ optional: true }).description("Reason for deletion"),
|
|
353
353
|
}),
|
|
354
354
|
...db.fields.timestamps(),
|
|
355
355
|
})
|
|
356
|
-
.description(`Archive for deleted ${
|
|
356
|
+
.description(`Archive for deleted ${table.name} records`);
|
|
357
357
|
|
|
358
358
|
// Extend source table with deletedAt field
|
|
359
359
|
const extendFields = {
|
|
@@ -361,15 +361,15 @@ function processSoftDelete(
|
|
|
361
361
|
};
|
|
362
362
|
|
|
363
363
|
return {
|
|
364
|
-
|
|
364
|
+
tables: { archive: archiveTable },
|
|
365
365
|
extends: { fields: extendFields },
|
|
366
366
|
executors: [
|
|
367
367
|
{
|
|
368
|
-
name: `${
|
|
368
|
+
name: `${table.name.toLowerCase()}-on-delete`,
|
|
369
369
|
resolve: async () => await import("./executors/on-delete"),
|
|
370
370
|
context: {
|
|
371
|
-
|
|
372
|
-
|
|
371
|
+
sourceTable: table,
|
|
372
|
+
archiveTable,
|
|
373
373
|
namespace,
|
|
374
374
|
},
|
|
375
375
|
},
|
|
@@ -379,14 +379,14 @@ function processSoftDelete(
|
|
|
379
379
|
|
|
380
380
|
function createSoftDeletePlugin(
|
|
381
381
|
pluginConfig?: SoftDeletePluginConfig,
|
|
382
|
-
): Plugin<
|
|
382
|
+
): Plugin<SoftDeleteTableConfig, SoftDeletePluginConfig> {
|
|
383
383
|
return {
|
|
384
384
|
id: "@example/soft-delete",
|
|
385
385
|
description: "Adds soft delete with archive functionality",
|
|
386
386
|
importPath: "./plugins/soft-delete",
|
|
387
387
|
pluginConfig,
|
|
388
|
-
|
|
389
|
-
|
|
388
|
+
tableConfigRequired: (config) => config?.requireTableConfig === true,
|
|
389
|
+
onTableLoaded: processSoftDelete,
|
|
390
390
|
};
|
|
391
391
|
}
|
|
392
392
|
|
|
@@ -403,24 +403,24 @@ import { withPluginContext } from "@tailor-platform/sdk/plugin";
|
|
|
403
403
|
import { getDB } from "generated/tailordb";
|
|
404
404
|
|
|
405
405
|
interface SoftDeleteContext {
|
|
406
|
-
|
|
407
|
-
|
|
406
|
+
sourceTable: TailorAnyDBType;
|
|
407
|
+
archiveTable: TailorAnyDBType;
|
|
408
408
|
namespace: string;
|
|
409
409
|
}
|
|
410
410
|
|
|
411
411
|
export default withPluginContext((ctx: SoftDeleteContext) => {
|
|
412
|
-
const {
|
|
412
|
+
const { sourceTable, archiveTable, namespace } = ctx;
|
|
413
413
|
|
|
414
414
|
return createExecutor({
|
|
415
|
-
name: `${
|
|
416
|
-
description: `Archives deleted ${
|
|
417
|
-
trigger: recordDeletedTrigger({ type:
|
|
415
|
+
name: `${sourceTable.name.toLowerCase()}-on-delete`,
|
|
416
|
+
description: `Archives deleted ${sourceTable.name} records`,
|
|
417
|
+
trigger: recordDeletedTrigger({ type: sourceTable }),
|
|
418
418
|
operation: {
|
|
419
419
|
kind: "function",
|
|
420
420
|
body: async ({ oldRecord, user }) => {
|
|
421
421
|
const db = getDB(namespace as "tailordb");
|
|
422
422
|
await db
|
|
423
|
-
.insertInto(
|
|
423
|
+
.insertInto(archiveTable.name)
|
|
424
424
|
.values({
|
|
425
425
|
originalId: oldRecord.id,
|
|
426
426
|
originalData: JSON.stringify(oldRecord),
|
|
@@ -461,28 +461,28 @@ export const customer = db
|
|
|
461
461
|
});
|
|
462
462
|
```
|
|
463
463
|
|
|
464
|
-
### Generation-only Plugin (
|
|
464
|
+
### Generation-only Plugin (Table List)
|
|
465
465
|
|
|
466
466
|
A plugin that only uses `onTailorDBReady` to generate output files:
|
|
467
467
|
|
|
468
468
|
```typescript
|
|
469
469
|
import type { Plugin, GeneratorResult } from "@tailor-platform/sdk";
|
|
470
470
|
|
|
471
|
-
const
|
|
472
|
-
id: "@example/
|
|
471
|
+
const tableListPlugin: Plugin = {
|
|
472
|
+
id: "@example/table-list",
|
|
473
473
|
description: "Generates a list of all TailorDB table names",
|
|
474
474
|
|
|
475
475
|
onTailorDBReady(ctx): GeneratorResult {
|
|
476
|
-
const
|
|
477
|
-
Object.
|
|
478
|
-
name:
|
|
479
|
-
fieldCount: Object.keys(
|
|
476
|
+
const allTables = ctx.tailordb.flatMap((ns) =>
|
|
477
|
+
Object.values(ns.tables).map((table) => ({
|
|
478
|
+
name: table.name,
|
|
479
|
+
fieldCount: Object.keys(table.fields).length,
|
|
480
480
|
namespace: ns.namespace,
|
|
481
481
|
})),
|
|
482
482
|
);
|
|
483
|
-
const content = `// Generated
|
|
483
|
+
const content = `// Generated table list\nexport const tables = ${JSON.stringify(allTables, null, 2)} as const;\n`;
|
|
484
484
|
return {
|
|
485
|
-
files: [{ path: `${ctx.baseDir}/
|
|
485
|
+
files: [{ path: `${ctx.baseDir}/tables.ts`, content }],
|
|
486
486
|
};
|
|
487
487
|
},
|
|
488
488
|
};
|
|
@@ -499,15 +499,17 @@ const plugin: Plugin = {
|
|
|
499
499
|
importPath: "./plugins/hybrid",
|
|
500
500
|
|
|
501
501
|
// Definition-time: Generate additional tables from attached source tables
|
|
502
|
-
|
|
503
|
-
return {
|
|
502
|
+
onTableLoaded(context) {
|
|
503
|
+
return { tables: { derived: createDerivedTable(context.table) } };
|
|
504
504
|
},
|
|
505
505
|
|
|
506
506
|
// Generation-time: Generate output files from all finalized tables
|
|
507
507
|
onTailorDBReady(ctx) {
|
|
508
|
-
const
|
|
508
|
+
const allTables = ctx.tailordb.flatMap((ns) =>
|
|
509
|
+
Object.values(ns.tables).map((table) => table.name),
|
|
510
|
+
);
|
|
509
511
|
return {
|
|
510
|
-
files: [{ path: `${ctx.baseDir}/output.ts`, content: generateCode(
|
|
512
|
+
files: [{ path: `${ctx.baseDir}/output.ts`, content: generateCode(allTables) }],
|
|
511
513
|
};
|
|
512
514
|
},
|
|
513
515
|
};
|
|
@@ -515,13 +517,13 @@ const plugin: Plugin = {
|
|
|
515
517
|
|
|
516
518
|
## Adding Type Safety
|
|
517
519
|
|
|
518
|
-
### Plugin-level type safety (
|
|
520
|
+
### Plugin-level type safety (TableConfig / PluginConfig)
|
|
519
521
|
|
|
520
|
-
Use TypeScript type parameters on `Plugin<
|
|
521
|
-
in `
|
|
522
|
+
Use TypeScript type parameters on `Plugin<TableConfig, PluginConfig>` to get type-safe config
|
|
523
|
+
in `onTableLoaded` and `onNamespaceLoaded` methods:
|
|
522
524
|
|
|
523
525
|
```typescript
|
|
524
|
-
interface
|
|
526
|
+
interface MyTableConfig {
|
|
525
527
|
archiveReason?: boolean;
|
|
526
528
|
}
|
|
527
529
|
|
|
@@ -529,11 +531,11 @@ interface MyPluginConfig {
|
|
|
529
531
|
prefix?: string;
|
|
530
532
|
}
|
|
531
533
|
|
|
532
|
-
const plugin: Plugin<
|
|
534
|
+
const plugin: Plugin<MyTableConfig, MyPluginConfig> = {
|
|
533
535
|
id: "@example/my-plugin",
|
|
534
536
|
// ...
|
|
535
|
-
|
|
536
|
-
// context.
|
|
537
|
+
onTableLoaded(context) {
|
|
538
|
+
// context.tableConfig is MyTableConfig
|
|
537
539
|
// context.pluginConfig is MyPluginConfig
|
|
538
540
|
},
|
|
539
541
|
};
|
|
@@ -546,6 +548,9 @@ for the `PluginConfigs` interface. Plugin authors should ship this in their pack
|
|
|
546
548
|
|
|
547
549
|
```typescript
|
|
548
550
|
// your-plugin/types.d.ts (shipped with your plugin package)
|
|
551
|
+
export {}; // required: a top-level import/export makes this file augment
|
|
552
|
+
// the module below instead of replacing its other exports
|
|
553
|
+
|
|
549
554
|
declare module "@tailor-platform/sdk" {
|
|
550
555
|
interface PluginConfigs<Fields extends string> {
|
|
551
556
|
"@example/soft-delete": {
|
|
@@ -559,6 +564,8 @@ declare module "@tailor-platform/sdk" {
|
|
|
559
564
|
The `Fields` type parameter provides field names from the table being configured, enabling field-aware configurations:
|
|
560
565
|
|
|
561
566
|
```typescript
|
|
567
|
+
export {};
|
|
568
|
+
|
|
562
569
|
declare module "@tailor-platform/sdk" {
|
|
563
570
|
interface PluginConfigs<Fields extends string> {
|
|
564
571
|
"@example/i18n": {
|
|
@@ -567,3 +574,41 @@ declare module "@tailor-platform/sdk" {
|
|
|
567
574
|
}
|
|
568
575
|
}
|
|
569
576
|
```
|
|
577
|
+
|
|
578
|
+
### Resolving plugin-level config from a `Plugin[]` array (declaration merging)
|
|
579
|
+
|
|
580
|
+
`PluginConfig` is already available inside your own plugin's hooks via `context.pluginConfig`.
|
|
581
|
+
If other code instead needs to look up your plugin's config from a `Plugin[]` array by `id` —
|
|
582
|
+
without importing your plugin's config type — register it on the `PluginConfigRegistry`
|
|
583
|
+
interface. Plugin authors should ship this in their package's type definitions:
|
|
584
|
+
|
|
585
|
+
```typescript
|
|
586
|
+
// your-plugin/types.d.ts (shipped with your plugin package)
|
|
587
|
+
export {}; // required: a top-level import/export makes this file augment
|
|
588
|
+
// the module below instead of replacing its other exports
|
|
589
|
+
|
|
590
|
+
declare module "@tailor-platform/sdk/plugin" {
|
|
591
|
+
interface PluginConfigRegistry {
|
|
592
|
+
"@example/soft-delete": {
|
|
593
|
+
archiveTablePrefix?: string;
|
|
594
|
+
};
|
|
595
|
+
}
|
|
596
|
+
}
|
|
597
|
+
```
|
|
598
|
+
|
|
599
|
+
This only registers the type; it does not provide a function to read it. Callers resolve a
|
|
600
|
+
registered config from `Plugin[]` using the public `Plugin` and `PluginConfigRegistry` types:
|
|
601
|
+
|
|
602
|
+
```typescript
|
|
603
|
+
import type { Plugin } from "@tailor-platform/sdk";
|
|
604
|
+
import type { PluginConfigRegistry } from "@tailor-platform/sdk/plugin";
|
|
605
|
+
|
|
606
|
+
function resolvePluginConfig<Id extends keyof PluginConfigRegistry>(
|
|
607
|
+
plugins: readonly Plugin[],
|
|
608
|
+
id: Id,
|
|
609
|
+
): PluginConfigRegistry[Id] | undefined {
|
|
610
|
+
return plugins.find((p) => p.id === id)?.pluginConfig as PluginConfigRegistry[Id] | undefined;
|
|
611
|
+
}
|
|
612
|
+
```
|
|
613
|
+
|
|
614
|
+
An `id` that isn't registered fails to compile, instead of silently resolving to `unknown`.
|
package/docs/plugin/index.md
CHANGED
|
@@ -73,7 +73,7 @@ export const customer = db
|
|
|
73
73
|
### Per-table Config Requirement
|
|
74
74
|
|
|
75
75
|
Per-table config is optional by default. Plugin authors can change this with
|
|
76
|
-
`
|
|
76
|
+
`tableConfigRequired` (boolean or function). When a function is used, it receives
|
|
77
77
|
the plugin-level config from `definePlugins()`.
|
|
78
78
|
|
|
79
79
|
### Global Plugin Configuration
|
|
@@ -116,7 +116,7 @@ Plugins have 5 hooks across two lifecycle phases. Each hook fires at a specific
|
|
|
116
116
|
tailor generate
|
|
117
117
|
│
|
|
118
118
|
├─ Load TailorDB tables
|
|
119
|
-
│ ├─
|
|
119
|
+
│ ├─ onTableLoaded ← per table with .plugin() attached
|
|
120
120
|
│ └─ onNamespaceLoaded ← once per namespace (namespace plugins)
|
|
121
121
|
│
|
|
122
122
|
├─ Resolve Auth
|
|
@@ -136,7 +136,7 @@ tailor generate
|
|
|
136
136
|
|
|
137
137
|
| Hook | Trigger | Can do |
|
|
138
138
|
| ------------------- | ------------------------------------ | ----------------------------------------------------------------- |
|
|
139
|
-
| `
|
|
139
|
+
| `onTableLoaded` | Each table with `.plugin()` attached | Generate tables, resolvers, executors; extend source table fields |
|
|
140
140
|
| `onNamespaceLoaded` | Once per namespace | Generate tables, resolvers, executors |
|
|
141
141
|
|
|
142
142
|
These hooks produce TailorDB tables, resolvers, and executors that become part of the application. Requires `importPath` on the plugin.
|
package/docs/quickstart.md
CHANGED
|
@@ -12,7 +12,7 @@ Contact us [here](https://www.tailor.tech/demo) to get started.
|
|
|
12
12
|
|
|
13
13
|
### Install Node.js
|
|
14
14
|
|
|
15
|
-
The SDK requires Node.js 22.
|
|
15
|
+
The SDK requires Node.js 22.18.0 or later. Install Node.js via your package manager by following the official Node.js instructions.
|
|
16
16
|
|
|
17
17
|
Alternatively, you can use [Bun](https://bun.sh/) as the runtime.
|
|
18
18
|
|