@tailor-platform/sdk 2.2.0 → 2.3.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.
Files changed (55) hide show
  1. package/CHANGELOG.md +115 -0
  2. package/dist/application-BZfk4HKm.mjs +3 -0
  3. package/dist/{application-BpLeawBg.mjs → application-F-nl107y.mjs} +118 -24
  4. package/dist/application-F-nl107y.mjs.map +1 -0
  5. package/dist/cli/commands/tailordb/migrate/diff-calculator.d.mts +43 -20
  6. package/dist/cli/commands/tailordb/migrate/generate.d.mts +6 -0
  7. package/dist/cli/commands/tailordb/migrate/rename-detection.d.mts +22 -0
  8. package/dist/cli/commands/tailordb/migrate/snapshot-types.d.mts +1 -1
  9. package/dist/cli/commands/tailordb/migrate/snapshot.d.mts +26 -7
  10. package/dist/cli/lib.mjs +2 -2
  11. package/dist/cli/main.mjs +203 -42
  12. package/dist/cli/main.mjs.map +1 -1
  13. package/dist/cli/ts-hook.mjs +52 -7
  14. package/dist/completion/zsh-worker.zsh +23 -3
  15. package/dist/configure/index.d.mts +2 -2
  16. package/dist/configure/index.mjs +90 -23
  17. package/dist/configure/index.mjs.map +1 -1
  18. package/dist/configure/services/index.d.mts +2 -2
  19. package/dist/configure/services/workflow/index.d.mts +2 -2
  20. package/dist/configure/services/workflow/wait-point.d.mts +72 -13
  21. package/dist/{errors-CWj21238.mjs → errors-BVb6vYGy.mjs} +16 -2
  22. package/dist/{errors-CWj21238.mjs.map → errors-BVb6vYGy.mjs.map} +1 -1
  23. package/dist/kysely/index.d.mts +2 -1
  24. package/dist/kysely/index.mjs.map +1 -1
  25. package/dist/{register-ts-hook-CTth1eqj.mjs → register-ts-hook-ClI226n2.mjs} +2034 -511
  26. package/dist/register-ts-hook-ClI226n2.mjs.map +1 -0
  27. package/dist/{service-goqlJJgA.mjs → service-C_WpbKHu.mjs} +38 -4
  28. package/dist/service-C_WpbKHu.mjs.map +1 -0
  29. package/dist/service-D1RCdzIL.mjs +3 -0
  30. package/dist/{service-CCwl3Avt.mjs → service-hZskxZmg.mjs} +2 -2
  31. package/dist/{service-CCwl3Avt.mjs.map → service-hZskxZmg.mjs.map} +1 -1
  32. package/dist/vitest/index.mjs +83 -1
  33. package/dist/vitest/index.mjs.map +1 -1
  34. package/dist/vitest/mocks/file.d.mts +1 -1
  35. package/dist/vitest/mocks/workflow.d.mts +13 -1
  36. package/dist/wait-point-invoker-__oE88_P.mjs +148 -0
  37. package/dist/wait-point-invoker-__oE88_P.mjs.map +1 -0
  38. package/dist/wait-point-registry-TL99zotw.mjs +47 -0
  39. package/dist/wait-point-registry-TL99zotw.mjs.map +1 -0
  40. package/docs/cli/setup.md +14 -1
  41. package/docs/cli/tailordb.md +9 -6
  42. package/docs/cli-reference.md +2 -1
  43. package/docs/github-actions.md +73 -28
  44. package/docs/migration/v2.md +54 -0
  45. package/docs/services/tailordb-migration.md +137 -35
  46. package/docs/services/workflow.md +52 -2
  47. package/docs/testing.md +12 -0
  48. package/package.json +4 -4
  49. package/dist/application-BpLeawBg.mjs.map +0 -1
  50. package/dist/application-BxLLiLsr.mjs +0 -3
  51. package/dist/register-ts-hook-CTth1eqj.mjs.map +0 -1
  52. package/dist/service-_XmjSEGr.mjs +0 -3
  53. package/dist/service-goqlJJgA.mjs.map +0 -1
  54. package/dist/test-env-key-D7UkZp99.mjs +0 -75
  55. package/dist/test-env-key-D7UkZp99.mjs.map +0 -1
@@ -30,7 +30,7 @@ import { Trigger } from "./executor/trigger/index.mjs";
30
30
  import { createExecutor } from "./executor/executor.mjs";
31
31
  import "./executor/index.mjs";
32
32
  import { defineWorkflowExecutionPolicies, defineWorkflowExecutionPolicy } from "./workflow/execution-policy.mjs";
33
- import { WaitPointInstance, createWaitPoint, createWaitPoints } from "./workflow/wait-point.mjs";
33
+ import { ParameterizedWaitPointInstance, WaitPointInstance, createWaitPoint, createWaitPoints } from "./workflow/wait-point.mjs";
34
34
  import "./workflow/index.mjs";
35
35
  import { defineStaticWebSite } from "./staticwebsite/index.mjs";
36
36
  import { defineAIGateway } from "./aigateway/index.mjs";
@@ -38,4 +38,4 @@ import { defineIdp } from "./idp/index.mjs";
38
38
  import { defineSecretManager } from "./secrets/index.mjs";
39
39
  import { HttpAdapter, HttpAdapterGraphQLQuery, HttpAdapterGraphQLRequest, HttpAdapterGraphQLResponse, HttpAdapterInput, HttpAdapterInputFn, HttpAdapterOutputFn, HttpAdapterRequest, HttpAdapterResponse, HttpAdapterTypedDocumentNode, createHttpAdapter } from "./http-adapter/http-adapter.mjs";
40
40
  import "./http-adapter/index.mjs";
