@cosmicdrift/kumiko-framework 0.389.0 → 0.390.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/AGENTS.md +9 -4
- package/README.md +1 -1
- package/agents/examples/apex-surface-auth.md +2 -3
- package/agents/examples/api-worker-split.md +9 -2
- package/agents/examples/auth-claims.md +1 -1
- package/agents/examples/cross-feature-events.md +12 -12
- package/agents/examples/crypto-shredding-hr.md +2 -2
- package/agents/examples/encrypted-tenant-config.md +1 -1
- package/agents/examples/error-contract.md +12 -7
- package/agents/examples/event-sourcing.md +29 -29
- package/agents/examples/files-post-processing.md +10 -8
- package/agents/examples/inbound-mail-triage.md +1 -0
- package/agents/examples/lane-routing.md +2 -1
- package/agents/examples/legal-pages.md +2 -2
- package/agents/examples/lifecycle-hooks.md +3 -3
- package/agents/examples/managed-config.md +4 -4
- package/agents/examples/managed-pages.md +1 -1
- package/agents/examples/relations.md +19 -4
- package/agents/examples/search.md +4 -4
- package/agents/examples/secrets-demo.md +9 -6
- package/agents/examples/state-machine.md +2 -2
- package/agents/examples/tenant-settings.md +1 -1
- package/agents/examples/user-data-rights.md +3 -6
- package/agents/examples/workflow-engine.md +53 -47
- package/agents/examples.md +4 -4
- package/agents/features.md +1 -1
- package/dist/api/auth-middleware.js +1 -1
- package/dist/api/auth-routes-invite.js +2 -1
- package/dist/api/entity-read-access.d.ts +3 -1
- package/dist/api/export/export-columns.d.ts +3 -1
- package/dist/api/export/export-route.js +3 -2
- package/dist/api/export/export-screen.d.ts +2 -1
- package/dist/api/extra-route.d.ts +3 -1
- package/dist/api/index.d.ts +23 -27
- package/dist/api/index.js +13 -15
- package/dist/api/jwt.js +1 -1
- package/dist/api/observability-middleware.d.ts +1 -1
- package/dist/api/observability-middleware.js +2 -1
- package/dist/api/request-context-internals.d.ts +31 -0
- package/dist/api/request-context-internals.js +11 -0
- package/dist/api/request-context-scopes.d.ts +14 -0
- package/dist/api/request-context-scopes.js +69 -0
- package/dist/api/request-context.d.ts +1 -40
- package/dist/api/request-context.js +22 -51
- package/dist/api/request-id-middleware.d.ts +1 -1
- package/dist/api/route-registrars.d.ts +2 -1
- package/dist/api/route-registrars.js +1 -1
- package/dist/api/routes.js +7 -3
- package/dist/api/server-boot-checks.d.ts +1 -1
- package/dist/api/server-boot-checks.js +2 -2
- package/dist/api/server-event-dispatcher.d.ts +6 -1
- package/dist/api/server-event-dispatcher.js +3 -4
- package/dist/api/server-extra-routes.d.ts +1 -1
- package/dist/api/server-extra-routes.js +2 -1
- package/dist/api/server-middleware.js +3 -1
- package/dist/api/server-routes.d.ts +2 -1
- package/dist/api/server-wiring.js +6 -4
- package/dist/api/server.d.ts +2 -1
- package/dist/api/sse-route.d.ts +2 -1
- package/dist/api/tenant-scoped-secrets.d.ts +2 -0
- package/dist/api/tenant-scoped-secrets.js +13 -0
- package/dist/api/websocket-route.d.ts +1 -1
- package/dist/auth/index.d.ts +0 -1
- package/dist/auth/roles.d.ts +0 -5
- package/dist/compliance/duration-spec.d.ts +0 -1
- package/dist/compliance/duration-spec.js +0 -5
- package/dist/compliance/index.d.ts +4 -4
- package/dist/compliance/index.js +2 -2
- package/dist/compliance/profiles.d.ts +0 -15
- package/dist/compliance/profiles.js +0 -23
- package/dist/config/index.d.ts +10 -10
- package/dist/config/index.js +13 -1
- package/dist/config/internals.d.ts +9 -0
- package/dist/config/internals.js +1 -0
- package/dist/consumer-cli-internals.d.ts +4 -0
- package/dist/consumer-cli-internals.js +1 -0
- package/dist/consumer-cli.d.ts +1 -4
- package/dist/consumer-cli.js +5 -1
- package/dist/crypto/event-pii.js +1 -1
- package/dist/crypto/index.d.ts +8 -9
- package/dist/crypto/index.js +7 -8
- package/dist/crypto/pg-kms-adapter.js +6 -1
- package/dist/db/apply-entity-event.d.ts +1 -1
- package/dist/db/apply-entity-event.js +15 -47
- package/dist/db/blind-index-cleanup.js +91 -77
- package/dist/db/collect-table-metas.js +1 -1
- package/dist/db/compound-types.d.ts +1 -1
- package/dist/db/compound-types.js +0 -7
- package/dist/db/config-seed.d.ts +2 -1
- package/dist/db/config-seed.js +6 -1
- package/dist/db/connection.d.ts +3 -1
- package/dist/db/connection.js +15 -5
- package/dist/db/cross-tenant-reads.d.ts +1 -1
- package/dist/db/cross-tenant-reads.js +1 -1
- package/dist/db/dialect.d.ts +0 -5
- package/dist/db/dialect.js +0 -3
- package/dist/db/eagerload.d.ts +2 -1
- package/dist/db/entity-field-encryption.d.ts +1 -1
- package/dist/db/entity-table-meta.d.ts +1 -1
- package/dist/db/event-store-executor-context.d.ts +3 -1
- package/dist/db/event-store-executor-context.js +4 -3
- package/dist/db/event-store-executor-read-filter.d.ts +1 -1
- package/dist/db/event-store-executor-read-rows.d.ts +2 -1
- package/dist/db/event-store-executor-read-search.d.ts +2 -1
- package/dist/db/event-store-executor-read-sort.d.ts +2 -1
- package/dist/db/event-store-executor-read.js +2 -2
- package/dist/db/event-store-executor-write-atomic.js +8 -7
- package/dist/db/event-store-executor-write-steps.d.ts +3 -2
- package/dist/db/event-store-executor-write.js +7 -4
- package/dist/db/event-store-executor.d.ts +1 -1
- package/dist/db/executor-managed-tables.d.ts +7 -1
- package/dist/db/executor-managed-tables.js +11 -2
- package/dist/db/index.d.ts +29 -28
- package/dist/db/index.js +22 -20
- package/dist/db/known-table-names.d.ts +6 -0
- package/dist/db/known-table-names.js +21 -0
- package/dist/db/list-aggregate-labels.d.ts +1 -1
- package/dist/db/located-timestamp.d.ts +1 -1
- package/dist/db/located-timestamp.js +0 -5
- package/dist/db/migrate-generator.d.ts +17 -1
- package/dist/db/migrate-generator.js +50 -20
- package/dist/db/migrate-primary-key.d.ts +12 -0
- package/dist/db/migrate-primary-key.js +45 -0
- package/dist/db/migrate-rls-diff.d.ts +20 -0
- package/dist/db/migrate-rls-diff.js +61 -0
- package/dist/db/migrate-runner.js +4 -0
- package/dist/db/money.d.ts +1 -1
- package/dist/db/money.js +1 -1
- package/dist/db/parent-ref-clause.d.ts +2 -1
- package/dist/db/pg-error.d.ts +2 -0
- package/dist/db/pg-error.js +11 -0
- package/dist/db/queries/ddl.d.ts +3 -0
- package/dist/db/queries/ddl.js +34 -1
- package/dist/db/queries/event-store.js +4 -2
- package/dist/db/queries/event-tenants.d.ts +2 -0
- package/dist/db/queries/event-tenants.js +17 -0
- package/dist/db/queries/rebuild-rls-guard.d.ts +2 -0
- package/dist/db/queries/rebuild-rls-guard.js +29 -0
- package/dist/db/queries/rls-boot-catalog.d.ts +16 -0
- package/dist/db/queries/rls-boot-catalog.js +39 -0
- package/dist/db/queries/rls-catalog.d.ts +6 -0
- package/dist/db/queries/rls-catalog.js +82 -0
- package/dist/db/queries/rls-scope.d.ts +3 -0
- package/dist/db/queries/rls-scope.js +17 -0
- package/dist/db/queries/rls-shape.d.ts +10 -0
- package/dist/db/queries/rls-shape.js +42 -0
- package/dist/db/queries/session-advisory-lock.d.ts +2 -0
- package/dist/db/queries/session-advisory-lock.js +23 -0
- package/dist/db/queries/shadow-swap.d.ts +1 -2
- package/dist/db/queries/shadow-swap.js +9 -25
- package/dist/db/queries/test-stack.d.ts +4 -1
- package/dist/db/queries/test-stack.js +83 -2
- package/dist/db/query.js +11 -7
- package/dist/db/reference-data.d.ts +1 -1
- package/dist/db/reference-data.js +6 -1
- package/dist/db/render-ddl.d.ts +6 -2
- package/dist/db/render-ddl.js +7 -7
- package/dist/db/render-rls-ddl.d.ts +35 -0
- package/dist/db/render-rls-ddl.js +127 -0
- package/dist/db/replay-migration-sql.d.ts +3 -1
- package/dist/db/replay-migration-sql.js +22 -5
- package/dist/db/replay-rls.d.ts +25 -0
- package/dist/db/replay-rls.js +156 -0
- package/dist/db/row-level-security-boot-check.d.ts +5 -0
- package/dist/db/row-level-security-boot-check.js +85 -0
- package/dist/db/row-level-security-connection.d.ts +3 -0
- package/dist/db/row-level-security-connection.js +213 -0
- package/dist/db/row-level-security-scope.d.ts +33 -0
- package/dist/db/row-level-security-scope.js +127 -0
- package/dist/db/scope-tenant-db-to-tenant.d.ts +3 -0
- package/dist/db/scope-tenant-db-to-tenant.js +14 -0
- package/dist/db/sql-identifier.d.ts +1 -0
- package/dist/db/sql-identifier.js +3 -0
- package/dist/db/table-builder.d.ts +2 -1
- package/dist/db/table-builder.js +1 -1
- package/dist/db/table-info.js +1 -1
- package/dist/db/table-push.d.ts +11 -2
- package/dist/db/table-push.js +15 -2
- package/dist/db/tenant-db-runner.d.ts +3 -1
- package/dist/db/tenant-db-runner.js +4 -3
- package/dist/db/tenant-db-scoped-rebind.d.ts +10 -0
- package/dist/db/tenant-db-scoped-rebind.js +33 -0
- package/dist/db/tenant-db-statement-runner.d.ts +13 -0
- package/dist/db/tenant-db-statement-runner.js +48 -0
- package/dist/db/tenant-db.d.ts +17 -12
- package/dist/db/tenant-db.js +49 -120
- package/dist/db/tenant-id-filter.d.ts +3 -0
- package/dist/db/tenant-id-filter.js +30 -0
- package/dist/db/transaction-serialization.d.ts +6 -0
- package/dist/db/transaction-serialization.js +60 -0
- package/dist/derivatives/delete-stored-file.js +1 -1
- package/dist/derivatives/index.d.ts +2 -5
- package/dist/derivatives/index.js +2 -3
- package/dist/engine/access.d.ts +2 -1
- package/dist/engine/access.js +1 -1
- package/dist/engine/boot-validator/entity-handler.d.ts +2 -1
- package/dist/engine/boot-validator/entity-handler.js +1 -1
- package/dist/engine/boot-validator/entity-list-aggregate-options.d.ts +1 -1
- package/dist/engine/boot-validator/list-table-aggregate-options.d.ts +1 -1
- package/dist/engine/boot-validator/list-table-aggregate-query.d.ts +2 -1
- package/dist/engine/boot-validator/nav.d.ts +3 -1
- package/dist/engine/boot-validator/nav.js +1 -1
- package/dist/engine/boot-validator/ownership.d.ts +2 -1
- package/dist/engine/boot-validator/parent-ref.d.ts +2 -1
- package/dist/engine/boot-validator/projection-list-screens.d.ts +2 -1
- package/dist/engine/boot-validator/query-refs.d.ts +2 -1
- package/dist/engine/boot-validator/screens-forms.d.ts +2 -1
- package/dist/engine/boot-validator/screens-kind-shared.d.ts +3 -1
- package/dist/engine/boot-validator/screens.d.ts +2 -1
- package/dist/engine/boot-validator/workspaces.d.ts +3 -1
- package/dist/engine/bridge-stub.d.ts +5 -2
- package/dist/engine/bridge-stub.js +39 -24
- package/dist/engine/config-helpers.d.ts +2 -2
- package/dist/engine/config-helpers.js +0 -9
- package/dist/engine/constants.d.ts +0 -10
- package/dist/engine/constants.js +0 -8
- package/dist/engine/create-app.js +1 -1
- package/dist/engine/define-feature.d.ts +2 -1
- package/dist/engine/define-feature.js +1 -2
- package/dist/engine/define-handler.d.ts +1 -1
- package/dist/engine/define-step.d.ts +0 -1
- package/dist/engine/define-step.js +0 -3
- package/dist/engine/embedded-derived.d.ts +1 -1
- package/dist/engine/entity-handlers.d.ts +2 -1
- package/dist/engine/entity-handlers.js +7 -7
- package/dist/engine/entity-list-runtime-options.js +3 -1
- package/dist/engine/entity-list-searchability.d.ts +2 -1
- package/dist/engine/event-def.d.ts +2 -1
- package/dist/engine/event-helpers.d.ts +3 -1
- package/dist/engine/event-helpers.js +3 -3
- package/dist/engine/extension-names.d.ts +2 -8
- package/dist/engine/extension-names.js +2 -2
- package/dist/engine/extension-selector-plugins.d.ts +1 -1
- package/dist/engine/extensions/storage-provider.d.ts +1 -2
- package/dist/engine/extensions/user-data.d.ts +0 -8
- package/dist/engine/factories.d.ts +2 -1
- package/dist/engine/feature-builder-state.d.ts +8 -1
- package/dist/engine/feature-changelog.d.ts +1 -1
- package/dist/engine/feature-config-events-jobs.d.ts +4 -1
- package/dist/engine/feature-entity-handlers.d.ts +5 -1
- package/dist/engine/feature-manifest.js +1 -1
- package/dist/engine/feature-ui-extensions.d.ts +7 -1
- package/dist/engine/feature-ui-extensions.js +6 -4
- package/dist/engine/field-access.d.ts +2 -1
- package/dist/engine/handler-field-references.d.ts +0 -4
- package/dist/engine/index.d.ts +57 -54
- package/dist/engine/index.js +22 -27
- package/dist/engine/instruction-fields.d.ts +1 -1
- package/dist/engine/personal-data-fields.d.ts +1 -1
- package/dist/engine/qualified-name.d.ts +0 -1
- package/dist/engine/read-claim.d.ts +2 -1
- package/dist/engine/registry-facade.js +0 -3
- package/dist/engine/registry-ingest.d.ts +2 -1
- package/dist/engine/registry-ingest.js +1 -2
- package/dist/engine/registry-state.d.ts +12 -2
- package/dist/engine/registry-state.js +2 -3
- package/dist/engine/registry-validate.d.ts +3 -1
- package/dist/engine/registry-validate.js +7 -7
- package/dist/engine/run-in.d.ts +1 -1
- package/dist/engine/run-in.js +0 -1
- package/dist/engine/schema-builder.d.ts +1 -1
- package/dist/engine/schema-builder.js +1 -1
- package/dist/engine/screen-filter-ops.d.ts +2 -1
- package/dist/engine/screen-filter-ops.js +0 -5
- package/dist/engine/soft-delete-cleanup.d.ts +1 -1
- package/dist/engine/soft-delete-cleanup.js +4 -4
- package/dist/engine/state-machine.js +2 -1
- package/dist/engine/steps/_read-source.js +1 -1
- package/dist/engine/steps/aggregate-append-event.js +2 -2
- package/dist/engine/steps/call-feature.js +2 -2
- package/dist/engine/steps/mail-send.js +1 -1
- package/dist/engine/steps/retry.js +1 -1
- package/dist/engine/steps/wait-for-event.js +1 -1
- package/dist/engine/steps/wait.js +1 -1
- package/dist/engine/steps/webhook-send.js +1 -1
- package/dist/engine/template-variables.d.ts +2 -1
- package/dist/engine/transfer-adjacency.d.ts +1 -1
- package/dist/engine/types/index.d.ts +8 -31
- package/dist/engine/types/index.js +2 -10
- package/dist/engine/validation.d.ts +2 -1
- package/dist/entrypoint/index.d.ts +7 -35
- package/dist/entrypoint/index.js +7 -1
- package/dist/entrypoint/internals.d.ts +40 -0
- package/dist/entrypoint/internals.js +1 -0
- package/dist/entrypoint/row-level-security-mode-check.d.ts +3 -0
- package/dist/entrypoint/row-level-security-mode-check.js +19 -0
- package/dist/env/dry-run-internals.d.ts +10 -0
- package/dist/env/dry-run-internals.js +1 -0
- package/dist/env/dry-run.d.ts +1 -10
- package/dist/env/dry-run.js +2 -1
- package/dist/env/index.d.ts +1 -85
- package/dist/env/index.js +6 -50
- package/dist/env/internals.d.ts +87 -0
- package/dist/env/internals.js +53 -0
- package/dist/errors/classes.js +2 -2
- package/dist/errors/index.d.ts +5 -14
- package/dist/errors/index.js +4 -9
- package/dist/errors/member-resolution.js +1 -1
- package/dist/errors/reasons.d.ts +0 -1
- package/dist/errors/reasons.js +7 -7
- package/dist/errors/serialize.d.ts +0 -18
- package/dist/errors/serialize.js +0 -27
- package/dist/es-ops/index.d.ts +4 -4
- package/dist/es-ops/index.js +2 -2
- package/dist/es-ops/operations-schema.d.ts +1 -1
- package/dist/es-ops/types.d.ts +4 -5
- package/dist/event-store/admin-api-internals.d.ts +14 -0
- package/dist/event-store/admin-api-internals.js +1 -0
- package/dist/event-store/admin-api.d.ts +1 -14
- package/dist/event-store/admin-api.js +11 -6
- package/dist/event-store/archive.js +4 -2
- package/dist/event-store/errors.js +2 -2
- package/dist/event-store/event-store.js +41 -34
- package/dist/event-store/events-schema.js +4 -1
- package/dist/event-store/index.d.ts +11 -13
- package/dist/event-store/index.js +7 -9
- package/dist/event-store/rebuild-dead-letter.js +4 -2
- package/dist/event-store/snapshot.js +4 -3
- package/dist/event-store/stream-scope.d.ts +2 -0
- package/dist/event-store/stream-scope.js +6 -0
- package/dist/event-store/upcaster-dead-letter.js +4 -2
- package/dist/event-store/upcaster.d.ts +2 -1
- package/dist/files/action-form-upload.d.ts +2 -1
- package/dist/files/action-form-upload.js +1 -1
- package/dist/files/assert-file-refs-belong-to-tenant.d.ts +2 -1
- package/dist/files/assert-file-refs-belong-to-tenant.js +1 -1
- package/dist/files/bind-pending-file-refs.d.ts +2 -1
- package/dist/files/bind-pending-file-refs.js +2 -1
- package/dist/files/bind-referenced-files.write.js +1 -1
- package/dist/files/create-file-ref-from-bytes.d.ts +6 -3
- package/dist/files/create-file-ref-from-bytes.js +3 -3
- package/dist/files/create-file-ref.d.ts +3 -2
- package/dist/files/create-file-ref.js +2 -2
- package/dist/files/dispose-removed-file-refs.d.ts +2 -1
- package/dist/files/dispose-removed-file-refs.js +1 -1
- package/dist/files/feature.js +2 -2
- package/dist/files/file-handle.js +1 -1
- package/dist/files/file-routes.d.ts +1 -1
- package/dist/files/file-routes.js +12 -2
- package/dist/files/index.d.ts +11 -13
- package/dist/files/index.js +5 -7
- package/dist/files/load-save-file-refs.d.ts +2 -1
- package/dist/files/load-save-file-refs.js +1 -1
- package/dist/files/provider-resolver.d.ts +5 -4
- package/dist/files/provider-resolver.js +4 -4
- package/dist/files/storage-tracking.js +4 -2
- package/dist/files/sweep-orphaned-uploads.d.ts +1 -1
- package/dist/files/sweep-orphaned-uploads.js +1 -1
- package/dist/i18n/index.d.ts +2 -8
- package/dist/i18n/index.js +1 -1
- package/dist/i18n/internals.d.ts +7 -0
- package/dist/i18n/internals.js +1 -0
- package/dist/i18n/required-surface-keys.d.ts +4 -1
- package/dist/internal/row-level-security.d.ts +3 -0
- package/dist/internal/row-level-security.js +3 -0
- package/dist/internal/stack-support.d.ts +1 -1
- package/dist/internal/stack-support.js +1 -1
- package/dist/internal/testing.d.ts +1 -0
- package/dist/internal/testing.js +9 -5
- package/dist/jobs/index.d.ts +1 -1
- package/dist/jobs/job-append-event.d.ts +12 -0
- package/dist/jobs/job-append-event.js +30 -0
- package/dist/jobs/job-runner-context.d.ts +2 -2
- package/dist/jobs/job-runner-context.js +46 -16
- package/dist/jobs/job-runner-execution.d.ts +1 -1
- package/dist/jobs/job-runner-execution.js +6 -4
- package/dist/jobs/job-runner-gates.d.ts +1 -1
- package/dist/jobs/job-runner-gates.js +0 -1
- package/dist/jobs/job-runner-helpers.d.ts +11 -4
- package/dist/jobs/job-runner-helpers.js +10 -1
- package/dist/jobs/job-runner-scope.d.ts +5 -2
- package/dist/jobs/job-runner-types.d.ts +2 -1
- package/dist/jobs/job-runner.js +19 -6
- package/dist/jobs/max-per-tenant.d.ts +1 -1
- package/dist/logging/index.d.ts +1 -2
- package/dist/logging/index.js +1 -1
- package/dist/logging/pino-logger.js +1 -1
- package/dist/logging/utils.d.ts +1 -0
- package/dist/logging/utils.js +6 -0
- package/dist/migrations/index.d.ts +3 -3
- package/dist/migrations/index.js +3 -3
- package/dist/migrations/pending-rebuilds.d.ts +1 -1
- package/dist/migrations/pending-rebuilds.js +1 -1
- package/dist/migrations/pii-event-backfill.js +4 -1
- package/dist/observability/escape-hatch-report.d.ts +2 -1
- package/dist/observability/index.d.ts +7 -15
- package/dist/observability/index.js +4 -12
- package/dist/observability/metric-validator.js +1 -1
- package/dist/observability/metrics-handle.d.ts +0 -1
- package/dist/observability/metrics-handle.js +2 -15
- package/dist/observability/recording-tracer.d.ts +1 -2
- package/dist/observability/recording-tracer.js +0 -6
- package/dist/observability/sensitive-filter.d.ts +0 -2
- package/dist/observability/sensitive-filter.js +0 -29
- package/dist/pipeline/active-membership.d.ts +2 -1
- package/dist/pipeline/active-membership.js +6 -2
- package/dist/pipeline/append-event-core.d.ts +2 -1
- package/dist/pipeline/append-event-core.js +2 -2
- package/dist/pipeline/attach-outside-transaction.d.ts +3 -0
- package/dist/pipeline/attach-outside-transaction.js +13 -0
- package/dist/pipeline/auth-claims-resolver.d.ts +2 -1
- package/dist/pipeline/cascade-handler.d.ts +2 -1
- package/dist/pipeline/cascade-handler.js +3 -2
- package/dist/pipeline/config-accessor-factory.d.ts +1 -1
- package/dist/pipeline/config-accessor-factory.js +1 -1
- package/dist/pipeline/context-services.d.ts +56 -0
- package/dist/pipeline/context-services.js +73 -0
- package/dist/pipeline/dispatch-batch.d.ts +2 -1
- package/dist/pipeline/dispatch-batch.js +31 -18
- package/dist/pipeline/dispatch-query.js +5 -4
- package/dist/pipeline/dispatch-scope.d.ts +6 -0
- package/dist/pipeline/dispatch-scope.js +27 -0
- package/dist/pipeline/dispatch-shared.d.ts +13 -9
- package/dist/pipeline/dispatch-shared.js +75 -198
- package/dist/pipeline/dispatch-stream.js +8 -4
- package/dist/pipeline/dispatch-write.d.ts +2 -1
- package/dist/pipeline/dispatch-write.js +10 -8
- package/dist/pipeline/dispatcher-utils.d.ts +3 -1
- package/dist/pipeline/dispatcher-utils.js +8 -2
- package/dist/pipeline/dispatcher.d.ts +3 -2
- package/dist/pipeline/dispatcher.js +4 -3
- package/dist/pipeline/event-consumer-state.d.ts +0 -1
- package/dist/pipeline/event-dispatcher-delivery.d.ts +1 -1
- package/dist/pipeline/event-dispatcher-delivery.js +4 -2
- package/dist/pipeline/event-dispatcher.d.ts +2 -2
- package/dist/pipeline/event-dispatcher.js +7 -3
- package/dist/pipeline/event-retention.js +59 -56
- package/dist/pipeline/handler-access-error.js +2 -1
- package/dist/pipeline/handler-context-auth.d.ts +5 -6
- package/dist/pipeline/handler-context-auth.js +7 -4
- package/dist/pipeline/handler-context-config.d.ts +2 -5
- package/dist/pipeline/handler-context-config.js +2 -2
- package/dist/pipeline/handler-context-db.d.ts +32 -7
- package/dist/pipeline/handler-context-db.js +26 -17
- package/dist/pipeline/handler-context-dispatch.d.ts +13 -7
- package/dist/pipeline/handler-context-dispatch.js +9 -8
- package/dist/pipeline/handler-context-events.d.ts +22 -36
- package/dist/pipeline/handler-context-events.js +36 -31
- package/dist/pipeline/handler-context-member-resolution.d.ts +2 -0
- package/dist/pipeline/handler-context-member-resolution.js +110 -0
- package/dist/pipeline/handler-context-notify.d.ts +3 -2
- package/dist/pipeline/handler-context-notify.js +1 -1
- package/dist/pipeline/handler-context-observability.d.ts +2 -4
- package/dist/pipeline/handler-context-observability.js +7 -5
- package/dist/pipeline/handler-context-phase-denials.d.ts +11 -0
- package/dist/pipeline/handler-context-phase-denials.js +98 -0
- package/dist/pipeline/handler-context-scope.d.ts +7 -10
- package/dist/pipeline/handler-context-scope.js +18 -20
- package/dist/pipeline/index.d.ts +9 -21
- package/dist/pipeline/index.js +5 -7
- package/dist/pipeline/irreversible-operation-gate.d.ts +1 -1
- package/dist/pipeline/irreversible-operation-gate.js +2 -2
- package/dist/pipeline/lifecycle-pipeline.d.ts +8 -7
- package/dist/pipeline/lifecycle-pipeline.js +9 -15
- package/dist/pipeline/member-read-only-transaction.js +11 -3
- package/dist/pipeline/member-reader.d.ts +1 -1
- package/dist/pipeline/member-reader.js +2 -2
- package/dist/pipeline/msp-rebuild.js +5 -3
- package/dist/pipeline/multi-stream-apply-context.js +3 -2
- package/dist/pipeline/notify-scope.d.ts +2 -1
- package/dist/pipeline/pre-handler-gates.d.ts +2 -1
- package/dist/pipeline/pre-transaction-reservations.d.ts +3 -3
- package/dist/pipeline/pre-transaction-reservations.js +9 -7
- package/dist/pipeline/projection-rebuild.js +12 -5
- package/dist/pipeline/projection-state.d.ts +0 -6
- package/dist/pipeline/projection-state.js +0 -5
- package/dist/pipeline/projections-runner.d.ts +2 -1
- package/dist/pipeline/projections-runner.js +10 -6
- package/dist/pipeline/system-hooks.d.ts +3 -1
- package/dist/pipeline/system-hooks.js +6 -4
- package/dist/pipeline/system-identity-switch.d.ts +4 -2
- package/dist/pipeline/system-identity-switch.js +51 -36
- package/dist/pipeline/typed-append-event.d.ts +2 -0
- package/dist/pipeline/typed-append-event.js +4 -0
- package/dist/pipeline/write-origin.js +2 -2
- package/dist/pipeline/write-result-masking.d.ts +1 -1
- package/dist/random/index.d.ts +1 -2
- package/dist/random/index.js +1 -2
- package/dist/rate-limit/bucket.d.ts +2 -1
- package/dist/rate-limit/middleware.js +2 -1
- package/dist/redis/index.d.ts +3 -4
- package/dist/redis/index.js +2 -2
- package/dist/schema-cli/apply-command.js +5 -2
- package/dist/schema-cli/baseline-command.js +7 -2
- package/dist/schema-cli/generate-command.js +7 -9
- package/dist/schema-cli/shared.d.ts +4 -0
- package/dist/schema-cli/shared.js +21 -2
- package/dist/schema-cli/status-command.js +8 -2
- package/dist/schema-cli/validate-command.js +52 -4
- package/dist/schema-cli.d.ts +0 -1
- package/dist/search/configure-tenant-index.d.ts +1 -3
- package/dist/search/configure-tenant-index.js +0 -4
- package/dist/search/index.d.ts +1 -4
- package/dist/search/index.js +0 -2
- package/dist/search/meilisearch-adapter-internals.d.ts +8 -0
- package/dist/search/meilisearch-adapter-internals.js +9 -0
- package/dist/search/meilisearch-adapter.d.ts +1 -8
- package/dist/search/meilisearch-adapter.js +6 -7
- package/dist/search/meilisearch-peer.d.ts +2 -0
- package/dist/search/meilisearch-peer.js +5 -0
- package/dist/search/reindex-entity.js +93 -87
- package/dist/secrets/index.d.ts +3 -4
- package/dist/secrets/index.js +2 -3
- package/dist/seeding/index.d.ts +2 -2
- package/dist/seeding/index.js +1 -2
- package/dist/time/index.d.ts +2 -2
- package/dist/time/index.js +1 -1
- package/dist/time/tz-context.d.ts +0 -5
- package/dist/time/tz-context.js +0 -9
- package/dist/ui-types/index.d.ts +8 -11
- package/dist/ui-types/index.js +3 -3
- package/dist/upgrade-changelog.d.ts +3 -2
- package/dist/upgrade-changelog.js +12 -8
- package/dist/upgrade-cli-internals.d.ts +8 -0
- package/dist/upgrade-cli-internals.js +63 -0
- package/dist/upgrade-cli.d.ts +1 -9
- package/dist/upgrade-cli.js +10 -64
- package/dist/utils/import-optional-peer.d.ts +6 -0
- package/dist/utils/import-optional-peer.js +19 -0
- package/dist/utils/index.d.ts +1 -4
- package/dist/utils/index.js +1 -4
- package/package.json +22 -18
- package/src/changes.json +206 -0
- package/dist/crypto/request-kms-cache.d.ts +0 -8
- package/dist/crypto/request-kms-cache.js +0 -21
- package/dist/engine/codemod/index.d.ts +0 -2
- package/dist/engine/codemod/index.js +0 -1
- package/dist/engine/codemod/pipeline-codemod.d.ts +0 -50
- package/dist/engine/codemod/pipeline-codemod.js +0 -536
- package/dist/engine/feature-ast/entity-field-types.d.ts +0 -13
- package/dist/engine/feature-ast/entity-field-types.js +0 -35
- package/dist/engine/feature-ast/extractors/ai-steps.d.ts +0 -6
- package/dist/engine/feature-ast/extractors/ai-steps.js +0 -254
- package/dist/engine/feature-ast/extractors/events.d.ts +0 -5
- package/dist/engine/feature-ast/extractors/events.js +0 -275
- package/dist/engine/feature-ast/extractors/handlers.d.ts +0 -24
- package/dist/engine/feature-ast/extractors/handlers.js +0 -358
- package/dist/engine/feature-ast/extractors/hooks.d.ts +0 -24
- package/dist/engine/feature-ast/extractors/hooks.js +0 -248
- package/dist/engine/feature-ast/extractors/index.d.ts +0 -14
- package/dist/engine/feature-ast/extractors/index.js +0 -13
- package/dist/engine/feature-ast/extractors/jobs-routes.d.ts +0 -7
- package/dist/engine/feature-ast/extractors/jobs-routes.js +0 -145
- package/dist/engine/feature-ast/extractors/projections-screens.d.ts +0 -10
- package/dist/engine/feature-ast/extractors/projections-screens.js +0 -195
- package/dist/engine/feature-ast/extractors/resolve-import.d.ts +0 -21
- package/dist/engine/feature-ast/extractors/resolve-import.js +0 -180
- package/dist/engine/feature-ast/extractors/round1.d.ts +0 -11
- package/dist/engine/feature-ast/extractors/round1.js +0 -87
- package/dist/engine/feature-ast/extractors/round2.d.ts +0 -7
- package/dist/engine/feature-ast/extractors/round2.js +0 -191
- package/dist/engine/feature-ast/extractors/round3.d.ts +0 -23
- package/dist/engine/feature-ast/extractors/round3.js +0 -292
- package/dist/engine/feature-ast/extractors/round5.d.ts +0 -9
- package/dist/engine/feature-ast/extractors/round5.js +0 -68
- package/dist/engine/feature-ast/extractors/round6.d.ts +0 -4
- package/dist/engine/feature-ast/extractors/round6.js +0 -17
- package/dist/engine/feature-ast/extractors/shared.d.ts +0 -94
- package/dist/engine/feature-ast/extractors/shared.js +0 -343
- package/dist/engine/feature-ast/index.d.ts +0 -16
- package/dist/engine/feature-ast/index.js +0 -10
- package/dist/engine/feature-ast/parse.d.ts +0 -31
- package/dist/engine/feature-ast/parse.js +0 -485
- package/dist/engine/feature-ast/patch.d.ts +0 -212
- package/dist/engine/feature-ast/patch.js +0 -611
- package/dist/engine/feature-ast/patcher.d.ts +0 -217
- package/dist/engine/feature-ast/patcher.js +0 -281
- package/dist/engine/feature-ast/pattern-change-schema.d.ts +0 -1238
- package/dist/engine/feature-ast/pattern-change-schema.js +0 -1072
- package/dist/engine/feature-ast/pattern-id-matchers.d.ts +0 -7
- package/dist/engine/feature-ast/pattern-id-matchers.js +0 -211
- package/dist/engine/feature-ast/pattern-id-schema.d.ts +0 -251
- package/dist/engine/feature-ast/pattern-id-schema.js +0 -166
- package/dist/engine/feature-ast/patterns.d.ts +0 -322
- package/dist/engine/feature-ast/patterns.js +0 -107
- package/dist/engine/feature-ast/render.d.ts +0 -47
- package/dist/engine/feature-ast/render.js +0 -666
- package/dist/engine/feature-ast/source-location.d.ts +0 -17
- package/dist/engine/feature-ast/source-location.js +0 -27
- package/dist/engine/pattern-library/index.d.ts +0 -2
- package/dist/engine/pattern-library/index.js +0 -3
- package/dist/engine/pattern-library/library.d.ts +0 -14
- package/dist/engine/pattern-library/library.js +0 -94
- package/dist/engine/pattern-library/mixed-schemas.d.ts +0 -16
- package/dist/engine/pattern-library/mixed-schemas.js +0 -559
- package/dist/engine/pattern-library/opaque-schemas.d.ts +0 -7
- package/dist/engine/pattern-library/opaque-schemas.js +0 -115
- package/dist/engine/pattern-library/shared-fields.d.ts +0 -122
- package/dist/engine/pattern-library/shared-fields.js +0 -88
- package/dist/engine/pattern-library/static-schemas.d.ts +0 -21
- package/dist/engine/pattern-library/static-schemas.js +0 -487
- package/dist/engine/pattern-library/types.d.ts +0 -158
- package/dist/engine/pattern-library/types.js +0 -36
- package/dist/engine/resolve-config-or-param.d.ts +0 -18
- package/dist/engine/resolve-config-or-param.js +0 -76
- package/src/scripts/codemod/README.md +0 -187
- package/src/scripts/codemod/codemod-support.ts +0 -334
- package/src/scripts/codemod/collect-source-files.ts +0 -48
- package/src/scripts/codemod/crypto-shredding-testing-move.ts +0 -119
- package/src/scripts/codemod/db-factory.ts +0 -810
- package/src/scripts/codemod/feature-factory.ts +0 -429
- package/src/scripts/codemod/feature-layout.ts +0 -424
- package/src/scripts/codemod/import-extensions.ts +0 -118
- package/src/scripts/codemod/migrate-cross-tenant.ts +0 -328
- package/src/scripts/codemod/migrate-db-raw.ts +0 -401
- package/src/scripts/codemod/migrate-open-to-all.ts +0 -235
- package/src/scripts/codemod/object-form.ts +0 -746
- package/src/scripts/codemod/package-merge.ts +0 -299
- package/src/scripts/codemod/pii-personal-migration.ts +0 -816
- package/src/scripts/codemod/remove-engine-payload-casts.ts +0 -318
- package/src/scripts/codemod/s3-imports.ts +0 -236
- package/src/scripts/codemod/tenant-db-options.ts +0 -454
- package/src/scripts/codemod/testing-injection.ts +0 -215
- package/src/scripts/codemod/testing-move-targets.ts +0 -161
- package/src/scripts/codemod/testing-move.ts +0 -542
- package/src/scripts/codemod/unprocessable-error-details-reason.ts +0 -411
|
@@ -2,7 +2,9 @@ import { EXT_FILE_PROVIDER } from "../engine/extension-names.js";
|
|
|
2
2
|
import { assertSeedModeNotInProduction } from "../event-store/seed-clock.js";
|
|
3
3
|
import { makeFileProviderResolver } from "../files/provider-resolver.js";
|
|
4
4
|
import { createFallbackLogger } from "../logging/index.js";
|
|
5
|
-
import { createNoopProvider
|
|
5
|
+
import { createNoopProvider } from "../observability/index.js";
|
|
6
|
+
import { wrapRedisClient } from "../observability/redis-wrapper.js";
|
|
7
|
+
import { registerStandardMetrics } from "../observability/standard-metrics.js";
|
|
6
8
|
import { configAccessorFactoryOf } from "../pipeline/config-accessor-factory.js";
|
|
7
9
|
import { createDispatcher } from "../pipeline/dispatcher.js";
|
|
8
10
|
import { createLifecycleHooks } from "../pipeline/lifecycle-pipeline.js";
|
|
@@ -28,7 +30,7 @@ export function withFileProviderResolver(registry, context, cacheSync) {
|
|
|
28
30
|
...context,
|
|
29
31
|
_fileProviderResolver: makeFileProviderResolver({
|
|
30
32
|
registry,
|
|
31
|
-
|
|
33
|
+
configAccessorFactory: configAccessorFactoryOf(context),
|
|
32
34
|
secrets: context.secrets,
|
|
33
35
|
db: context.db,
|
|
34
36
|
...(clock ? { now: () => clock.now() } : {}),
|
|
@@ -54,7 +56,7 @@ export function resolveServerWiring(options) {
|
|
|
54
56
|
// Inject tracer + meter into the AppContext so the dispatcher can propagate
|
|
55
57
|
// them into every HandlerContext it builds. Build the per-tenant file-provider
|
|
56
58
|
// resolver once (when a provider plugin is mounted) — the dispatcher uses it
|
|
57
|
-
// to materialise `ctx.files`, the upload routes + MSP-applies share it. The
|
|
59
|
+
// to materialise `ctx.services.files`, the upload routes + MSP-applies share it. The
|
|
58
60
|
// resolver reads config + the s3.secretAccessKey secret under SYSTEM identity.
|
|
59
61
|
const contextWithFiles = withFileProviderResolver(options.registry, options.context, cacheSync);
|
|
60
62
|
const fileProviderResolver = contextWithFiles._fileProviderResolver;
|
|
@@ -142,7 +144,7 @@ function resolveServerSseBroker(explicitSseBroker, bootLog) {
|
|
|
142
144
|
}
|
|
143
145
|
function resolveServerObservability(explicitObservability, registry) {
|
|
144
146
|
// Observability — Noop by default so no call-site needs to null-check.
|
|
145
|
-
// Every handler/middleware that reaches for ctx.tracer / ctx.metrics gets
|
|
147
|
+
// Every handler/middleware that reaches for ctx.obs.tracer / ctx.obs.metrics gets
|
|
146
148
|
// a working, zero-cost fallback when no provider is configured.
|
|
147
149
|
const observability = explicitObservability ?? createNoopProvider();
|
|
148
150
|
// Register framework + feature metrics once on this meter. Standard
|
package/dist/api/server.d.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
|
+
import type { RunIn } from "@cosmicdrift/kumiko-types/config";
|
|
1
2
|
import { Hono } from "hono";
|
|
2
3
|
import type { PgListenClient } from "../db/connection.ts";
|
|
3
|
-
import type { AppContext, Registry
|
|
4
|
+
import type { AppContext, Registry } from "../engine/types/index.ts";
|
|
4
5
|
import type { ErrorDocsConfig } from "../errors/docs-url.ts";
|
|
5
6
|
import type { Lifecycle } from "../lifecycle/index.ts";
|
|
6
7
|
import type { ObservabilityProvider } from "../observability/index.ts";
|
package/dist/api/sse-route.d.ts
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
|
+
import type { AccessRule } from "@cosmicdrift/kumiko-types/handlers";
|
|
2
|
+
import type { OwnershipMap } from "@cosmicdrift/kumiko-types/ownership";
|
|
1
3
|
import { Hono } from "hono";
|
|
2
|
-
import type { AccessRule, OwnershipMap } from "../engine/types/index.ts";
|
|
3
4
|
import { type SseBroker } from "./sse-broker.ts";
|
|
4
5
|
/**
|
|
5
6
|
* Heartbeat cadence for SSE streams.
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { runInRowLevelSecurityScope, tenantRowLevelSecurityScope, } from "../db/row-level-security-scope.js";
|
|
2
|
+
// Signature routes run before any tenant scope exists, and plugin code parses unauthenticated bytes,
|
|
3
|
+
// so only the secret accesses themselves open a scope, and only for the tenant the call names.
|
|
4
|
+
export function tenantScopedSecrets(secrets) {
|
|
5
|
+
const scoped = (tenantId, run) => runInRowLevelSecurityScope(tenantRowLevelSecurityScope(tenantId), run);
|
|
6
|
+
return {
|
|
7
|
+
withRunner: (runner) => tenantScopedSecrets(secrets.withRunner(runner)),
|
|
8
|
+
get: (tenantId, ...rest) => scoped(tenantId, () => secrets.get(tenantId, ...rest)),
|
|
9
|
+
has: (tenantId, ...rest) => scoped(tenantId, () => secrets.has(tenantId, ...rest)),
|
|
10
|
+
set: (tenantId, ...rest) => scoped(tenantId, () => secrets.set(tenantId, ...rest)),
|
|
11
|
+
delete: (tenantId, ...rest) => scoped(tenantId, () => secrets.delete(tenantId, ...rest)),
|
|
12
|
+
};
|
|
13
|
+
}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { WEBSOCKET_BACKPRESSURE_LIMIT_BYTES, WEBSOCKET_DEFAULT_MAX_CONNECTIONS_PER_USER, WEBSOCKET_DEFAULT_MAX_MESSAGE_BYTES, WEBSOCKET_MAX_PAYLOAD_BYTES, WEBSOCKET_ROUTE_PATH_PREFIX, type WebSocketMessageData, type WebSocketSessionHandlers } from "@cosmicdrift/kumiko-types/websocket-route";
|
|
2
2
|
import type { SessionUser } from "../engine/types/index.ts";
|
|
3
3
|
import { type AuthSessionChecker, type TenantLifecycleStatusResolver } from "./auth-middleware.ts";
|
|
4
|
-
import {
|
|
4
|
+
import type { RequestContextData } from "./request-context-internals.ts";
|
|
5
5
|
export { WEBSOCKET_BACKPRESSURE_LIMIT_BYTES, WEBSOCKET_DEFAULT_MAX_CONNECTIONS_PER_USER, WEBSOCKET_DEFAULT_MAX_MESSAGE_BYTES, WEBSOCKET_MAX_PAYLOAD_BYTES, WEBSOCKET_ROUTE_PATH_PREFIX, };
|
|
6
6
|
export declare const WEBSOCKET_HEARTBEAT_INTERVAL_MS = 25000;
|
|
7
7
|
export declare const WEBSOCKET_PENDING_BUFFER_LIMIT_BYTES: number;
|
package/dist/auth/index.d.ts
CHANGED
package/dist/auth/roles.d.ts
CHANGED
|
@@ -9,8 +9,3 @@ export declare const ROLES: {
|
|
|
9
9
|
readonly SystemAdmin: "SystemAdmin";
|
|
10
10
|
readonly Member: "Member";
|
|
11
11
|
};
|
|
12
|
-
/**
|
|
13
|
-
* Union of all known role names for compile-time checks of
|
|
14
|
-
* handler access rules and ownership maps.
|
|
15
|
-
*/
|
|
16
|
-
export type Role = (typeof ROLES)[keyof typeof ROLES];
|
|
@@ -3,6 +3,5 @@ import type { DurationSpec, RetentionSpec } from "./profiles.ts";
|
|
|
3
3
|
type Instant = InstanceType<ReturnType<typeof getTemporal>["Instant"]>;
|
|
4
4
|
export declare function durationSpecToMs(spec: DurationSpec): number;
|
|
5
5
|
export declare function addDurationSpec(now: Instant, spec: DurationSpec): Instant;
|
|
6
|
-
export declare function describeDurationSpec(spec: DurationSpec): string;
|
|
7
6
|
export declare function subtractRetentionSpec(now: Instant, spec: RetentionSpec): Instant;
|
|
8
7
|
export {};
|
|
@@ -28,11 +28,6 @@ export function addDurationSpec(now, spec) {
|
|
|
28
28
|
}
|
|
29
29
|
// Human-readable descriptions for logs and error messages. Not localized;
|
|
30
30
|
// operator output is English-only.
|
|
31
|
-
export function describeDurationSpec(spec) {
|
|
32
|
-
if ("days" in spec)
|
|
33
|
-
return `${spec.days} day${spec.days === 1 ? "" : "s"}`;
|
|
34
|
-
return `${spec.hours} hour${spec.hours === 1 ? "" : "s"}`;
|
|
35
|
-
}
|
|
36
31
|
// Calendar-aware cutoff: months/years are subtracted on a UTC calendar so
|
|
37
32
|
// "24 months" is not approximated as 730 fixed days (leap years, month ends).
|
|
38
33
|
export function subtractRetentionSpec(now, spec) {
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
export { addDurationSpec,
|
|
1
|
+
export { addDurationSpec, subtractRetentionSpec, } from "./duration-spec.ts";
|
|
2
2
|
export { complianceProfileOverrideSchema } from "./override-schema.ts";
|
|
3
|
-
export type {
|
|
4
|
-
export { COMPLIANCE_PROFILES,
|
|
5
|
-
export type {
|
|
3
|
+
export type { ComplianceProfile, ComplianceProfileKey, ComplianceProfileOverride, DurationSpec, EffectiveComplianceProfile, } from "./profiles.ts";
|
|
4
|
+
export { COMPLIANCE_PROFILES, resolveComplianceProfile, SELECTABLE_PROFILE_KEYS, } from "./profiles.ts";
|
|
5
|
+
export type { SubProcessor } from "./sub-processors.ts";
|
|
6
6
|
export { getActiveSubProcessors, getPlannedSubProcessors, KUMIKO_SUB_PROCESSORS, } from "./sub-processors.ts";
|
package/dist/compliance/index.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
// `@cosmicdrift/kumiko-framework/compliance` — Data protection and compliance foundation.
|
|
2
2
|
// Used by compliance-profiles, data-retention, user-data-rights, and related features.
|
|
3
|
-
export { addDurationSpec,
|
|
3
|
+
export { addDurationSpec, subtractRetentionSpec, } from "./duration-spec.js";
|
|
4
4
|
export { complianceProfileOverrideSchema } from "./override-schema.js";
|
|
5
|
-
export { COMPLIANCE_PROFILES,
|
|
5
|
+
export { COMPLIANCE_PROFILES, resolveComplianceProfile, SELECTABLE_PROFILE_KEYS, } from "./profiles.js";
|
|
6
6
|
export { getActiveSubProcessors, getPlannedSubProcessors, KUMIKO_SUB_PROCESSORS, } from "./sub-processors.js";
|
|
@@ -70,21 +70,6 @@ export interface ComplianceProfile {
|
|
|
70
70
|
* tenants must select an actual profile.
|
|
71
71
|
*/
|
|
72
72
|
export declare const SELECTABLE_PROFILE_KEYS: readonly ["eu-dsgvo", "swiss-dsg", "de-hr-dsgvo-hgb"];
|
|
73
|
-
/**
|
|
74
|
-
* Top-level `ComplianceProfile` properties that a tenant override may modify.
|
|
75
|
-
* Identity fields (key, region, label, extends) are excluded because
|
|
76
|
-
* overriding them would destroy the profile's identity.
|
|
77
|
-
*
|
|
78
|
-
* This is the single source of truth for:
|
|
79
|
-
* - the set-profile handler whitelist, which rejects typos
|
|
80
|
-
* - the snapshot test that guards against drift from the profile's top level
|
|
81
|
-
*
|
|
82
|
-
* When a new top-level property is added to `ComplianceProfile` (for example,
|
|
83
|
-
* `dataSubjectRights` or `crossBorderTransferRules`), it must be added here;
|
|
84
|
-
* otherwise set-profile rejects valid overrides. The snapshot test in
|
|
85
|
-
* profiles.test.ts detects drift in either direction.
|
|
86
|
-
*/
|
|
87
|
-
export declare const OVERRIDABLE_PROFILE_KEYS: ReadonlySet<string>;
|
|
88
73
|
type DeepReadonly<T> = T extends object ? {
|
|
89
74
|
readonly [K in keyof T]: DeepReadonly<T[K]>;
|
|
90
75
|
} : T;
|
|
@@ -164,29 +164,6 @@ export const SELECTABLE_PROFILE_KEYS = [
|
|
|
164
164
|
"swiss-dsg",
|
|
165
165
|
"de-hr-dsgvo-hgb",
|
|
166
166
|
];
|
|
167
|
-
/**
|
|
168
|
-
* Top-level `ComplianceProfile` properties that a tenant override may modify.
|
|
169
|
-
* Identity fields (key, region, label, extends) are excluded because
|
|
170
|
-
* overriding them would destroy the profile's identity.
|
|
171
|
-
*
|
|
172
|
-
* This is the single source of truth for:
|
|
173
|
-
* - the set-profile handler whitelist, which rejects typos
|
|
174
|
-
* - the snapshot test that guards against drift from the profile's top level
|
|
175
|
-
*
|
|
176
|
-
* When a new top-level property is added to `ComplianceProfile` (for example,
|
|
177
|
-
* `dataSubjectRights` or `crossBorderTransferRules`), it must be added here;
|
|
178
|
-
* otherwise set-profile rejects valid overrides. The snapshot test in
|
|
179
|
-
* profiles.test.ts detects drift in either direction.
|
|
180
|
-
*/
|
|
181
|
-
export const OVERRIDABLE_PROFILE_KEYS = new Set([
|
|
182
|
-
"userRights",
|
|
183
|
-
"notifications",
|
|
184
|
-
"breach",
|
|
185
|
-
"auditLog",
|
|
186
|
-
"subProcessor",
|
|
187
|
-
"tenantDestroyGracePeriod",
|
|
188
|
-
"forgetDiscovery",
|
|
189
|
-
]);
|
|
190
167
|
// These paths are replaced as atomic values rather than merged recursively.
|
|
191
168
|
// This is required for discriminated unions, where a patch may provide a
|
|
192
169
|
// sibling property instead of an override; for example, changing retention
|
package/dist/config/index.d.ts
CHANGED
|
@@ -1,5 +1,8 @@
|
|
|
1
|
+
import type { BundledListsOptions } from "@cosmicdrift/kumiko-types/screen";
|
|
2
|
+
import { type RowLevelSecurityMode } from "../db/render-rls-ddl.ts";
|
|
1
3
|
import type { ValidateBootOptions } from "../engine/boot-validator.ts";
|
|
2
|
-
import type {
|
|
4
|
+
import type { FeatureDefinition } from "../engine/types/index.ts";
|
|
5
|
+
import type { AppClientConfig, AppPortEntry } from "./internals.ts";
|
|
3
6
|
export type AppInfraPorts = {
|
|
4
7
|
readonly postgres?: number;
|
|
5
8
|
readonly redis?: number;
|
|
@@ -16,10 +19,6 @@ export type AppPorts = {
|
|
|
16
19
|
* of several apps never share a Meilisearch or Postgres. */
|
|
17
20
|
readonly infra?: AppInfraPorts;
|
|
18
21
|
};
|
|
19
|
-
export type AppClientConfig = {
|
|
20
|
-
/** Client bundle entry files, relative to the app root (e.g. "src/client.tsx"). */
|
|
21
|
-
readonly entries: readonly string[];
|
|
22
|
-
};
|
|
23
22
|
/** The boot-validator options an app owns; `env` and the cipher are injected by the runners. */
|
|
24
23
|
export type AppValidateBootOptions = Pick<ValidateBootOptions, "navAllowlist" | "navAllowlistExempt" | "requiredLocales" | "warnOnUniqueAccessRoles">;
|
|
25
24
|
export type AppConfig = {
|
|
@@ -37,19 +36,20 @@ export type AppConfig = {
|
|
|
37
36
|
readonly validateBootOptions?: AppValidateBootOptions;
|
|
38
37
|
/** One table block for every list of the bundled features. kumiko/schema.ts passes it to composeFeatures; the app's bin files pass it to the runners, like validateBootOptions. */
|
|
39
38
|
readonly bundledLists?: BundledListsOptions;
|
|
39
|
+
/** "on" enforces tenant isolation in Postgres via row level security; schema tooling and every runner read this one value. Default "on". */
|
|
40
|
+
readonly rowLevelSecurity?: RowLevelSecurityMode;
|
|
40
41
|
};
|
|
41
42
|
export declare const APP_CONFIG_FILE = "kumiko.config.ts";
|
|
42
43
|
declare const INFRA_PORT_NAMES: readonly ["postgres", "redis", "meilisearch", "s3"];
|
|
43
44
|
export type AppPortRole = "dev" | "e2e" | (typeof INFRA_PORT_NAMES)[number];
|
|
44
|
-
export type AppPortEntry = {
|
|
45
|
-
readonly role: AppPortRole;
|
|
46
|
-
readonly port: number;
|
|
47
|
-
};
|
|
48
45
|
/** Every port the app claims, in a stable order. */
|
|
49
46
|
export declare function listAppPorts(ports: AppPorts): readonly AppPortEntry[];
|
|
50
47
|
/** Problems with the declared ports: out of range or claimed twice by this app. */
|
|
51
48
|
export declare function findAppPortProblems(ports: AppPorts): readonly string[];
|
|
52
49
|
export declare function defineAppConfig(config: AppConfig): AppConfig;
|
|
53
|
-
/**
|
|
50
|
+
/**
|
|
51
|
+
* Raw `features` plus `prodFeatures`, without the bundled foundation: the runners compose it,
|
|
52
|
+
* tooling such as `runSchemaCli` takes `FEATURES` from `kumiko/schema`.
|
|
53
|
+
*/
|
|
54
54
|
export declare function allAppFeatures(config: Pick<AppConfig, "features" | "prodFeatures">): readonly FeatureDefinition[];
|
|
55
55
|
export {};
|
package/dist/config/index.js
CHANGED
|
@@ -1,3 +1,8 @@
|
|
|
1
|
+
// The app's single config file (kumiko.config.ts). Type-only imports keep it
|
|
2
|
+
// loadable by tooling (kumiko check, agent lint, port registry) without
|
|
3
|
+
// pulling the engine runtime.
|
|
4
|
+
import { isOneOf } from "@cosmicdrift/kumiko-types/type-guards";
|
|
5
|
+
import { ROW_LEVEL_SECURITY_MODES } from "../db/render-rls-ddl.js";
|
|
1
6
|
export const APP_CONFIG_FILE = "kumiko.config.ts";
|
|
2
7
|
const INFRA_PORT_NAMES = [
|
|
3
8
|
"postgres",
|
|
@@ -50,12 +55,19 @@ export function defineAppConfig(config) {
|
|
|
50
55
|
problems.push(`client.entries: "${entry}" must be a relative .ts/.tsx path inside the app`);
|
|
51
56
|
}
|
|
52
57
|
}
|
|
58
|
+
if (config.rowLevelSecurity !== undefined &&
|
|
59
|
+
!isOneOf(ROW_LEVEL_SECURITY_MODES, config.rowLevelSecurity)) {
|
|
60
|
+
problems.push(`rowLevelSecurity must be one of ${ROW_LEVEL_SECURITY_MODES.join(", ")}, got ${String(config.rowLevelSecurity)}`);
|
|
61
|
+
}
|
|
53
62
|
if (problems.length > 0) {
|
|
54
63
|
throw new Error(`defineAppConfig: ${problems.join("; ")}`);
|
|
55
64
|
}
|
|
56
65
|
return config;
|
|
57
66
|
}
|
|
58
|
-
/**
|
|
67
|
+
/**
|
|
68
|
+
* Raw `features` plus `prodFeatures`, without the bundled foundation: the runners compose it,
|
|
69
|
+
* tooling such as `runSchemaCli` takes `FEATURES` from `kumiko/schema`.
|
|
70
|
+
*/
|
|
59
71
|
export function allAppFeatures(config) {
|
|
60
72
|
return [...config.features, ...(config.prodFeatures ?? [])];
|
|
61
73
|
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import type { AppPortRole } from "./index.ts";
|
|
2
|
+
export type AppClientConfig = {
|
|
3
|
+
/** Client bundle entry files, relative to the app root (e.g. "src/client.tsx"). */
|
|
4
|
+
readonly entries: readonly string[];
|
|
5
|
+
};
|
|
6
|
+
export type AppPortEntry = {
|
|
7
|
+
readonly role: AppPortRole;
|
|
8
|
+
readonly port: number;
|
|
9
|
+
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
package/dist/consumer-cli.d.ts
CHANGED
|
@@ -1,5 +1,2 @@
|
|
|
1
|
-
|
|
2
|
-
readonly log: (line: string) => void;
|
|
3
|
-
readonly err: (line: string) => void;
|
|
4
|
-
};
|
|
1
|
+
import type { ConsumerCliOut } from "./consumer-cli-internals.ts";
|
|
5
2
|
export declare function runConsumerCli(argv: readonly string[], out: ConsumerCliOut): Promise<number>;
|
package/dist/consumer-cli.js
CHANGED
|
@@ -79,7 +79,11 @@ export async function runConsumerCli(argv, out) {
|
|
|
79
79
|
out.err(" DATABASE_URL not set.");
|
|
80
80
|
return 1;
|
|
81
81
|
}
|
|
82
|
-
const { db, close } = createDbConnection({
|
|
82
|
+
const { db, close } = createDbConnection({
|
|
83
|
+
url: dbUrl,
|
|
84
|
+
rowLevelSecurity: "off", // consumer state tables carry no tenant_id
|
|
85
|
+
...dbConnectionOptionsFromEnv(),
|
|
86
|
+
});
|
|
83
87
|
try {
|
|
84
88
|
if (sub === "status") {
|
|
85
89
|
const state = await getConsumerState(db, name, instanceId);
|
package/dist/crypto/event-pii.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
// PII on custom-event payloads. Entity CRUD events get their PII
|
|
2
|
-
// encrypted by the executor; events written via ctx.
|
|
2
|
+
// encrypted by the executor; events written via ctx.events.append / MSP-apply /
|
|
3
3
|
// low-level append() (delivery attempt-log, jobs run-logger) had no encrypt
|
|
4
4
|
// path at all. `r.defineEvent(name, schema, { piiFields })` declares which
|
|
5
5
|
// payload fields are PII and which payload field names the owning user;
|
package/dist/crypto/index.d.ts
CHANGED
|
@@ -1,11 +1,10 @@
|
|
|
1
|
-
export {
|
|
2
|
-
export { configuredEventPiiCatalog
|
|
1
|
+
export { collectLookupableFields, computeBlindIndex, configureBlindIndexKey, configuredBlindIndexKey, decodeBlindIndexKey, } from "./blind-index.ts";
|
|
2
|
+
export { configuredEventPiiCatalog } from "./event-pii.ts";
|
|
3
3
|
export { InMemoryKmsAdapter } from "./in-memory-kms-adapter.ts";
|
|
4
4
|
export { isSelfPiiField } from "./is-self-pii-field.ts";
|
|
5
|
-
export {
|
|
6
|
-
export {
|
|
7
|
-
export { type
|
|
8
|
-
export { createPgKmsAdapter,
|
|
9
|
-
export { configuredPiiSubjectKms, configurePiiSubjectKms, decryptPiiFieldValues, decryptPiiValueForSubject,
|
|
10
|
-
export {
|
|
11
|
-
export { collectPiiEncryptedFields, collectPiiSubjectFields, collectSearchableSubjectFields, isRecordKeyedField, type ResolveSubjectOptions, resolveSubjectForField, SubjectResolutionError, } from "./subject-resolver.ts";
|
|
5
|
+
export { resolvePlatformKeks } from "./kek-source.ts";
|
|
6
|
+
export { KeyAlreadyExistsError, KeyErasedError, type KmsAdapter, type KmsContext, type LocalKeyKmsAdapter, type SubjectId, subjectIdSchema, subjectIdToKey, subjectKeyForRecord, subjectKeyForUser, } from "./kms-adapter.ts";
|
|
7
|
+
export { type KmsWiring, requireKmsWiring, requireKmsWiringAsync, resolveKmsWiring, resolveKmsWiringAsync, } from "./kms-wiring.ts";
|
|
8
|
+
export { createPgKmsAdapter, rewrapSubjectKeys, } from "./pg-kms-adapter.ts";
|
|
9
|
+
export { configuredPiiSubjectKms, configurePiiSubjectKms, decryptPiiFieldValues, decryptPiiValueForSubject, encryptPiiFieldValues, encryptPiiJsonValueForSubject, encryptPiiValueForSubject, isPiiCiphertext, PII_CIPHERTEXT_PREFIX, PII_ERASED_SENTINEL, } from "./pii-field-encryption.ts";
|
|
10
|
+
export { collectPiiEncryptedFields, collectPiiSubjectFields, isRecordKeyedField, resolveSubjectForField, SubjectResolutionError, } from "./subject-resolver.ts";
|
package/dist/crypto/index.js
CHANGED
|
@@ -1,11 +1,10 @@
|
|
|
1
|
-
export {
|
|
2
|
-
export { configuredEventPiiCatalog
|
|
1
|
+
export { collectLookupableFields, computeBlindIndex, configureBlindIndexKey, configuredBlindIndexKey, decodeBlindIndexKey, } from "./blind-index.js";
|
|
2
|
+
export { configuredEventPiiCatalog } from "./event-pii.js";
|
|
3
3
|
export { InMemoryKmsAdapter } from "./in-memory-kms-adapter.js";
|
|
4
4
|
export { isSelfPiiField } from "./is-self-pii-field.js";
|
|
5
5
|
export { resolvePlatformKeks } from "./kek-source.js";
|
|
6
|
-
export {
|
|
7
|
-
export {
|
|
8
|
-
export { createPgKmsAdapter,
|
|
9
|
-
export { configuredPiiSubjectKms, configurePiiSubjectKms, decryptPiiFieldValues, decryptPiiValueForSubject, encryptPiiFieldValues, encryptPiiJsonValueForSubject, encryptPiiValueForSubject, isPiiCiphertext, PII_CIPHERTEXT_PREFIX,
|
|
10
|
-
export {
|
|
11
|
-
export { collectPiiEncryptedFields, collectPiiSubjectFields, collectSearchableSubjectFields, isRecordKeyedField, resolveSubjectForField, SubjectResolutionError, } from "./subject-resolver.js";
|
|
6
|
+
export { KeyAlreadyExistsError, KeyErasedError, subjectIdSchema, subjectIdToKey, subjectKeyForRecord, subjectKeyForUser, } from "./kms-adapter.js";
|
|
7
|
+
export { requireKmsWiring, requireKmsWiringAsync, resolveKmsWiring, resolveKmsWiringAsync, } from "./kms-wiring.js";
|
|
8
|
+
export { createPgKmsAdapter, rewrapSubjectKeys, } from "./pg-kms-adapter.js";
|
|
9
|
+
export { configuredPiiSubjectKms, configurePiiSubjectKms, decryptPiiFieldValues, decryptPiiValueForSubject, encryptPiiFieldValues, encryptPiiJsonValueForSubject, encryptPiiValueForSubject, isPiiCiphertext, PII_CIPHERTEXT_PREFIX, PII_ERASED_SENTINEL, } from "./pii-field-encryption.js";
|
|
10
|
+
export { collectPiiEncryptedFields, collectPiiSubjectFields, isRecordKeyedField, resolveSubjectForField, SubjectResolutionError, } from "./subject-resolver.js";
|
|
@@ -57,6 +57,7 @@ export class PgKmsAdapter {
|
|
|
57
57
|
this.connection = createDbConnection({
|
|
58
58
|
url: options.databaseUrl,
|
|
59
59
|
maxConnections: options.maxConnections ?? 4,
|
|
60
|
+
rowLevelSecurity: "off", // key tables carry no tenant_id
|
|
60
61
|
});
|
|
61
62
|
this.sql = this.connection.client;
|
|
62
63
|
}
|
|
@@ -171,7 +172,11 @@ export async function rewrapSubjectKeys(options) {
|
|
|
171
172
|
fromKeks.set(Number(version), decodePlatformKek(kek));
|
|
172
173
|
}
|
|
173
174
|
const batchSize = options.batchSize ?? 200;
|
|
174
|
-
const connection = createDbConnection({
|
|
175
|
+
const connection = createDbConnection({
|
|
176
|
+
url: options.databaseUrl,
|
|
177
|
+
maxConnections: 2,
|
|
178
|
+
rowLevelSecurity: "off", // key tables carry no tenant_id
|
|
179
|
+
});
|
|
175
180
|
const sql = connection.client;
|
|
176
181
|
const failures = [];
|
|
177
182
|
const result = { scanned: 0, rewrapped: 0, skippedErased: 0, failures };
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
+
import type { EntityDefinition } from "@cosmicdrift/kumiko-types/fields";
|
|
1
2
|
import type { ExecutorManagedRunner } from "@cosmicdrift/kumiko-types/executor-brand";
|
|
2
|
-
import type { EntityDefinition } from "../engine/types/index.ts";
|
|
3
3
|
import type { StoredEvent } from "../event-store/index.ts";
|
|
4
4
|
import type { DbRow } from "./connection.ts";
|
|
5
5
|
import type { TableColumns } from "./dialect.ts";
|
|
@@ -1,49 +1,3 @@
|
|
|
1
|
-
// applyEntityEvent — the ONLY write logic for r.entity tables from
|
|
2
|
-
// StoredEvents. Both callers use it:
|
|
3
|
-
//
|
|
4
|
-
// - createEventStoreExecutor (live, in the write TX) passes the just-appended
|
|
5
|
-
// StoredEvent directly; sensitive fields are table ciphertext in the payload
|
|
6
|
-
// (validated at boot as pii/encrypted).
|
|
7
|
-
// - rebuildProjection via ImplicitProjection (replay, in the rebuild TX)
|
|
8
|
-
// passes the same StoredEvent; apply copies ciphertext byte-for-byte,
|
|
9
|
-
// while bidx is recalculated below.
|
|
10
|
-
//
|
|
11
|
-
// Live==Rebuild equivalence therefore holds by construction for ALL fields —
|
|
12
|
-
// changed write logic needs to be maintained in only ONE place, with no sync
|
|
13
|
-
// contract. The only legitimate divergence is crypto-shredding
|
|
14
|
-
// (DEK erased → value unreadable, bidx NULL). Load-bearing test:
|
|
15
|
-
// db/__tests__/implicit-projection-equivalence.integration.test.ts.
|
|
16
|
-
//
|
|
17
|
-
// Tenant isolation: applyEntityEvent expects an ExecutorManagedRunner (tx or pool), NOT
|
|
18
|
-
// a TenantDb wrapper. Two sources keep it safe:
|
|
19
|
-
// 1. The live path reads the target row through the tenant-scoped TenantDb
|
|
20
|
-
// before writing — loadById() for update/delete/forget, db.fetchOne() for
|
|
21
|
-
// restore — so the aggregateId is already tenant-validated on arrival.
|
|
22
|
-
// 2. create sets tenantId explicitly from event.tenantId, never derived from
|
|
23
|
-
// the TenantDb wrapper default.
|
|
24
|
-
// The missing TenantDb wrapper in this function is therefore not a hole.
|
|
25
|
-
//
|
|
26
|
-
// Auto-verbs:
|
|
27
|
-
// <entity>.created → INSERT
|
|
28
|
-
// <entity>.updated → UPDATE WHERE id=aggregateId
|
|
29
|
-
// <entity>.deleted → soft-delete-UPDATE if entity.softDelete, otherwise hard-DELETE
|
|
30
|
-
// <entity>.restored → undelete-UPDATE (meaningful only for softDelete)
|
|
31
|
-
// <entity>.forgotten → always hard-DELETE (Art.17 purge, including softDelete);
|
|
32
|
-
// via executor.forget(). Rebuild replays created→forgotten
|
|
33
|
-
// → the row is gone, making this rebuild-safe (unlike a
|
|
34
|
-
// direct deleteMany).
|
|
35
|
-
//
|
|
36
|
-
// Domain events (r.defineEvent) on the same aggregate are NOT handled here —
|
|
37
|
-
// they never went through the Executor in the live path and must be handled by
|
|
38
|
-
// explicit r.projection-apply handlers or r.multiStreamProjection.
|
|
39
|
-
// ImplicitProjection registers the auto-verbs.
|
|
40
|
-
//
|
|
41
|
-
// Return shape: ApplyResult with `kind` and an optional `row`.
|
|
42
|
-
// - "applied" → the write completed. `row` contains the written row for
|
|
43
|
-
// create/update/soft-delete/restore. For hard-delete, `row` is null
|
|
44
|
-
// (DELETE statements do not provide a returning row).
|
|
45
|
-
// - "skipped" → the event is not an auto-verb (a domain event on the same
|
|
46
|
-
// aggregate). Caller no-op.
|
|
47
1
|
import { isOneOf } from "@cosmicdrift/kumiko-types/type-guards";
|
|
48
2
|
import { requestContext } from "../api/request-context.js";
|
|
49
3
|
import { collectLookupableFields, computeBlindIndexValues } from "../crypto/blind-index.js";
|
|
@@ -51,6 +5,8 @@ import { configuredPiiSubjectKms, decryptPiiFieldValues, isPiiCiphertext, PII_ER
|
|
|
51
5
|
import { collectPiiFileReferenceFields } from "../crypto/subject-resolver.js";
|
|
52
6
|
import { deleteMany, insertOne, updateMany } from "../db/query.js";
|
|
53
7
|
import { InternalError } from "../errors/index.js";
|
|
8
|
+
import { activeRowLevelSecurityScope, runInSystemRowLevelSecurityScope, } from "./row-level-security-scope.js";
|
|
9
|
+
import { asEntityTableMeta } from "./table-introspection.js";
|
|
54
10
|
const AUTO_VERBS = ["created", "updated", "deleted", "restored", "forgotten"];
|
|
55
11
|
/** Parses event.type into an AutoVerb when the event is an auto-verb
|
|
56
12
|
* for the given aggregate; otherwise returns null (a domain event). */
|
|
@@ -85,7 +41,19 @@ async function decryptFileReferenceCiphertext(entity, values) {
|
|
|
85
41
|
/** Applies an auto-event idempotently to the entity table.
|
|
86
42
|
* Called both during live append (inside the write TX) and during rebuild
|
|
87
43
|
* (inside the rebuild TX), using identical logic. */
|
|
88
|
-
|
|
44
|
+
// An ambient tenant scope stays, so a live write cannot land a row in another tenant (row-level security
|
|
45
|
+
// rejects it). Replay, rebuild and boot seeds run without a tenant scope and global tables live on the system
|
|
46
|
+
// tenant, so only those write system scoped.
|
|
47
|
+
export function applyEntityEvent(event, table, entity, tx) {
|
|
48
|
+
if (keepsAmbientTenantScope(table))
|
|
49
|
+
return applyEntityEventInScope(event, table, entity, tx);
|
|
50
|
+
return runInSystemRowLevelSecurityScope("replay, rebuild and global-table projection writes carry no tenant scope of their own", () => applyEntityEventInScope(event, table, entity, tx));
|
|
51
|
+
}
|
|
52
|
+
function keepsAmbientTenantScope(table) {
|
|
53
|
+
return (activeRowLevelSecurityScope()?.kind === "tenant" &&
|
|
54
|
+
asEntityTableMeta(table)?.tenancy !== "global");
|
|
55
|
+
}
|
|
56
|
+
async function applyEntityEventInScope(event, table, entity, tx) {
|
|
89
57
|
const verb = parseAutoVerb(event);
|
|
90
58
|
if (verb === null)
|
|
91
59
|
return { kind: "skipped" };
|