41
- export { type AIGatewayConfig, AuthAccessTokenArgs, AuthAccessTokenIssuedArgs, AuthAccessTokenRefreshedArgs, AuthAccessTokenRevokedArgs, AuthAccessTokenTrigger, type AuthConfig, type AuthConnectionConfig, type AuthConnectionOAuth2Config, type AuthConnectionTokenResult, type AuthExternalConfig, type AuthOwnConfig, type AuthServiceInput, type BeforeLoginClaims, type BeforeLoginHookArgs, type BuiltinIdP, type ConcurrencyPolicy, type DefinedAuth, type ExecutionPolicyConcurrency, type ExecutionPolicyDefInput, type ExecutionPolicyExactInstance, type ExecutionPolicyGroupOptions, type ExecutionPolicyInstance, type ExecutionPolicyWildcardInstance, type ExecutorServiceConfig, type ExecutorServiceInput, type FederatedIdentity, type FederatedIdentityClaims, type FederatedIdentityProvider, FunctionOperation, GqlOperation, HttpAdapter, HttpAdapterGraphQLQuery, HttpAdapterGraphQLRequest, HttpAdapterGraphQLResponse, HttpAdapterInput, HttpAdapterInputFn, HttpAdapterOutputFn, HttpAdapterRequest, HttpAdapterResponse, HttpAdapterTypedDocumentNode, type IDToken, type IdPConfig, type IdPEmailConfig, type IdPExternalConfig, type IdPGqlOperations, type IdPGqlOperationsInput as IdPGqlOperationsConfig, type IdPPermission, type IdPPermissionCondition, type IdProvider as IdProviderConfig, IdpUserArgs, IdpUserCreatedArgs, IdpUserDeletedArgs, IdpUserTrigger, IdpUserUpdatedArgs, IncomingWebhookArgs, IncomingWebhookRequest, IncomingWebhookResponse, IncomingWebhookResponseConfig, IncomingWebhookTrigger, IncomingWebhookTriggerOptions, type IsAutoFilledDBField, type IsReadOnlyDBField, type OAuth2ClientInput as OAuth2Client, type OAuth2ClientGrantType, type OIDC, Operation, type PermissionCondition, type QueryType, RecordCreatedArgs, RecordDeletedArgs, RecordUpdatedArgs, type ResolvedExecutionPolicyInstance, type Resolver, ResolverExecutedArgs, ResolverExecutedTrigger, type ResolverExternalConfig, type ResolverPermission, type ResolverPermissionCondition, type ResolverPermissionPolicy, type ResolverServiceConfig, type ResolverServiceInput, type RetryPolicy, type SAML, type SCIMAttribute, type SCIMAttributeMapping, type SCIMAttributeType, type SCIMAuthorization, type SCIMConfig, type SCIMResource, ScheduleArgs, ScheduleTrigger, type SecretsConfig, type StaticWebsiteConfig, type TailorAnyDBField, type TailorAnyDBType, type TailorDBField, type TailorDBInstance, TailorDBTrigger, type TailorDBType, type TailorTypeGqlPermission, type TailorTypePermission, type TenantProvider as TenantProviderConfig, Trigger, type UserAttributeKey, type UserAttributeListKey, type UserAttributes, type UsernameFieldKey, type ValueOperand, WaitPointInstance, WebhookOperation, Workflow, WorkflowConfig, WorkflowExecutionArgs, WorkflowExecutionCompletedArgs, WorkflowExecutionResumedArgs, WorkflowExecutionRetriedArgs, WorkflowExecutionStartedArgs, WorkflowExecutionTrigger, WorkflowExecutionWaitResolvedArgs, WorkflowExecutionWaitStartedArgs, WorkflowJob, WorkflowJobContext, WorkflowJobExecutionArgs, WorkflowJobExecutionCompletedArgs, WorkflowJobExecutionStartedArgs, WorkflowJobExecutionTrigger, WorkflowJobExecutionWaitResolvedArgs, WorkflowJobExecutionWaitStartedArgs, WorkflowOperation, type WorkflowServiceConfig, type WorkflowServiceInput, authAccessTokenIssuedTrigger, authAccessTokenRefreshedTrigger, authAccessTokenRevokedTrigger, authAccessTokenTrigger, createExecutor, createHttpAdapter, createResolver, createWaitPoint, createWaitPoints, createWorkflow, createWorkflowJob, db, defineAIGateway, defineAuth, defineIdp, defineSecretManager, defineStaticWebSite, defineWorkflowExecutionPolicies, defineWorkflowExecutionPolicy, idpUserCreatedTrigger, idpUserDeletedTrigger, idpUserTrigger, idpUserUpdatedTrigger, incomingWebhookTrigger, recordCreatedTrigger, recordDeletedTrigger, recordTrigger, recordUpdatedTrigger, resolverExecutedTrigger, scheduleTrigger, unsafeAllowAllGqlPermission, unsafeAllowAllIdPPermission, unsafeAllowAllTypePermission, workflowExecutionCompletedTrigger, workflowExecutionResumedTrigger, workflowExecutionRetriedTrigger, workflowExecutionStartedTrigger, workflowExecutionTrigger, workflowExecutionWaitResolvedTrigger, workflowExecutionWaitStartedTrigger, workflowJobExecutionCompletedTrigger, workflowJobExecutionStartedTrigger, workflowJobExecutionTrigger, workflowJobExecutionWaitResolvedTrigger, workflowJobExecutionWaitStartedTrigger };
41
+ export { type AIGatewayConfig, AuthAccessTokenArgs, AuthAccessTokenIssuedArgs, AuthAccessTokenRefreshedArgs, AuthAccessTokenRevokedArgs, AuthAccessTokenTrigger, type AuthConfig, type AuthConnectionConfig, type AuthConnectionOAuth2Config, type AuthConnectionTokenResult, type AuthExternalConfig, type AuthOwnConfig, type AuthServiceInput, type BeforeLoginClaims, type BeforeLoginHookArgs, type BuiltinIdP, type ConcurrencyPolicy, type DefinedAuth, type ExecutionPolicyConcurrency, type ExecutionPolicyDefInput, type ExecutionPolicyExactInstance, type ExecutionPolicyGroupOptions, type ExecutionPolicyInstance, type ExecutionPolicyWildcardInstance, type ExecutorServiceConfig, type ExecutorServiceInput, type FederatedIdentity, type FederatedIdentityClaims, type FederatedIdentityProvider, FunctionOperation, GqlOperation, HttpAdapter, HttpAdapterGraphQLQuery, HttpAdapterGraphQLRequest, HttpAdapterGraphQLResponse, HttpAdapterInput, HttpAdapterInputFn, HttpAdapterOutputFn, HttpAdapterRequest, HttpAdapterResponse, HttpAdapterTypedDocumentNode, type IDToken, type IdPConfig, type IdPEmailConfig, type IdPExternalConfig, type IdPGqlOperations, type IdPGqlOperationsInput as IdPGqlOperationsConfig, type IdPPermission, type IdPPermissionCondition, type IdProvider as IdProviderConfig, IdpUserArgs, IdpUserCreatedArgs, IdpUserDeletedArgs, IdpUserTrigger, IdpUserUpdatedArgs, IncomingWebhookArgs, IncomingWebhookRequest, IncomingWebhookResponse, IncomingWebhookResponseConfig, IncomingWebhookTrigger, IncomingWebhookTriggerOptions, type IsAutoFilledDBField, type IsReadOnlyDBField, type OAuth2ClientInput as OAuth2Client, type OAuth2ClientGrantType, type OIDC, Operation, ParameterizedWaitPointInstance, type PermissionCondition, type QueryType, RecordCreatedArgs, RecordDeletedArgs, RecordUpdatedArgs, type ResolvedExecutionPolicyInstance, type Resolver, ResolverExecutedArgs, ResolverExecutedTrigger, type ResolverExternalConfig, type ResolverPermission, type ResolverPermissionCondition, type ResolverPermissionPolicy, type ResolverServiceConfig, type ResolverServiceInput, type RetryPolicy, type SAML, type SCIMAttribute, type SCIMAttributeMapping, type SCIMAttributeType, type SCIMAuthorization, type SCIMConfig, type SCIMResource, ScheduleArgs, ScheduleTrigger, type SecretsConfig, type StaticWebsiteConfig, type TailorAnyDBField, type TailorAnyDBType, type TailorDBField, type TailorDBInstance, TailorDBTrigger, type TailorDBType, type TailorTypeGqlPermission, type TailorTypePermission, type TenantProvider as TenantProviderConfig, Trigger, type UserAttributeKey, type UserAttributeListKey, type UserAttributes, type UsernameFieldKey, type ValueOperand, WaitPointInstance, WebhookOperation, Workflow, WorkflowConfig, WorkflowExecutionArgs, WorkflowExecutionCompletedArgs, WorkflowExecutionResumedArgs, WorkflowExecutionRetriedArgs, WorkflowExecutionStartedArgs, WorkflowExecutionTrigger, WorkflowExecutionWaitResolvedArgs, WorkflowExecutionWaitStartedArgs, WorkflowJob, WorkflowJobContext, WorkflowJobExecutionArgs, WorkflowJobExecutionCompletedArgs, WorkflowJobExecutionStartedArgs, WorkflowJobExecutionTrigger, WorkflowJobExecutionWaitResolvedArgs, WorkflowJobExecutionWaitStartedArgs, WorkflowOperation, type WorkflowServiceConfig, type WorkflowServiceInput, authAccessTokenIssuedTrigger, authAccessTokenRefreshedTrigger, authAccessTokenRevokedTrigger, authAccessTokenTrigger, createExecutor, createHttpAdapter, createResolver, createWaitPoint, createWaitPoints, createWorkflow, createWorkflowJob, db, defineAIGateway, defineAuth, defineIdp, defineSecretManager, defineStaticWebSite, defineWorkflowExecutionPolicies, defineWorkflowExecutionPolicy, idpUserCreatedTrigger, idpUserDeletedTrigger, idpUserTrigger, idpUserUpdatedTrigger, incomingWebhookTrigger, recordCreatedTrigger, recordDeletedTrigger, recordTrigger, recordUpdatedTrigger, resolverExecutedTrigger, scheduleTrigger, unsafeAllowAllGqlPermission, unsafeAllowAllIdPPermission, unsafeAllowAllTypePermission, workflowExecutionCompletedTrigger, workflowExecutionResumedTrigger, workflowExecutionRetriedTrigger, workflowExecutionStartedTrigger, workflowExecutionTrigger, workflowExecutionWaitResolvedTrigger, workflowExecutionWaitStartedTrigger, workflowJobExecutionCompletedTrigger, workflowJobExecutionStartedTrigger, workflowJobExecutionTrigger, workflowJobExecutionWaitResolvedTrigger, workflowJobExecutionWaitStartedTrigger };
@@ -4,6 +4,6 @@ import { ConcurrencyPolicy, RetryPolicy } from "../../../types/workflow.generate
4
4
  import { WorkflowJob, WorkflowJobContext, createWorkflowJob } from "./job.mjs";
5
5
  import { Workflow, WorkflowConfig, createWorkflow } from "./workflow.mjs";
6
6
  import { defineWorkflowExecutionPolicies, defineWorkflowExecutionPolicy } from "./execution-policy.mjs";
7
- import { WaitPointInstance, createWaitPoint, createWaitPoints } from "./wait-point.mjs";
7
+ import { ParameterizedWaitPointInstance, WaitPointInstance, createWaitPoint, createWaitPoints } from "./wait-point.mjs";
8
8
  import "./types.mjs";
9
- export { type ConcurrencyPolicy, type ExecutionPolicyConcurrency, type ExecutionPolicyDefInput, type ExecutionPolicyExactInstance, type ExecutionPolicyGroupOptions, type ExecutionPolicyInstance, type ExecutionPolicyWildcardInstance, type ResolvedExecutionPolicyInstance, type RetryPolicy, WaitPointInstance, Workflow, WorkflowConfig, WorkflowJob, WorkflowJobContext, type WorkflowServiceConfig, type WorkflowServiceInput, createWaitPoint, createWaitPoints, createWorkflow, createWorkflowJob, defineWorkflowExecutionPolicies, defineWorkflowExecutionPolicy };
9
+ export { type ConcurrencyPolicy, type ExecutionPolicyConcurrency, type ExecutionPolicyDefInput, type ExecutionPolicyExactInstance, type ExecutionPolicyGroupOptions, type ExecutionPolicyInstance, type ExecutionPolicyWildcardInstance, ParameterizedWaitPointInstance, type ResolvedExecutionPolicyInstance, type RetryPolicy, WaitPointInstance, Workflow, WorkflowConfig, WorkflowJob, WorkflowJobContext, type WorkflowServiceConfig, type WorkflowServiceInput, createWaitPoint, createWaitPoints, createWorkflow, createWorkflowJob, defineWorkflowExecutionPolicies, defineWorkflowExecutionPolicy };
@@ -1,4 +1,4 @@
1
- import { JsonCompatible, TypeLevelError } from "../../../types/helpers.mjs";
1
+ import { JsonCompatible, Prettify, TypeLevelError } from "../../../types/helpers.mjs";
2
2
  //#region src/configure/services/workflow/wait-point.d.ts
3
3
  /**
4
4
  * A single wait point instance with typed `.wait()` and `.resolve()` methods.
@@ -14,24 +14,79 @@ interface WaitPointInstance<Payload = undefined, Result = undefined> {
14
14
  resolve: (executionId: string, callback: (payload: [Payload] extends [undefined] ? undefined : Payload) => Result | Promise<Result>) => Promise<void>;
15
15
  }
16
16
  /**
17
- * The type produced by `define<Payload, Result>()` / `createWaitPoint<Payload, Result>(key)`.
18
- * Resolves to `WaitPointInstance<Payload, Result>` when both types are JsonValue-compatible,
17
+ * A wait point whose key carries `$params`, so the runtime key is built per call.
18
+ *
19
+ * `.with(params)` substitutes the params into the declared key and returns the
20
+ * same two-method surface as an unparameterized wait point.
21
+ */
22
+ interface ParameterizedWaitPointInstance<Params extends object, Payload = undefined, Result = undefined> {
23
+ /**
24
+ * Bind runtime values to the key's `$params`.
25
+ * @param params - One value per `$param` in the declared key
26
+ * @returns A wait point bound to the resulting key
27
+ * @throws If a param value is empty, contains characters outside `[a-z0-9-]`,
28
+ * starts or ends with `-`, or makes the resulting key exceed 63 characters
29
+ */
30
+ with(params: Params): WaitPointInstance<Payload, Result>;
31
+ }
32
+ type NonEmptyString = `${string & {}}${string}`;
33
+ type KeySegments<Key extends string> = Key extends `${infer Head}-${infer Tail}` ? Head | KeySegments<Tail> : Key;
34
+ type KeySegmentList<Key extends string> = Key extends `${infer Head}-${infer Tail}` ? [Head, ...KeySegmentList<Tail>] : [Key];
35
+ type ParamSegments<Key extends string> = Extract<KeySegments<Key>, `$${NonEmptyString}`>;
36
+ type ParamName<Segment extends string> = Segment extends `$${infer Name}` ? Name : never;
37
+ type KeyParams<Key extends string> = [ParamSegments<Key>] extends [never] ? undefined : Prettify<{ [Name in ParamName<ParamSegments<Key>>]: string; }>;
38
+ type HasLiteralSegment<Segments extends readonly string[]> = Segments extends readonly [infer Head extends string, ...infer Tail extends readonly string[]] ? Head extends `$${string}` ? HasLiteralSegment<Tail> : true : false;
39
+ type HasDuplicateParam<Segments extends readonly string[]> = Segments extends readonly [infer Head extends string, ...infer Tail extends readonly string[]] ? Head extends `$${string}` ? Head extends Tail[number] ? true : HasDuplicateParam<Tail> : HasDuplicateParam<Tail> : false;
40
+ /**
41
+ * Resolves to `Instance` when both `Payload` and `Result` are JsonValue-compatible,
19
42
  * or to a type-level error that surfaces at the call site.
20
43
  */
21
- type WaitPointDef<Payload, Result> = [null] extends [Payload] ? TypeLevelError<"Payload cannot be null at the top level"> : [undefined] extends [Result] ? TypeLevelError<"Result cannot be (or include) undefined (resolve callback must return a value)"> : [Payload] extends [undefined] ? [Result] extends [JsonCompatible<Result>] ? WaitPointInstance<Payload, Result> : TypeLevelError<"Result must be JsonValue-compatible (plain objects/arrays; no class instances or functions)"> : [undefined] extends [Payload] ? TypeLevelError<"Payload cannot include undefined at the top level"> : [Payload] extends [JsonCompatible<Payload>] ? [Result] extends [JsonCompatible<Result>] ? WaitPointInstance<Payload, Result> : TypeLevelError<"Result must be JsonValue-compatible (plain objects/arrays; no class instances or functions)"> : TypeLevelError<"Payload must be JsonValue-compatible (plain objects/arrays; no class instances or functions)">;
44
+ type ValidatedWaitPoint<Payload, Result, Instance> = [null] extends [Payload] ? TypeLevelError<"Payload cannot be null at the top level"> : [undefined] extends [Result] ? TypeLevelError<"Result cannot be (or include) undefined (resolve callback must return a value)"> : [Payload] extends [undefined] ? [Result] extends [JsonCompatible<Result>] ? Instance : TypeLevelError<"Result must be JsonValue-compatible (plain objects/arrays; no class instances or functions)"> : [undefined] extends [Payload] ? TypeLevelError<"Payload cannot include undefined at the top level"> : [Payload] extends [JsonCompatible<Payload>] ? [Result] extends [JsonCompatible<Result>] ? Instance : TypeLevelError<"Result must be JsonValue-compatible (plain objects/arrays; no class instances or functions)"> : TypeLevelError<"Payload must be JsonValue-compatible (plain objects/arrays; no class instances or functions)">;
45
+ /**
46
+ * The type produced by `define<Payload, Result>()` (the no-key form inside `createWaitPoints`).
47
+ */
48
+ type WaitPointDef<Payload, Result> = ValidatedWaitPoint<Payload, Result, WaitPointInstance<Payload, Result>>;
49
+ /**
50
+ * The type produced by `define(key)<Payload, Result>()`. Keys containing
51
+ * `$params` resolve to a {@link ParameterizedWaitPointInstance}; plain keys
52
+ * resolve to a {@link WaitPointInstance}, so the same call shape covers both.
53
+ */
54
+ type WaitPointKeyDef<Key extends string, Payload, Result> = string extends Key ? TypeLevelError<"Wait point key must be a string literal"> : HasDuplicateParam<KeySegmentList<Key>> extends true ? TypeLevelError<"Wait point key repeats a $param name"> : HasLiteralSegment<KeySegmentList<Key>> extends false ? TypeLevelError<"Wait point key needs at least one literal segment alongside its $params"> : [KeyParams<Key>] extends [undefined] ? ValidatedWaitPoint<Payload, Result, WaitPointInstance<Payload, Result>> : KeyParams<Key> extends (infer Params extends object) ? ValidatedWaitPoint<Payload, Result, ParameterizedWaitPointInstance<Params, Payload, Result>> : never;
55
+ /**
56
+ * The factory returned when a key is passed before the type arguments.
57
+ * Calling it yields the wait point the key describes.
58
+ */
59
+ type WaitPointFactory<Key extends string> = <Payload = undefined, Result = undefined>() => WaitPointKeyDef<Key, Payload, Result>;
22
60
  /**
23
61
  * The `define` function passed to the `createWaitPoints` builder callback.
24
- * Returns an actual WaitPointInstance (not a phantom marker) so that the
25
- * builder's return type can flow through as-is, preserving JSDoc comments
26
- * on each property for IDE autocompletion.
62
+ *
63
+ * Called with no arguments, the property name becomes the key. Called with a
64
+ * key, that key is used verbatim — and any `$params` in it become the argument
65
+ * of `.with()`. The key comes first so TypeScript can infer it as a literal;
66
+ * `Payload` / `Result` follow on the returned factory.
27
67
  *
28
68
  * JSON validation is encoded in the return type rather than in type-parameter
29
69
  * constraints, because tsgo rejects self-referential constraints like
30
70
  * `Payload extends JsonCompatible<Payload>` as circular.
31
71
  */
32
- type DefineFn = <Payload = undefined, Result = undefined>() => WaitPointDef<Payload, Result>;
72
+ type DefineFn = {
73
+ <Payload = undefined, Result = undefined>(): WaitPointDef<Payload, Result>;
74
+ /**
75
+ * Use a key of your own instead of the property name — the only way to give
76
+ * a key `$params`, since the key has to be read as a literal type and giving
77
+ * `Payload` / `Result` explicitly would stop that.
78
+ * @param key - The wait point key
79
+ * @returns A factory taking the type arguments
80
+ */
81
+ for<const Key extends string>(key: Key): WaitPointFactory<Key>;
82
+ };
33
83
  /**
34
- * Create a single typed wait point with an explicit key.
84
+ * Create a single typed wait point with a fixed key.
85
+ *
86
+ * The key must match `[a-z0-9-]` (3-63 characters, starting and ending with
87
+ * `[a-z0-9]`), which `deploy` reports on. For a key with `$params`, use
88
+ * {@link createWaitPoints}: binding params needs the key inferred as a literal
89
+ * type, which only its `define` offers.
35
90
  *
36
91
  * `Payload` and `Result` must be JsonValue-compatible.
37
92
  * Functions and objects with a `toJSON` method are rejected at the type level;
@@ -46,7 +101,9 @@ type DefineFn = <Payload = undefined, Result = undefined>() => WaitPointDef<Payl
46
101
  declare function createWaitPoint<Payload = undefined, Result = undefined>(key: string): WaitPointDef<Payload, Result>;
47
102
  /**
48
103
  * Create a group of typed wait points for human-in-the-loop workflows.
49
- * Property names become the wait point keys.
104
+ * Property names become the wait point keys, so they must match
105
+ * `[a-z0-9-]`, which `deploy` reports on — pass an explicit key to `define`
106
+ * when they do not.
50
107
  *
51
108
  * The return type is the same as the builder's return type, so JSDoc on each
52
109
  * property is preserved and visible in IDE autocompletion.
@@ -60,13 +117,15 @@ declare function createWaitPoint<Payload = undefined, Result = undefined>(key: s
60
117
  * export const waitPoints = createWaitPoints(define => ({
61
118
  * // Preceding JSDoc on this property is shown in IDE autocompletion
62
119
  * approval: define<{ message: string }, { approved: boolean }>(),
120
+ * // A key with $params is bound per call through `.with()`
121
+ * lineApproval: define.for("line-approval-$lineId")<{ message: string }, { approved: boolean }>(),
63
122
  * }));
64
123
  *
65
- * // IDE shows the JSDoc when typing `waitPoints.`
66
124
  * await waitPoints.approval.wait({ message: "Please approve" });
125
+ * await waitPoints.lineApproval.with({ lineId: line.id }).wait({ message: "Please approve" });
67
126
  *
68
127
  * // For 2-level access, use destructured export with JSDoc attached to the export itself.
69
128
  */
70
- declare function createWaitPoints<T extends Record<string, WaitPointInstance<any, any>>>(builder: (define: DefineFn) => T): T;
129
+ declare function createWaitPoints<T extends Record<string, WaitPointInstance<any, any> | ParameterizedWaitPointInstance<any, any, any>>>(builder: (define: DefineFn) => T): T;
71
130
  //#endregion
72
- export { WaitPointInstance, createWaitPoint, createWaitPoints };
131
+ export { ParameterizedWaitPointInstance, WaitPointInstance, createWaitPoint, createWaitPoints };
@@ -69,7 +69,21 @@ function createCLIError(options) {
69
69
  function isCLIError(error) {
70
70
  return error instanceof Error && error.name === "CLIError";
71
71
  }
72
+ const MISSING_NAMED_EXPORT_PATTERN = /does not provide an export named '(?!default')([^']+)'/;
73
+ /**
74
+ * Suggest `import type` when importing user code fails on a missing named
75
+ * export. The CLI strips types from each file in isolation, so a type-only
76
+ * export does not exist at runtime and a plain import of it fails to link.
77
+ * @param error - Error thrown while importing user modules
78
+ * @returns Suggestion text, or undefined when the error is not that failure
79
+ */
80
+ function typeOnlyImportHint(error) {
81
+ if (!(error instanceof SyntaxError)) return void 0;
82
+ const name = MISSING_NAMED_EXPORT_PATTERN.exec(error.message)?.[1];
83
+ if (!name) return void 0;
84
+ return `If '${name}' is a type, import it with \`import type\` (or the inline \`type\` modifier). The CLI runs TypeScript by stripping types from each file in isolation, so type-only exports do not exist at runtime. Set "verbatimModuleSyntax": true in tsconfig.json to catch this at typecheck.`;
85
+ }
72
86
 
73
87
  //#endregion
74
- export { isCLIError as i, formatCopyableCommand as n, formatNextAction as r, createCLIError as t };
75
- //# sourceMappingURL=errors-CWj21238.mjs.map
88
+ export { typeOnlyImportHint as a, isCLIError as i, formatCopyableCommand as n, formatNextAction as r, createCLIError as t };
89
+ //# sourceMappingURL=errors-BVb6vYGy.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"errors-CWj21238.mjs","names":[],"sources":["../src/cli/shared/errors.ts"],"sourcesContent":["import { styles } from \"./logger\";\n\n/**\n * Options for creating a CLI error\n */\nexport interface CLIErrorOptions {\n message: string;\n details?: string;\n suggestion?: string;\n command?: string;\n code?: string;\n next?: CLIErrorNextAction;\n context?: Readonly<Record<string, unknown>>;\n}\n\nexport interface CLIErrorNextAction {\n /** Executable name, such as `tailor`. */\n command: string;\n /** Arguments passed directly to the executable. */\n args: readonly string[];\n}\n\n/**\n * CLI error interface with formatted output\n */\nexport interface CLIError extends Error {\n readonly code?: string;\n readonly details?: string;\n readonly suggestion?: string;\n readonly command?: string;\n readonly next?: CLIErrorNextAction;\n readonly context?: Readonly<Record<string, unknown>>;\n format(): string;\n}\n\ntype CLIErrorInternal = Error & {\n code?: string;\n details?: string;\n suggestion?: string;\n command?: string;\n next?: CLIErrorNextAction;\n context?: Readonly<Record<string, unknown>>;\n format(): string;\n};\n\nfunction shellQuote(value: string): string {\n if (process.platform === \"win32\") {\n if (/^[A-Za-z0-9_./:=@+\\\\-]+$/.test(value)) return value;\n return `\"${value.replaceAll('\"', '\\\\\"')}\"`;\n }\n if (/^[A-Za-z0-9_./:=@+-]+$/.test(value)) return value;\n return `'${value.replaceAll(\"'\", `'\"'\"'`)}'`;\n}\n\nfunction needsArgvRendering(argv: readonly string[]): boolean {\n // cmd.exe/PowerShell expand %, $, and ! even inside double quotes, so no\n // quoting can keep such values literal on Windows.\n return process.platform === \"win32\" && argv.some((value) => /[%$!]/.test(value));\n}\n\n/**\n * Render an argv array as a copyable command line for the current platform's shell\n * @param {readonly string[]} argv - Executable name followed by its arguments\n * @returns {string} A shell-quoted command line, or an `argv [...]` JSON rendering when the platform shell cannot keep a value literal\n */\nexport function formatCopyableCommand(argv: readonly string[]): string {\n if (needsArgvRendering(argv)) {\n return `argv ${JSON.stringify(argv)}`;\n }\n return argv.map(shellQuote).join(\" \");\n}\n\n/**\n * Format an executable and argv as a shell-safe user-facing command.\n * @param next - Executable and arguments to format\n * @returns Shell command, or an argv representation when shell quoting is unsafe\n */\nexport function formatNextAction(next: CLIErrorNextAction): string {\n const argv = [next.command, ...next.args];\n const rendered = formatCopyableCommand(argv);\n return needsArgvRendering(argv) ? `with ${rendered}` : `\\`${rendered}\\``;\n}\n\n/**\n * Format CLI error for output\n * @param error - CLIError instance to format\n * @returns Formatted error message\n */\nfunction formatError(error: CLIError): string {\n const parts: string[] = [\n styles.error(`Error${error.code ? ` [${error.code}]` : \"\"}: ${error.message}`),\n ];\n\n if (error.details) {\n parts.push(`\\n ${styles.dim(\"Details:\")} ${error.details}`);\n }\n\n if (error.suggestion) {\n parts.push(`\\n ${styles.info(\"Suggestion:\")} ${error.suggestion}`);\n }\n\n if (error.command) {\n parts.push(\n `\\n ${styles.dim(\"Help:\")} Run \\`tailor ${error.command} --help\\` for usage information.`,\n );\n }\n\n if (error.next) {\n parts.push(`\\n ${styles.info(\"Next:\")} Run ${formatNextAction(error.next)}.`);\n }\n\n return parts.join(\"\");\n}\n\n/**\n * Create a CLI error with formatted output\n * @param options - Options to construct a CLIError\n * @returns Constructed CLIError instance\n */\nfunction createCLIError(options: CLIErrorOptions): CLIError {\n const error = new Error(options.message) as CLIErrorInternal;\n error.name = \"CLIError\";\n error.code = options.code;\n error.details = options.details;\n error.suggestion = options.suggestion;\n error.command = options.command;\n error.next = options.next;\n error.context = options.context;\n error.format = () => formatError(error);\n return error;\n}\n\n/**\n * Type guard to check if an error is a CLIError\n * @param error - Error to check\n * @returns True if the error is a CLIError\n */\nexport function isCLIError(error: unknown): error is CLIError {\n return error instanceof Error && error.name === \"CLIError\";\n}\n\n// Re-export createCLIError as CLIError for backward compatibility\nexport { createCLIError as CLIError };\n"],"mappings":";;;AA6CA,SAAS,WAAW,OAAuB;CACzC,IAAI,QAAQ,aAAa,SAAS;EAChC,IAAI,2BAA2B,KAAK,KAAK,GAAG,OAAO;EACnD,OAAO,IAAI,MAAM,WAAW,MAAK,MAAK,EAAE;CAC1C;CACA,IAAI,yBAAyB,KAAK,KAAK,GAAG,OAAO;CACjD,OAAO,IAAI,MAAM,WAAW,KAAK,OAAO,EAAE;AAC5C;AAEA,SAAS,mBAAmB,MAAkC;CAG5D,OAAO,QAAQ,aAAa,WAAW,KAAK,MAAM,UAAU,QAAQ,KAAK,KAAK,CAAC;AACjF;;;;;;AAOA,SAAgB,sBAAsB,MAAiC;CACrE,IAAI,mBAAmB,IAAI,GACzB,OAAO,QAAQ,KAAK,UAAU,IAAI;CAEpC,OAAO,KAAK,IAAI,UAAU,CAAC,CAAC,KAAK,GAAG;AACtC;;;;;;AAOA,SAAgB,iBAAiB,MAAkC;CACjE,MAAM,OAAO,CAAC,KAAK,SAAS,GAAG,KAAK,IAAI;CACxC,MAAM,WAAW,sBAAsB,IAAI;CAC3C,OAAO,mBAAmB,IAAI,IAAI,QAAQ,aAAa,KAAK,SAAS;AACvE;;;;;;AAOA,SAAS,YAAY,OAAyB;CAC5C,MAAM,QAAkB,CACtB,OAAO,MAAM,QAAQ,MAAM,OAAO,KAAK,MAAM,KAAK,KAAK,GAAG,IAAI,MAAM,SAAS,CAC/E;CAEA,IAAI,MAAM,SACR,MAAM,KAAK,OAAO,OAAO,IAAI,UAAU,EAAE,GAAG,MAAM,SAAS;CAG7D,IAAI,MAAM,YACR,MAAM,KAAK,OAAO,OAAO,KAAK,aAAa,EAAE,GAAG,MAAM,YAAY;CAGpE,IAAI,MAAM,SACR,MAAM,KACJ,OAAO,OAAO,IAAI,OAAO,EAAE,gBAAgB,MAAM,QAAQ,iCAC3D;CAGF,IAAI,MAAM,MACR,MAAM,KAAK,OAAO,OAAO,KAAK,OAAO,EAAE,OAAO,iBAAiB,MAAM,IAAI,EAAE,EAAE;CAG/E,OAAO,MAAM,KAAK,EAAE;AACtB;;;;;;AAOA,SAAS,eAAe,SAAoC;CAC1D,MAAM,QAAQ,IAAI,MAAM,QAAQ,OAAO;CACvC,MAAM,OAAO;CACb,MAAM,OAAO,QAAQ;CACrB,MAAM,UAAU,QAAQ;CACxB,MAAM,aAAa,QAAQ;CAC3B,MAAM,UAAU,QAAQ;CACxB,MAAM,OAAO,QAAQ;CACrB,MAAM,UAAU,QAAQ;CACxB,MAAM,eAAe,YAAY,KAAK;CACtC,OAAO;AACT;;;;;;AAOA,SAAgB,WAAW,OAAmC;CAC5D,OAAO,iBAAiB,SAAS,MAAM,SAAS;AAClD"}
1
+ {"version":3,"file":"errors-BVb6vYGy.mjs","names":[],"sources":["../src/cli/shared/errors.ts"],"sourcesContent":["import { styles } from \"./logger\";\n\n/**\n * Options for creating a CLI error\n */\nexport interface CLIErrorOptions {\n message: string;\n details?: string;\n suggestion?: string;\n command?: string;\n code?: string;\n next?: CLIErrorNextAction;\n context?: Readonly<Record<string, unknown>>;\n}\n\nexport interface CLIErrorNextAction {\n /** Executable name, such as `tailor`. */\n command: string;\n /** Arguments passed directly to the executable. */\n args: readonly string[];\n}\n\n/**\n * CLI error interface with formatted output\n */\nexport interface CLIError extends Error {\n readonly code?: string;\n readonly details?: string;\n readonly suggestion?: string;\n readonly command?: string;\n readonly next?: CLIErrorNextAction;\n readonly context?: Readonly<Record<string, unknown>>;\n format(): string;\n}\n\ntype CLIErrorInternal = Error & {\n code?: string;\n details?: string;\n suggestion?: string;\n command?: string;\n next?: CLIErrorNextAction;\n context?: Readonly<Record<string, unknown>>;\n format(): string;\n};\n\nfunction shellQuote(value: string): string {\n if (process.platform === \"win32\") {\n if (/^[A-Za-z0-9_./:=@+\\\\-]+$/.test(value)) return value;\n return `\"${value.replaceAll('\"', '\\\\\"')}\"`;\n }\n if (/^[A-Za-z0-9_./:=@+-]+$/.test(value)) return value;\n return `'${value.replaceAll(\"'\", `'\"'\"'`)}'`;\n}\n\nfunction needsArgvRendering(argv: readonly string[]): boolean {\n // cmd.exe/PowerShell expand %, $, and ! even inside double quotes, so no\n // quoting can keep such values literal on Windows.\n return process.platform === \"win32\" && argv.some((value) => /[%$!]/.test(value));\n}\n\n/**\n * Render an argv array as a copyable command line for the current platform's shell\n * @param {readonly string[]} argv - Executable name followed by its arguments\n * @returns {string} A shell-quoted command line, or an `argv [...]` JSON rendering when the platform shell cannot keep a value literal\n */\nexport function formatCopyableCommand(argv: readonly string[]): string {\n if (needsArgvRendering(argv)) {\n return `argv ${JSON.stringify(argv)}`;\n }\n return argv.map(shellQuote).join(\" \");\n}\n\n/**\n * Format an executable and argv as a shell-safe user-facing command.\n * @param next - Executable and arguments to format\n * @returns Shell command, or an argv representation when shell quoting is unsafe\n */\nexport function formatNextAction(next: CLIErrorNextAction): string {\n const argv = [next.command, ...next.args];\n const rendered = formatCopyableCommand(argv);\n return needsArgvRendering(argv) ? `with ${rendered}` : `\\`${rendered}\\``;\n}\n\n/**\n * Format CLI error for output\n * @param error - CLIError instance to format\n * @returns Formatted error message\n */\nfunction formatError(error: CLIError): string {\n const parts: string[] = [\n styles.error(`Error${error.code ? ` [${error.code}]` : \"\"}: ${error.message}`),\n ];\n\n if (error.details) {\n parts.push(`\\n ${styles.dim(\"Details:\")} ${error.details}`);\n }\n\n if (error.suggestion) {\n parts.push(`\\n ${styles.info(\"Suggestion:\")} ${error.suggestion}`);\n }\n\n if (error.command) {\n parts.push(\n `\\n ${styles.dim(\"Help:\")} Run \\`tailor ${error.command} --help\\` for usage information.`,\n );\n }\n\n if (error.next) {\n parts.push(`\\n ${styles.info(\"Next:\")} Run ${formatNextAction(error.next)}.`);\n }\n\n return parts.join(\"\");\n}\n\n/**\n * Create a CLI error with formatted output\n * @param options - Options to construct a CLIError\n * @returns Constructed CLIError instance\n */\nfunction createCLIError(options: CLIErrorOptions): CLIError {\n const error = new Error(options.message) as CLIErrorInternal;\n error.name = \"CLIError\";\n error.code = options.code;\n error.details = options.details;\n error.suggestion = options.suggestion;\n error.command = options.command;\n error.next = options.next;\n error.context = options.context;\n error.format = () => formatError(error);\n return error;\n}\n\n/**\n * Type guard to check if an error is a CLIError\n * @param error - Error to check\n * @returns True if the error is a CLIError\n */\nexport function isCLIError(error: unknown): error is CLIError {\n return error instanceof Error && error.name === \"CLIError\";\n}\n\nconst MISSING_NAMED_EXPORT_PATTERN = /does not provide an export named '(?!default')([^']+)'/;\n\n/**\n * Suggest `import type` when importing user code fails on a missing named\n * export. The CLI strips types from each file in isolation, so a type-only\n * export does not exist at runtime and a plain import of it fails to link.\n * @param error - Error thrown while importing user modules\n * @returns Suggestion text, or undefined when the error is not that failure\n */\nexport function typeOnlyImportHint(error: unknown): string | undefined {\n if (!(error instanceof SyntaxError)) return undefined;\n const name = MISSING_NAMED_EXPORT_PATTERN.exec(error.message)?.[1];\n if (!name) return undefined;\n return (\n `If '${name}' is a type, import it with \\`import type\\` (or the inline \\`type\\` modifier). ` +\n \"The CLI runs TypeScript by stripping types from each file in isolation, so type-only exports do not exist at runtime. \" +\n 'Set \"verbatimModuleSyntax\": true in tsconfig.json to catch this at typecheck.'\n );\n}\n\n// Re-export createCLIError as CLIError for backward compatibility\nexport { createCLIError as CLIError };\n"],"mappings":";;;AA6CA,SAAS,WAAW,OAAuB;CACzC,IAAI,QAAQ,aAAa,SAAS;EAChC,IAAI,2BAA2B,KAAK,KAAK,GAAG,OAAO;EACnD,OAAO,IAAI,MAAM,WAAW,MAAK,MAAK,EAAE;CAC1C;CACA,IAAI,yBAAyB,KAAK,KAAK,GAAG,OAAO;CACjD,OAAO,IAAI,MAAM,WAAW,KAAK,OAAO,EAAE;AAC5C;AAEA,SAAS,mBAAmB,MAAkC;CAG5D,OAAO,QAAQ,aAAa,WAAW,KAAK,MAAM,UAAU,QAAQ,KAAK,KAAK,CAAC;AACjF;;;;;;AAOA,SAAgB,sBAAsB,MAAiC;CACrE,IAAI,mBAAmB,IAAI,GACzB,OAAO,QAAQ,KAAK,UAAU,IAAI;CAEpC,OAAO,KAAK,IAAI,UAAU,CAAC,CAAC,KAAK,GAAG;AACtC;;;;;;AAOA,SAAgB,iBAAiB,MAAkC;CACjE,MAAM,OAAO,CAAC,KAAK,SAAS,GAAG,KAAK,IAAI;CACxC,MAAM,WAAW,sBAAsB,IAAI;CAC3C,OAAO,mBAAmB,IAAI,IAAI,QAAQ,aAAa,KAAK,SAAS;AACvE;;;;;;AAOA,SAAS,YAAY,OAAyB;CAC5C,MAAM,QAAkB,CACtB,OAAO,MAAM,QAAQ,MAAM,OAAO,KAAK,MAAM,KAAK,KAAK,GAAG,IAAI,MAAM,SAAS,CAC/E;CAEA,IAAI,MAAM,SACR,MAAM,KAAK,OAAO,OAAO,IAAI,UAAU,EAAE,GAAG,MAAM,SAAS;CAG7D,IAAI,MAAM,YACR,MAAM,KAAK,OAAO,OAAO,KAAK,aAAa,EAAE,GAAG,MAAM,YAAY;CAGpE,IAAI,MAAM,SACR,MAAM,KACJ,OAAO,OAAO,IAAI,OAAO,EAAE,gBAAgB,MAAM,QAAQ,iCAC3D;CAGF,IAAI,MAAM,MACR,MAAM,KAAK,OAAO,OAAO,KAAK,OAAO,EAAE,OAAO,iBAAiB,MAAM,IAAI,EAAE,EAAE;CAG/E,OAAO,MAAM,KAAK,EAAE;AACtB;;;;;;AAOA,SAAS,eAAe,SAAoC;CAC1D,MAAM,QAAQ,IAAI,MAAM,QAAQ,OAAO;CACvC,MAAM,OAAO;CACb,MAAM,OAAO,QAAQ;CACrB,MAAM,UAAU,QAAQ;CACxB,MAAM,aAAa,QAAQ;CAC3B,MAAM,UAAU,QAAQ;CACxB,MAAM,OAAO,QAAQ;CACrB,MAAM,UAAU,QAAQ;CACxB,MAAM,eAAe,YAAY,KAAK;CACtC,OAAO;AACT;;;;;;AAOA,SAAgB,WAAW,OAAmC;CAC5D,OAAO,iBAAiB,SAAS,MAAM,SAAS;AAClD;AAEA,MAAM,+BAA+B;;;;;;;;AASrC,SAAgB,mBAAmB,OAAoC;CACrE,IAAI,EAAE,iBAAiB,cAAc,OAAO;CAC5C,MAAM,OAAO,6BAA6B,KAAK,MAAM,OAAO,CAAC,GAAG;CAChE,IAAI,CAAC,MAAM,OAAO;CAClB,OACE,OAAO,KAAK;AAIhB"}
@@ -10,7 +10,8 @@ type ResolveUpdate<T> = T extends ColumnType$1<unknown, unknown, infer U> ? U :
10
10
  type ObjectColumnType<T> = ColumnType$1<{ [K in keyof T]-?: Exclude<ResolveSelect<T[K]>, undefined>; }, { [K in keyof T]: ResolveInsert<T[K]>; }, { [K in keyof T]: ResolveUpdate<T[K]>; }>;
11
11
  type ArrayColumnType<T> = ColumnType$1<ResolveSelect<T>[], ResolveInsert<T>[], ResolveUpdate<T>[]>;
12
12
  type Generated<T> = T extends ColumnType$1<infer S, infer I, infer U> ? ColumnType$1<S, I | undefined, U> : ColumnType$1<T, T | undefined, T>;
13
- type Serial<T = string | number> = ColumnType$1<T, TypeLevelError<"assigned by .serial(); remove it from the input"> | undefined, TypeLevelError<"assigned by .serial(); remove it from the input"> | undefined>;
13
+ type SerialColumnMustBeOmitted = TypeLevelError<"assigned by .serial(); remove it from the input">;
14
+ type Serial<T = string | number> = ColumnType$1<T, SerialColumnMustBeOmitted | undefined, SerialColumnMustBeOmitted | undefined>;
14
15
  type FlattenColumns<T> = { [K in keyof T]: T[K]; } & {};
15
16
  type TailordbKysely<DB> = Kysely$1<DB>;
16
17
  type NamespaceDB<NS, N extends keyof NS = keyof NS> = TailordbKysely<NS[N]>;
@@ -1 +1 @@
1
- {"version":3,"file":"index.mjs","names":["Kysely","TailordbDialect"],"sources":["../../src/kysely/index.ts"],"sourcesContent":["/**\n * Kysely integration module for generated TailorDB code.\n *\n * Re-exports kysely and function-kysely-tailordb types through a single import path\n * to avoid phantom dependency issues with pnpm, and provides the namespace-aware\n * utility types and factory functions the code generator emits against.\n *\n * It also holds the `TailorDB*` input types, which hand-written code uses to derive\n * create/read/update shapes straight from a table or field collection. They live here\n * rather than in the main entry point because they are built out of kysely's column\n * types, which the main entry point does not otherwise depend on.\n */\n\nimport { TailordbDialect } from \"@tailor-platform/function-kysely-tailordb\";\nimport {\n type ColumnType,\n Kysely,\n type Insertable,\n type KyselyConfig,\n type Selectable,\n type Transaction as KyselyTransaction,\n type Updateable,\n} from \"kysely\";\nimport type {\n IsAutoFilledDBField,\n IsReadOnlyDBField,\n TailorAnyDBField,\n TailorAnyDBType,\n} from \"#/configure/services/tailordb/types\";\nimport type { output, TypeLevelError } from \"#/types/helpers\";\n\nexport {\n type ColumnType,\n Kysely,\n type KyselyConfig,\n type Transaction,\n type Insertable,\n type Selectable,\n sql,\n type Updateable,\n} from \"kysely\";\n\nexport { TailordbDialect } from \"@tailor-platform/function-kysely-tailordb\";\n\nexport type Timestamp = ColumnType<Date, Date | string, Date | string>;\ntype ResolveSelect<T> = T extends ColumnType<infer S, unknown, unknown> ? S : T;\ntype ResolveInsert<T> = T extends ColumnType<unknown, infer I, unknown> ? I : T;\ntype ResolveUpdate<T> = T extends ColumnType<unknown, unknown, infer U> ? U : T;\nexport type ObjectColumnType<T> = ColumnType<\n { [K in keyof T]-?: Exclude<ResolveSelect<T[K]>, undefined> },\n { [K in keyof T]: ResolveInsert<T[K]> },\n { [K in keyof T]: ResolveUpdate<T[K]> }\n>;\nexport type ArrayColumnType<T> = ColumnType<\n ResolveSelect<T>[],\n ResolveInsert<T>[],\n ResolveUpdate<T>[]\n>;\nexport type Generated<T> =\n T extends ColumnType<infer S, infer I, infer U>\n ? ColumnType<S, I | undefined, U>\n : ColumnType<T, T | undefined, T>;\n// The insert/update types carry the reason as a string literal so that supplying a\n// value fails with it, instead of the bare \"does not exist\" an absent key produces.\n// `| undefined` is what makes the column omittable; Kysely drops undefined columns\n// from the statement, so passing it explicitly is the same as leaving it out.\nexport type Serial<T = string | number> = ColumnType<\n T,\n TypeLevelError<\"assigned by .serial(); remove it from the input\"> | undefined,\n TypeLevelError<\"assigned by .serial(); remove it from the input\"> | undefined\n>;\n\n// Kysely composes its input types out of intersections. Flattening them keeps the\n// shape readable in assignability errors and editor tooltips.\ntype FlattenColumns<T> = { [K in keyof T]: T[K] } & {};\n\nexport type TailordbKysely<DB> = Kysely<DB>;\nexport type NamespaceDB<NS, N extends keyof NS = keyof NS> = TailordbKysely<NS[N]>;\n\n/**\n * Create a namespace-aware getDB function for generated code.\n * @returns A getDB function that creates Kysely instances for specific namespaces\n */\nexport function createGetDB<NS>() {\n return function getDB<const N extends keyof NS & string>(\n namespace: N,\n config?: Omit<KyselyConfig, \"dialect\">,\n ): TailordbKysely<NS[N]> {\n const client = new tailordb.Client({ namespace });\n return new Kysely<NS[N]>({\n dialect: new TailordbDialect(client),\n ...config,\n });\n };\n}\n\nexport type NamespaceTransaction<NS, K extends keyof NS | TailordbKysely<NS[keyof NS]> = keyof NS> =\n K extends TailordbKysely<infer DB>\n ? KyselyTransaction<DB>\n : K extends keyof NS\n ? KyselyTransaction<NS[K]>\n : never;\n\nexport type NamespaceTableName<NS> = {\n [N in keyof NS]: keyof NS[N];\n}[keyof NS];\n\nexport type NamespaceTable<NS, T extends NamespaceTableName<NS>> = {\n [N in keyof NS]: T extends keyof NS[N] ? NS[N][T] : never;\n}[keyof NS];\n\nexport type NamespaceInsertable<NS, T extends NamespaceTableName<NS>> = FlattenColumns<\n Insertable<NamespaceTable<NS, T>>\n>;\nexport type NamespaceSelectable<NS, T extends NamespaceTableName<NS>> = FlattenColumns<\n Selectable<NamespaceTable<NS, T>>\n>;\nexport type NamespaceUpdateable<NS, T extends NamespaceTableName<NS>> = FlattenColumns<\n Updateable<NamespaceTable<NS, T>>\n>;\n\n/** What the derived input types accept: a table (`typeof myTable`) or a field collection. */\ntype TailorDBColumnsSource = TailorAnyDBType | Record<string, TailorAnyDBField>;\n\ntype DBFieldsOf<T> = T extends TailorAnyDBType ? T[\"fields\"] : T;\n\n// The column mapping below mirrors the one `kyselyTypePlugin` applies when it writes a\n// table interface (`plugin/builtin/kysely-type/type-processor.ts`), so both surfaces\n// resolve a field to the same column type — including inside nested objects, where the\n// function runtime also hands back a Date for a date/datetime.\n// `example/tests/kysely-parity.ts` pins the two against each other on real generator output.\ntype DBFieldType<F> = F extends TailorAnyDBField ? F[\"_defined\"][\"type\"] : never;\ntype IsArrayDBField<F> = F extends TailorAnyDBField\n ? F[\"_defined\"][\"array\"] extends true\n ? true\n : false\n : false;\n\ntype Unwrapped<F> = Exclude<output<F>, null>;\ntype ElementOutput<F> =\n IsArrayDBField<F> extends true\n ? Unwrapped<F> extends readonly (infer E)[]\n ? E\n : Unwrapped<F>\n : Unwrapped<F>;\n\ntype NestedFieldsOf<F> = F extends TailorAnyDBField ? F[\"fields\"] : never;\n\n// Nested props carry the same column mapping as top-level ones, so a datetime inside an\n// object also resolves to Timestamp. The optional marker matches what the output type\n// gives them, which is what the generator emits too.\n// `-readonly` because a field collection is inferred with `const`, and the generated\n// table interfaces declare their nested props mutable.\ntype NestedProps<Fields> = {\n -readonly [K in keyof Fields as null extends output<Fields[K]> ? never : K]: DBColumn<Fields[K]>;\n} & {\n -readonly [K in keyof Fields as null extends output<Fields[K]> ? K : never]?: DBColumn<Fields[K]>;\n};\n\n// The generator reaches for ObjectColumnType only when the object holds something whose\n// select and insert types differ: a timestamp, an optional prop, or a filled-in one.\ntype NestedNeedsColumnType<Fields> = true extends {\n [K in keyof Fields]: DBFieldType<Fields[K]> extends \"date\" | \"datetime\"\n ? true\n : null extends output<Fields[K]>\n ? true\n : DBFieldType<Fields[K]> extends \"nested\"\n ? NestedNeedsColumnType<NestedFieldsOf<Fields[K]>>\n : Fields[K] extends TailorAnyDBField\n ? IsAutoFilledDBField<Fields[K]>\n : false;\n}[keyof Fields]\n ? true\n : false;\n\ntype NestedColumn<F> =\n NestedNeedsColumnType<NestedFieldsOf<F>> extends true\n ? ObjectColumnType<FlattenColumns<NestedProps<NestedFieldsOf<F>>>>\n : FlattenColumns<NestedProps<NestedFieldsOf<F>>>;\n\ntype ElementColumn<F> =\n DBFieldType<F> extends \"date\" | \"datetime\"\n ? Timestamp\n : DBFieldType<F> extends \"nested\"\n ? NestedColumn<F>\n : ElementOutput<F>;\n\n// A ColumnType cannot sit inside an array — Kysely only unwraps it at the top level of a\n// table property — so an array of them keeps the ColumnType outermost.\ntype ArrayedColumn<F> =\n IsArrayDBField<F> extends true\n ? ElementColumn<F> extends ColumnType<unknown, unknown, unknown>\n ? ArrayColumnType<ElementColumn<F>>\n : ElementColumn<F>[]\n : ElementColumn<F>;\n\ntype NullableColumn<F> = null extends output<F> ? ArrayedColumn<F> | null : ArrayedColumn<F>;\n\ntype DBColumn<F> = F extends TailorAnyDBField\n ? IsReadOnlyDBField<F> extends true\n ? Serial<NullableColumn<F>>\n : IsAutoFilledDBField<F> extends true\n ? Generated<NullableColumn<F>>\n : NullableColumn<F>\n : never;\n\n// The column map the three derived types are built from. Not exported: it is how the\n// mapping is expressed, not something callers need to name.\ntype TailorDBColumns<T extends TailorDBColumnsSource> = {\n [K in keyof DBFieldsOf<T>]: K extends \"id\"\n ? Generated<output<DBFieldsOf<T>[K]>>\n : DBColumn<DBFieldsOf<T>[K]>;\n};\n\n/**\n * Create input derived from a TailorDB table (`typeof myTable`) or a field collection.\n *\n * Each field resolves to the column type `kyselyTypePlugin` writes for it, so this and\n * the generated table types agree: `.serial()` fields are never caller-supplied,\n * `.default()` / `.hooks({ create })` fields may be omitted, optional fields stay\n * optional, `id` is platform-generated, and a date or datetime reads back as `Date`.\n *\n * Pass a field collection when the fields are a type parameter — a shared module that\n * lets each project extend a table with its own fields cannot name a generated table\n * type. Declare it as `<const F extends Record<string, TailorAnyDBField>>` so the field\n * types are inferred; a bare `Record<string, TailorAnyDBField>` erases them and nothing\n * is checked.\n *\n * Hand the result to callers rather than consuming it inside the generic that declares\n * it: while `F` is still an unresolved type parameter the mapping stays deferred, so\n * assigning to it inside the function body reports the unevaluated conditional rather\n * than a readable shape.\n * @example\n * function createInput<const F extends Record<string, TailorAnyDBField>>(fields: F) {\n * return (input: TailorDBInsertable<F>) => { ... };\n * }\n */\nexport type TailorDBInsertable<T extends TailorDBColumnsSource> = FlattenColumns<\n Insertable<TailorDBColumns<T>>\n>;\n\n/** Read shape of a TailorDB table or field collection. See {@link TailorDBInsertable}. */\nexport type TailorDBSelectable<T extends TailorDBColumnsSource> = FlattenColumns<\n Selectable<TailorDBColumns<T>>\n>;\n\n/** Update input for a TailorDB table or field collection. See {@link TailorDBInsertable}. */\nexport type TailorDBUpdateable<T extends TailorDBColumnsSource> = FlattenColumns<\n Updateable<TailorDBColumns<T>>\n>;\n"],"mappings":";;;;;;;;;;;;;;;;;;;;AAmFA,SAAgB,cAAkB;CAChC,OAAO,SAAS,MACd,WACA,QACuB;EAEvB,OAAO,IAAIA,SAAc;GACvB,SAAS,IAAIC,kBAAgB,IAFZ,SAAS,OAAO,EAAE,UAAU,CAEX,CAAC;GACnC,GAAG;EACL,CAAC;CACH;AACF"}
1
+ {"version":3,"file":"index.mjs","names":["Kysely","TailordbDialect"],"sources":["../../src/kysely/index.ts"],"sourcesContent":["/**\n * Kysely integration module for generated TailorDB code.\n *\n * Re-exports kysely and function-kysely-tailordb types through a single import path\n * to avoid phantom dependency issues with pnpm, and provides the namespace-aware\n * utility types and factory functions the code generator emits against.\n *\n * It also holds the `TailorDB*` input types, which hand-written code uses to derive\n * create/read/update shapes straight from a table or field collection. They live here\n * rather than in the main entry point because they are built out of kysely's column\n * types, which the main entry point does not otherwise depend on.\n */\n\nimport { TailordbDialect } from \"@tailor-platform/function-kysely-tailordb\";\nimport {\n type ColumnType,\n Kysely,\n type Insertable,\n type KyselyConfig,\n type Selectable,\n type Transaction as KyselyTransaction,\n type Updateable,\n} from \"kysely\";\nimport type {\n IsAutoFilledDBField,\n IsReadOnlyDBField,\n TailorAnyDBField,\n TailorAnyDBType,\n} from \"#/configure/services/tailordb/types\";\nimport type { output, TypeLevelError } from \"#/types/helpers\";\n\nexport {\n type ColumnType,\n Kysely,\n type KyselyConfig,\n type Transaction,\n type Insertable,\n type Selectable,\n sql,\n type Updateable,\n} from \"kysely\";\n\nexport { TailordbDialect } from \"@tailor-platform/function-kysely-tailordb\";\n\nexport type Timestamp = ColumnType<Date, Date | string, Date | string>;\ntype ResolveSelect<T> = T extends ColumnType<infer S, unknown, unknown> ? S : T;\ntype ResolveInsert<T> = T extends ColumnType<unknown, infer I, unknown> ? I : T;\ntype ResolveUpdate<T> = T extends ColumnType<unknown, unknown, infer U> ? U : T;\nexport type ObjectColumnType<T> = ColumnType<\n { [K in keyof T]-?: Exclude<ResolveSelect<T[K]>, undefined> },\n { [K in keyof T]: ResolveInsert<T[K]> },\n { [K in keyof T]: ResolveUpdate<T[K]> }\n>;\nexport type ArrayColumnType<T> = ColumnType<\n ResolveSelect<T>[],\n ResolveInsert<T>[],\n ResolveUpdate<T>[]\n>;\nexport type Generated<T> =\n T extends ColumnType<infer S, infer I, infer U>\n ? ColumnType<S, I | undefined, U>\n : ColumnType<T, T | undefined, T>;\n// The insert/update types carry the reason so that supplying a value fails with it,\n// instead of the bare \"does not exist\" an absent key produces. The named alias is\n// what survives in nested positions (values()/set()), where tsc elides the marker's\n// type argument and only the name reaches the user.\n// `| undefined` is what makes the column omittable; Kysely drops undefined columns\n// from the statement, so passing it explicitly is the same as leaving it out.\ntype SerialColumnMustBeOmitted = TypeLevelError<\"assigned by .serial(); remove it from the input\">;\nexport type Serial<T = string | number> = ColumnType<\n T,\n SerialColumnMustBeOmitted | undefined,\n SerialColumnMustBeOmitted | undefined\n>;\n\n// Kysely composes its input types out of intersections. Flattening them keeps the\n// shape readable in assignability errors and editor tooltips.\ntype FlattenColumns<T> = { [K in keyof T]: T[K] } & {};\n\nexport type TailordbKysely<DB> = Kysely<DB>;\nexport type NamespaceDB<NS, N extends keyof NS = keyof NS> = TailordbKysely<NS[N]>;\n\n/**\n * Create a namespace-aware getDB function for generated code.\n * @returns A getDB function that creates Kysely instances for specific namespaces\n */\nexport function createGetDB<NS>() {\n return function getDB<const N extends keyof NS & string>(\n namespace: N,\n config?: Omit<KyselyConfig, \"dialect\">,\n ): TailordbKysely<NS[N]> {\n const client = new tailordb.Client({ namespace });\n return new Kysely<NS[N]>({\n dialect: new TailordbDialect(client),\n ...config,\n });\n };\n}\n\nexport type NamespaceTransaction<NS, K extends keyof NS | TailordbKysely<NS[keyof NS]> = keyof NS> =\n K extends TailordbKysely<infer DB>\n ? KyselyTransaction<DB>\n : K extends keyof NS\n ? KyselyTransaction<NS[K]>\n : never;\n\nexport type NamespaceTableName<NS> = {\n [N in keyof NS]: keyof NS[N];\n}[keyof NS];\n\nexport type NamespaceTable<NS, T extends NamespaceTableName<NS>> = {\n [N in keyof NS]: T extends keyof NS[N] ? NS[N][T] : never;\n}[keyof NS];\n\nexport type NamespaceInsertable<NS, T extends NamespaceTableName<NS>> = FlattenColumns<\n Insertable<NamespaceTable<NS, T>>\n>;\nexport type NamespaceSelectable<NS, T extends NamespaceTableName<NS>> = FlattenColumns<\n Selectable<NamespaceTable<NS, T>>\n>;\nexport type NamespaceUpdateable<NS, T extends NamespaceTableName<NS>> = FlattenColumns<\n Updateable<NamespaceTable<NS, T>>\n>;\n\n/** What the derived input types accept: a table (`typeof myTable`) or a field collection. */\ntype TailorDBColumnsSource = TailorAnyDBType | Record<string, TailorAnyDBField>;\n\ntype DBFieldsOf<T> = T extends TailorAnyDBType ? T[\"fields\"] : T;\n\n// The column mapping below mirrors the one `kyselyTypePlugin` applies when it writes a\n// table interface (`plugin/builtin/kysely-type/type-processor.ts`), so both surfaces\n// resolve a field to the same column type — including inside nested objects, where the\n// function runtime also hands back a Date for a date/datetime.\n// `example/tests/kysely-parity.ts` pins the two against each other on real generator output.\ntype DBFieldType<F> = F extends TailorAnyDBField ? F[\"_defined\"][\"type\"] : never;\ntype IsArrayDBField<F> = F extends TailorAnyDBField\n ? F[\"_defined\"][\"array\"] extends true\n ? true\n : false\n : false;\n\ntype Unwrapped<F> = Exclude<output<F>, null>;\ntype ElementOutput<F> =\n IsArrayDBField<F> extends true\n ? Unwrapped<F> extends readonly (infer E)[]\n ? E\n : Unwrapped<F>\n : Unwrapped<F>;\n\ntype NestedFieldsOf<F> = F extends TailorAnyDBField ? F[\"fields\"] : never;\n\n// Nested props carry the same column mapping as top-level ones, so a datetime inside an\n// object also resolves to Timestamp. The optional marker matches what the output type\n// gives them, which is what the generator emits too.\n// `-readonly` because a field collection is inferred with `const`, and the generated\n// table interfaces declare their nested props mutable.\ntype NestedProps<Fields> = {\n -readonly [K in keyof Fields as null extends output<Fields[K]> ? never : K]: DBColumn<Fields[K]>;\n} & {\n -readonly [K in keyof Fields as null extends output<Fields[K]> ? K : never]?: DBColumn<Fields[K]>;\n};\n\n// The generator reaches for ObjectColumnType only when the object holds something whose\n// select and insert types differ: a timestamp, an optional prop, or a filled-in one.\ntype NestedNeedsColumnType<Fields> = true extends {\n [K in keyof Fields]: DBFieldType<Fields[K]> extends \"date\" | \"datetime\"\n ? true\n : null extends output<Fields[K]>\n ? true\n : DBFieldType<Fields[K]> extends \"nested\"\n ? NestedNeedsColumnType<NestedFieldsOf<Fields[K]>>\n : Fields[K] extends TailorAnyDBField\n ? IsAutoFilledDBField<Fields[K]>\n : false;\n}[keyof Fields]\n ? true\n : false;\n\ntype NestedColumn<F> =\n NestedNeedsColumnType<NestedFieldsOf<F>> extends true\n ? ObjectColumnType<FlattenColumns<NestedProps<NestedFieldsOf<F>>>>\n : FlattenColumns<NestedProps<NestedFieldsOf<F>>>;\n\ntype ElementColumn<F> =\n DBFieldType<F> extends \"date\" | \"datetime\"\n ? Timestamp\n : DBFieldType<F> extends \"nested\"\n ? NestedColumn<F>\n : ElementOutput<F>;\n\n// A ColumnType cannot sit inside an array — Kysely only unwraps it at the top level of a\n// table property — so an array of them keeps the ColumnType outermost.\ntype ArrayedColumn<F> =\n IsArrayDBField<F> extends true\n ? ElementColumn<F> extends ColumnType<unknown, unknown, unknown>\n ? ArrayColumnType<ElementColumn<F>>\n : ElementColumn<F>[]\n : ElementColumn<F>;\n\ntype NullableColumn<F> = null extends output<F> ? ArrayedColumn<F> | null : ArrayedColumn<F>;\n\ntype DBColumn<F> = F extends TailorAnyDBField\n ? IsReadOnlyDBField<F> extends true\n ? Serial<NullableColumn<F>>\n : IsAutoFilledDBField<F> extends true\n ? Generated<NullableColumn<F>>\n : NullableColumn<F>\n : never;\n\n// The column map the three derived types are built from. Not exported: it is how the\n// mapping is expressed, not something callers need to name.\ntype TailorDBColumns<T extends TailorDBColumnsSource> = {\n [K in keyof DBFieldsOf<T>]: K extends \"id\"\n ? Generated<output<DBFieldsOf<T>[K]>>\n : DBColumn<DBFieldsOf<T>[K]>;\n};\n\n/**\n * Create input derived from a TailorDB table (`typeof myTable`) or a field collection.\n *\n * Each field resolves to the column type `kyselyTypePlugin` writes for it, so this and\n * the generated table types agree: `.serial()` fields are never caller-supplied,\n * `.default()` / `.hooks({ create })` fields may be omitted, optional fields stay\n * optional, `id` is platform-generated, and a date or datetime reads back as `Date`.\n *\n * Pass a field collection when the fields are a type parameter — a shared module that\n * lets each project extend a table with its own fields cannot name a generated table\n * type. Declare it as `<const F extends Record<string, TailorAnyDBField>>` so the field\n * types are inferred; a bare `Record<string, TailorAnyDBField>` erases them and nothing\n * is checked.\n *\n * Hand the result to callers rather than consuming it inside the generic that declares\n * it: while `F` is still an unresolved type parameter the mapping stays deferred, so\n * assigning to it inside the function body reports the unevaluated conditional rather\n * than a readable shape.\n * @example\n * function createInput<const F extends Record<string, TailorAnyDBField>>(fields: F) {\n * return (input: TailorDBInsertable<F>) => { ... };\n * }\n */\nexport type TailorDBInsertable<T extends TailorDBColumnsSource> = FlattenColumns<\n Insertable<TailorDBColumns<T>>\n>;\n\n/** Read shape of a TailorDB table or field collection. See {@link TailorDBInsertable}. */\nexport type TailorDBSelectable<T extends TailorDBColumnsSource> = FlattenColumns<\n Selectable<TailorDBColumns<T>>\n>;\n\n/** Update input for a TailorDB table or field collection. See {@link TailorDBInsertable}. */\nexport type TailorDBUpdateable<T extends TailorDBColumnsSource> = FlattenColumns<\n Updateable<TailorDBColumns<T>>\n>;\n"],"mappings":";;;;;;;;;;;;;;;;;;;;AAsFA,SAAgB,cAAkB;CAChC,OAAO,SAAS,MACd,WACA,QACuB;EAEvB,OAAO,IAAIA,SAAc;GACvB,SAAS,IAAIC,kBAAgB,IAFZ,SAAS,OAAO,EAAE,UAAU,CAEX,CAAC;GACnC,GAAG;EACL,CAAC;CACH;AACF"}