@k2b/cloud 0.6.0-rc.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/README.md +98 -0
- package/package.json +128 -0
- package/public/logo.svg +1 -0
- package/scripts/app-favicon.test.ts +49 -0
- package/scripts/app-favicon.ts +51 -0
- package/scripts/build.ts +205 -0
- package/scripts/preload.ts +164 -0
- package/scripts/sync-recovery-smoke.ts +200 -0
- package/src/_internal/app-favicon.ts +2 -0
- package/src/_internal/app-presentation.ts +61 -0
- package/src/_internal/app-workspace-state.ts +24 -0
- package/src/_internal/bounded-json.ts +47 -0
- package/src/_internal/build-metadata.ts +9 -0
- package/src/_internal/capabilities.ts +1118 -0
- package/src/_internal/define-app.ts +801 -0
- package/src/_internal/heartbeat.ts +167 -0
- package/src/_internal/help-catalog.ts +241 -0
- package/src/_internal/help.ts +95 -0
- package/src/_internal/nats-connection.ts +34 -0
- package/src/_internal/page-responses.ts +40 -0
- package/src/_internal/process-sync.ts +117 -0
- package/src/_internal/readiness.ts +3 -0
- package/src/_internal/registry-validation.ts +136 -0
- package/src/_internal/registry-watch.ts +52 -0
- package/src/_internal/registry.ts +338 -0
- package/src/_internal/runtime-compatibility.ts +64 -0
- package/src/_internal/runtime-context.ts +84 -0
- package/src/_internal/runtime-watcher.ts +78 -0
- package/src/_internal/static-assets.ts +86 -0
- package/src/_internal/status-preserving-ssr.ts +49 -0
- package/src/access/PermissionEditor.tsx +486 -0
- package/src/access/ResourceApiKeys.tsx +271 -0
- package/src/access/messages.ts +121 -0
- package/src/access/ui.ts +16 -0
- package/src/account/Avatar.tsx +28 -0
- package/src/account/EntitySearch.tsx +363 -0
- package/src/account/avatar-upload-dialog.tsx +197 -0
- package/src/account/avatar-upload.ts +149 -0
- package/src/account/ui.ts +3 -0
- package/src/ai/admin.ts +47 -0
- package/src/ai/approval-routes.ts +130 -0
- package/src/ai/approvals.ts +139 -0
- package/src/ai/assistant-models.ts +61 -0
- package/src/ai/attachments.ts +40 -0
- package/src/ai/browser.ts +92 -0
- package/src/ai/capabilities.ts +714 -0
- package/src/ai/capability-execution.ts +151 -0
- package/src/ai/chat/blocks.render.test.tsx +1108 -0
- package/src/ai/chat/blocks.tsx +730 -0
- package/src/ai/chat/builtin-tools.tsx +428 -0
- package/src/ai/chat/capability-table.tsx +87 -0
- package/src/ai/chat/composer-adapter.ts +169 -0
- package/src/ai/chat/file-tools.tsx +81 -0
- package/src/ai/chat/message-actions.tsx +370 -0
- package/src/ai/chat/message-utils.ts +479 -0
- package/src/ai/chat/messages.ts +43 -0
- package/src/ai/chat/presentation.tsx +395 -0
- package/src/ai/chat/primitives.tsx +3 -0
- package/src/ai/chat/tool-disclosure.tsx +41 -0
- package/src/ai/chat/turn-navigator-utils.ts +28 -0
- package/src/ai/chat/turn-navigator.tsx +164 -0
- package/src/ai/chat/user-message.tsx +149 -0
- package/src/ai/chat/visual-tools.tsx +435 -0
- package/src/ai/chat/web-tools.tsx +202 -0
- package/src/ai/chat-task-contracts.ts +113 -0
- package/src/ai/chat-tasks.ts +952 -0
- package/src/ai/client/controller.ts +1211 -0
- package/src/ai/client/file-source.ts +95 -0
- package/src/ai/client/live-connection.ts +140 -0
- package/src/ai/client/projection.ts +178 -0
- package/src/ai/client/transport.ts +111 -0
- package/src/ai/compaction.ts +182 -0
- package/src/ai/credentials.ts +124 -0
- package/src/ai/default-tool-contracts.ts +108 -0
- package/src/ai/default-tools.ts +127 -0
- package/src/ai/enrich.ts +280 -0
- package/src/ai/executor.ts +1624 -0
- package/src/ai/fetch-file-tool.ts +313 -0
- package/src/ai/file-context.ts +92 -0
- package/src/ai/file-media-type.ts +28 -0
- package/src/ai/file-mount.ts +16 -0
- package/src/ai/file-tools.ts +566 -0
- package/src/ai/files-store.ts +390 -0
- package/src/ai/firecrawl-tools.ts +305 -0
- package/src/ai/grids-skill.ts +126 -0
- package/src/ai/http.ts +265 -0
- package/src/ai/index.ts +337 -0
- package/src/ai/kit-skill.ts +22 -0
- package/src/ai/limits.ts +5 -0
- package/src/ai/live-events.ts +289 -0
- package/src/ai/live-messages.ts +45 -0
- package/src/ai/live-outbox.ts +102 -0
- package/src/ai/live-routes.ts +412 -0
- package/src/ai/live.ts +2 -0
- package/src/ai/maintenance.ts +302 -0
- package/src/ai/markdown-pdf-tool.ts +95 -0
- package/src/ai/memories.ts +605 -0
- package/src/ai/memory-learning-runs.ts +222 -0
- package/src/ai/memory-learning.ts +619 -0
- package/src/ai/memory-tool.ts +120 -0
- package/src/ai/memory-workflow-evidence.ts +158 -0
- package/src/ai/migrate.ts +2082 -0
- package/src/ai/model-access-migrate.ts +30 -0
- package/src/ai/model-access.ts +191 -0
- package/src/ai/personal-agent.ts +6 -0
- package/src/ai/prefs.ts +72 -0
- package/src/ai/project-tool.ts +94 -0
- package/src/ai/projects-routes.ts +277 -0
- package/src/ai/projects.ts +902 -0
- package/src/ai/protocol.ts +279 -0
- package/src/ai/provider.ts +73 -0
- package/src/ai/public-projection.ts +25 -0
- package/src/ai/resource-markers.ts +31 -0
- package/src/ai/resource-refs.ts +70 -0
- package/src/ai/routes.ts +1131 -0
- package/src/ai/runtime-tools.ts +39 -0
- package/src/ai/runtime.ts +544 -0
- package/src/ai/settings.ts +529 -0
- package/src/ai/short-id.ts +45 -0
- package/src/ai/skill-catalog.ts +73 -0
- package/src/ai/skill-format.ts +145 -0
- package/src/ai/skill-seeds.ts +430 -0
- package/src/ai/skill-tool.ts +81 -0
- package/src/ai/skills-routes.ts +143 -0
- package/src/ai/skills.ts +934 -0
- package/src/ai/solid.ts +27 -0
- package/src/ai/store.ts +3113 -0
- package/src/ai/stream.ts +308 -0
- package/src/ai/structured-runs.ts +66 -0
- package/src/ai/structured.ts +186 -0
- package/src/ai/system-prompt.ts +170 -0
- package/src/ai/task-prompt.ts +22 -0
- package/src/ai/timeline.ts +148 -0
- package/src/ai/tool-audit.ts +177 -0
- package/src/ai/tool-result-budget.ts +16 -0
- package/src/ai/tools.ts +155 -0
- package/src/ai/types.ts +967 -0
- package/src/ai/ui.tsx +39 -0
- package/src/ai/usage-migrate.ts +81 -0
- package/src/ai/usage.ts +315 -0
- package/src/ai/validate.ts +54 -0
- package/src/ai/vision-tool.ts +79 -0
- package/src/api/accounts-entities.ts +174 -0
- package/src/api/admin-ai-projects.ts +74 -0
- package/src/api/admin-ai-skills.ts +76 -0
- package/src/api/admin-ai-usage.ts +42 -0
- package/src/api/admin-core-settings.ts +508 -0
- package/src/api/admin-identity.ts +148 -0
- package/src/api/admin-lifecycle.ts +206 -0
- package/src/api/admin-linux-identities.ts +66 -0
- package/src/api/announcements.ts +131 -0
- package/src/api/app-approval.ts +129 -0
- package/src/api/apps.ts +51 -0
- package/src/api/auth/schemas.ts +54 -0
- package/src/api/auth.ts +370 -0
- package/src/api/capabilities.ts +658 -0
- package/src/api/help-messages.ts +19 -0
- package/src/api/help.ts +78 -0
- package/src/api/index.ts +108 -0
- package/src/api/mcp.ts +744 -0
- package/src/api/me-rail.ts +45 -0
- package/src/api/me.ts +753 -0
- package/src/api/search/schemas.ts +79 -0
- package/src/api/search.bench.ts +185 -0
- package/src/api/search.ts +407 -0
- package/src/api/sync-ops.ts +79 -0
- package/src/api/widgets.ts +143 -0
- package/src/browser/CloudResourceSearch.behavior.test.tsx +74 -0
- package/src/browser/CloudResourceSearch.tsx +791 -0
- package/src/browser/app-approval-vault.ts +305 -0
- package/src/browser/app-approval.ts +234 -0
- package/src/browser/live-websocket.ts +268 -0
- package/src/browser/locale-preference.ts +25 -0
- package/src/browser/notification-target.ts +27 -0
- package/src/browser/notification-timeout.ts +14 -0
- package/src/browser/notifications.ts +181 -0
- package/src/browser/resource-clipboard.ts +70 -0
- package/src/browser/resource-picker.tsx +39 -0
- package/src/browser/resource-search-messages.ts +55 -0
- package/src/browser/resource-search.ts +27 -0
- package/src/capabilities/client.ts +149 -0
- package/src/capabilities/response.ts +39 -0
- package/src/capabilities/server.ts +215 -0
- package/src/capabilities/signals.ts +4 -0
- package/src/capabilities/testing.ts +12 -0
- package/src/capabilities/types.ts +32 -0
- package/src/cli/access.ts +499 -0
- package/src/cli/account.ts +382 -0
- package/src/cli/admin/account-administration.ts +45 -0
- package/src/cli/admin/account-categories.ts +49 -0
- package/src/cli/admin/ai-usage.ts +118 -0
- package/src/cli/admin/app-sign-in.ts +49 -0
- package/src/cli/admin/data.ts +343 -0
- package/src/cli/admin/documentation.ts +34 -0
- package/src/cli/admin/gateway.ts +155 -0
- package/src/cli/admin/index.ts +61 -0
- package/src/cli/admin/instance.ts +250 -0
- package/src/cli/admin/jobs.ts +223 -0
- package/src/cli/admin/legal.ts +122 -0
- package/src/cli/admin/linux.ts +53 -0
- package/src/cli/admin/logs.ts +324 -0
- package/src/cli/admin/metrics.ts +142 -0
- package/src/cli/admin/nats.ts +167 -0
- package/src/cli/admin/notifications.ts +516 -0
- package/src/cli/admin/shared.ts +113 -0
- package/src/cli/admin/sync.ts +188 -0
- package/src/cli/admin/telemetry.ts +314 -0
- package/src/cli/admin/webhooks.ts +222 -0
- package/src/cli/admin/workflows.ts +367 -0
- package/src/cli/apps.ts +40 -0
- package/src/cli/capabilities.ts +239 -0
- package/src/cli/commands.ts +604 -0
- package/src/cli/index.ts +61 -0
- package/src/cli/locale.ts +31 -0
- package/src/cli/output.ts +58 -0
- package/src/clients/core.ts +20 -0
- package/src/config/env.ts +54 -0
- package/src/config/index.ts +6 -0
- package/src/contracts/account-categories.ts +62 -0
- package/src/contracts/announcements.ts +121 -0
- package/src/contracts/app-approval.ts +197 -0
- package/src/contracts/app.ts +162 -0
- package/src/contracts/capabilities.ts +484 -0
- package/src/contracts/index.ts +14 -0
- package/src/contracts/notification-live.ts +66 -0
- package/src/contracts/notification-types.ts +235 -0
- package/src/contracts/posix.ts +69 -0
- package/src/contracts/profile.ts +85 -0
- package/src/contracts/rail-preferences.ts +53 -0
- package/src/contracts/registry.ts +110 -0
- package/src/contracts/resource-clipboard.ts +33 -0
- package/src/contracts/settings-types.ts +98 -0
- package/src/contracts/shared.ts +408 -0
- package/src/contracts/user-notifications.ts +101 -0
- package/src/contracts/widgets.ts +183 -0
- package/src/desktop/index.ts +704 -0
- package/src/desktop/solid.tsx +938 -0
- package/src/index.ts +58 -0
- package/src/server/actor.ts +41 -0
- package/src/server/api/index.ts +2 -0
- package/src/server/api/respond.ts +96 -0
- package/src/server/api-client.ts +54 -0
- package/src/server/app-context.ts +39 -0
- package/src/server/help.ts +187 -0
- package/src/server/index.ts +89 -0
- package/src/server/locale.ts +55 -0
- package/src/server/middleware/auth.ts +386 -0
- package/src/server/middleware/index.ts +28 -0
- package/src/server/middleware/invocation.ts +55 -0
- package/src/server/middleware/middleware.ts +65 -0
- package/src/server/middleware/openapi.ts +126 -0
- package/src/server/middleware/rate-limit.ts +125 -0
- package/src/server/middleware/request-logger.ts +41 -0
- package/src/server/middleware/route-template.ts +46 -0
- package/src/server/middleware/runtime.ts +22 -0
- package/src/server/middleware/settings.ts +55 -0
- package/src/server/middleware/validator.ts +49 -0
- package/src/server/middleware/workload.ts +22 -0
- package/src/server/ratelimit.ts +151 -0
- package/src/server/request-cookies.ts +18 -0
- package/src/server/services/access.ts +644 -0
- package/src/server/services/freeipa/client.ts +137 -0
- package/src/server/services/freeipa/index.ts +9 -0
- package/src/server/services/freeipa/session.ts +123 -0
- package/src/server/services/freeipa/test-certificates.ts +44 -0
- package/src/server/services/freeipa/tls.ts +44 -0
- package/src/server/services/freeipa/transport.ts +116 -0
- package/src/server/services/freeipa/util.ts +59 -0
- package/src/server/services/geo.ts +198 -0
- package/src/server/services/index.ts +48 -0
- package/src/server/services/pagination.ts +22 -0
- package/src/server/services/services.ts +13 -0
- package/src/server/time.ts +33 -0
- package/src/services/account-category-policy.ts +51 -0
- package/src/services/account-lifecycle/audit.ts +41 -0
- package/src/services/account-lifecycle/index.ts +940 -0
- package/src/services/account-lifecycle/ipa-backfill.ts +152 -0
- package/src/services/account-lifecycle/notification-sender.ts +13 -0
- package/src/services/account-lifecycle/scheduler.ts +506 -0
- package/src/services/account-model.ts +22 -0
- package/src/services/accounts/app.ts +1671 -0
- package/src/services/accounts/authz.ts +44 -0
- package/src/services/accounts/avatar.ts +120 -0
- package/src/services/accounts/base-group.ts +11 -0
- package/src/services/accounts/base-user.ts +46 -0
- package/src/services/accounts/duplicate-emails.ts +82 -0
- package/src/services/accounts/entities.ts +622 -0
- package/src/services/accounts/group-sql.ts +106 -0
- package/src/services/accounts/groups.ts +272 -0
- package/src/services/accounts/index.ts +14 -0
- package/src/services/accounts/ipa-data.ts +66 -0
- package/src/services/accounts/lifecycle.ts +2 -0
- package/src/services/accounts/local-groups.ts +499 -0
- package/src/services/accounts/model.ts +129 -0
- package/src/services/accounts/notification-sender.ts +31 -0
- package/src/services/accounts/posix.ts +386 -0
- package/src/services/accounts/request-policy.ts +11 -0
- package/src/services/accounts/switching.ts +126 -0
- package/src/services/accounts/users.ts +745 -0
- package/src/services/announcements/index.ts +224 -0
- package/src/services/app-approval.ts +498 -0
- package/src/services/audit/index.ts +438 -0
- package/src/services/auth-flows/index.ts +15 -0
- package/src/services/auth-flows/ipa.ts +197 -0
- package/src/services/auth-flows/magic-link.ts +185 -0
- package/src/services/auth-flows/notification-sender.ts +10 -0
- package/src/services/auth-flows/password-reset.ts +268 -0
- package/src/services/auth-flows/proxy-return.ts +49 -0
- package/src/services/document-extraction.ts +148 -0
- package/src/services/freeipa-config.ts +179 -0
- package/src/services/gateway.ts +186 -0
- package/src/services/identity/constants.ts +18 -0
- package/src/services/identity/index.ts +52 -0
- package/src/services/identity/invocation-actor.ts +120 -0
- package/src/services/identity/invocation-authority.ts +53 -0
- package/src/services/identity/invocation-operations.ts +15 -0
- package/src/services/identity/invocation-token.ts +276 -0
- package/src/services/identity/key-config.ts +41 -0
- package/src/services/identity/key-ring.ts +530 -0
- package/src/services/identity/metrics.ts +29 -0
- package/src/services/identity/routes.ts +18 -0
- package/src/services/identity/runtime-config.ts +88 -0
- package/src/services/identity/session-token.ts +152 -0
- package/src/services/identity/signer-refresh.ts +44 -0
- package/src/services/identity/workload-auth.ts +64 -0
- package/src/services/index.ts +187 -0
- package/src/services/ipa/auth.ts +216 -0
- package/src/services/ipa/connection.ts +57 -0
- package/src/services/ipa/effective-groups.ts +70 -0
- package/src/services/ipa/groups.ts +722 -0
- package/src/services/ipa/guard.ts +17 -0
- package/src/services/ipa/index.ts +17 -0
- package/src/services/ipa/posix.ts +19 -0
- package/src/services/ipa/profile.ts +132 -0
- package/src/services/ipa/runtime.ts +28 -0
- package/src/services/ipa/search.ts +154 -0
- package/src/services/ipa/service-account.ts +15 -0
- package/src/services/ipa/sync-planning.ts +100 -0
- package/src/services/ipa/sync.ts +862 -0
- package/src/services/ipa/users.ts +806 -0
- package/src/services/legal-consent.ts +76 -0
- package/src/services/logging/index.ts +477 -0
- package/src/services/logging/redaction.ts +20 -0
- package/src/services/logging/trace.ts +1231 -0
- package/src/services/mandates/index.ts +855 -0
- package/src/services/mandates/policy.ts +85 -0
- package/src/services/network-security.ts +31 -0
- package/src/services/notifications/batches.ts +722 -0
- package/src/services/notifications/browser.ts +252 -0
- package/src/services/notifications/catalog.ts +113 -0
- package/src/services/notifications/channels.ts +104 -0
- package/src/services/notifications/dispatcher.ts +139 -0
- package/src/services/notifications/email.ts +118 -0
- package/src/services/notifications/index.ts +633 -0
- package/src/services/notifications/live.ts +50 -0
- package/src/services/notifications/observability.ts +407 -0
- package/src/services/notifications/platform.ts +421 -0
- package/src/services/notifications/runtime.ts +120 -0
- package/src/services/notifications/user.ts +248 -0
- package/src/services/notifications/web-push-transport.ts +135 -0
- package/src/services/oauth-tokens.ts +209 -0
- package/src/services/outbox.ts +187 -0
- package/src/services/pdf/gotenberg.ts +290 -0
- package/src/services/pdf/index.ts +43 -0
- package/src/services/pdf/markdown.ts +209 -0
- package/src/services/pdf/template-preview.ts +122 -0
- package/src/services/postgres.ts +76 -0
- package/src/services/providers/index.ts +27 -0
- package/src/services/providers/local/auth.ts +51 -0
- package/src/services/providers/local/index.ts +4 -0
- package/src/services/providers/local/users.ts +263 -0
- package/src/services/rail-preferences.ts +27 -0
- package/src/services/runtime-lifecycle.ts +191 -0
- package/src/services/secrets.ts +10 -0
- package/src/services/service-account-credentials.ts +891 -0
- package/src/services/service-accounts.ts +184 -0
- package/src/services/session/index.ts +236 -0
- package/src/services/session/test-fixture.ts +18 -0
- package/src/services/session/user.ts +144 -0
- package/src/services/settings/api.ts +61 -0
- package/src/services/settings/app.ts +86 -0
- package/src/services/settings/core-settings.ts +796 -0
- package/src/services/settings/crypto.ts +69 -0
- package/src/services/settings/defaults.ts +374 -0
- package/src/services/settings/index.ts +215 -0
- package/src/services/settings/namespace.ts +9 -0
- package/src/services/settings/snapshot.ts +49 -0
- package/src/services/settings/store.ts +241 -0
- package/src/services/settings/templates.ts +4 -0
- package/src/services/sync-ops.ts +403 -0
- package/src/services/topic-cursor.ts +22 -0
- package/src/services/weather/forecast.ts +323 -0
- package/src/services/weather/geo.ts +119 -0
- package/src/services/weather/index.ts +67 -0
- package/src/services/weather/location.ts +24 -0
- package/src/services/weather/locations.ts +133 -0
- package/src/services/weather/migrate.ts +45 -0
- package/src/services/weather/settings.ts +66 -0
- package/src/services/weather/short-id.ts +57 -0
- package/src/services/weather/types.ts +61 -0
- package/src/services/weather/ui.ts +50 -0
- package/src/services/webauthn.ts +385 -0
- package/src/shared/account-action-notice.ts +70 -0
- package/src/shared/account-display.ts +15 -0
- package/src/shared/account-session.ts +15 -0
- package/src/shared/ai-platform-prompt.ts +134 -0
- package/src/shared/ai-usage.ts +49 -0
- package/src/shared/app-presentation.ts +48 -0
- package/src/shared/app-url.ts +12 -0
- package/src/shared/branding.ts +14 -0
- package/src/shared/capability-messages.ts +70 -0
- package/src/shared/email-html.ts +54 -0
- package/src/shared/format.ts +91 -0
- package/src/shared/help.ts +68 -0
- package/src/shared/icons.ts +400 -0
- package/src/shared/index.ts +54 -0
- package/src/shared/locale.ts +48 -0
- package/src/shared/login-method.ts +44 -0
- package/src/shared/markdown/client.ts +130 -0
- package/src/shared/markdown/extensions/code.ts +105 -0
- package/src/shared/markdown/extensions/guided-help.ts +100 -0
- package/src/shared/markdown/extensions/images.ts +79 -0
- package/src/shared/markdown/extensions/info-blocks.ts +97 -0
- package/src/shared/markdown/extensions/katex.ts +120 -0
- package/src/shared/markdown/extensions/links.ts +43 -0
- package/src/shared/markdown/extensions/mark.ts +48 -0
- package/src/shared/markdown/extensions/sub-sup.ts +60 -0
- package/src/shared/markdown/extensions/tables.ts +109 -0
- package/src/shared/markdown/extensions/task-list.ts +53 -0
- package/src/shared/markdown/formula.ts +1187 -0
- package/src/shared/markdown/index.ts +193 -0
- package/src/shared/markdown/shared.ts +36 -0
- package/src/shared/mock-cover.ts +130 -0
- package/src/shared/network-address.ts +106 -0
- package/src/shared/redirect.ts +56 -0
- package/src/shared/template-rendering.ts +140 -0
- package/src/shared/theme.ts +68 -0
- package/src/shared/time.ts +13 -0
- package/src/ssr/AdminLayout.tsx +53 -0
- package/src/ssr/AdminSidebar.tsx +50 -0
- package/src/ssr/AppLaunchpad.island.tsx +236 -0
- package/src/ssr/AppWorkspaceController.island.tsx +21 -0
- package/src/ssr/BrowserNotifications.island.tsx +135 -0
- package/src/ssr/GlobalAnnouncements.island.tsx +142 -0
- package/src/ssr/GlobalSearchDialog.behavior.test.tsx +96 -0
- package/src/ssr/GlobalSearchDialog.tsx +35 -0
- package/src/ssr/GlobalSearchHelpDialog.tsx +104 -0
- package/src/ssr/GlobalSearchTrigger.island.tsx +55 -0
- package/src/ssr/HotkeysHelpRail.island.tsx +55 -0
- package/src/ssr/Layout.render.test.tsx +148 -0
- package/src/ssr/Layout.tsx +292 -0
- package/src/ssr/LayoutBreadcrumbs.island.tsx +44 -0
- package/src/ssr/LayoutFooter.tsx +22 -0
- package/src/ssr/LayoutHeader.tsx +81 -0
- package/src/ssr/LayoutHelp.tsx +869 -0
- package/src/ssr/LayoutPreferences.island.tsx +36 -0
- package/src/ssr/LayoutRail.tsx +58 -0
- package/src/ssr/MinimalLayout.tsx +46 -0
- package/src/ssr/PageError.tsx +29 -0
- package/src/ssr/ProfilePreferences.island.tsx +92 -0
- package/src/ssr/RailApps.island.tsx +61 -0
- package/src/ssr/RailEditor.tsx +293 -0
- package/src/ssr/RegisteredHelpDocuments.island.tsx +3 -0
- package/src/ssr/TimezoneCookie.island.tsx +23 -0
- package/src/ssr/admin-active-link.ts +47 -0
- package/src/ssr/admin-navigation.ts +78 -0
- package/src/ssr/app-appearance.ts +23 -0
- package/src/ssr/app-navigation.ts +41 -0
- package/src/ssr/help-messages.ts +104 -0
- package/src/ssr/index.ts +14 -0
- package/src/ssr/islands/SearchBar.island.tsx +80 -0
- package/src/ssr/islands/index.ts +16 -0
- package/src/ssr/layout-context.ts +17 -0
- package/src/ssr/layout-help-markdown.ts +9 -0
- package/src/ssr/layout-help-navigation.ts +24 -0
- package/src/ssr/layout-help-url.ts +5 -0
- package/src/ssr/layout-runtime.ts +22 -0
- package/src/ssr/page-error-messages.ts +25 -0
- package/src/ssr/platform-messages.ts +135 -0
- package/src/ssr/preference-controller.ts +44 -0
- package/src/ssr/profile-preferences-messages.ts +29 -0
- package/src/ssr/rail-context.ts +21 -0
- package/src/ssr/rail-messages.ts +66 -0
- package/src/ssr/rail-navigation.ts +60 -0
- package/src/ssr/runtime.ts +31 -0
- package/src/ssr/url-filter.ts +127 -0
- package/src/styles/base-popover.css +36 -0
- package/src/styles/effects.css +851 -0
- package/src/styles/global.css +268 -0
- package/src/styles/input.css +58 -0
- package/src/styles/tokens.css +230 -0
- package/src/styles/utilities-buttons.css +405 -0
- package/src/styles/utilities-data.css +33 -0
- package/src/styles/utilities-feedback.css +232 -0
- package/src/styles/utilities-layout.css +603 -0
- package/src/styles/utilities-markdown-editor.css +525 -0
- package/src/styles/utilities-markdown-table.css +234 -0
- package/src/styles/utilities-navigation.css +1054 -0
- package/src/types/ambient.d.ts +24 -0
- package/src/workflows/ai/index.ts +17 -0
- package/src/workflows/ai/runtime.ts +286 -0
- package/src/workflows/ai/store.ts +314 -0
- package/src/workflows/ai/types.ts +111 -0
- package/src/workflows/ai-actions.ts +269 -0
- package/src/workflows/authoring.ts +88 -0
- package/src/workflows/builtins.ts +193 -0
- package/src/workflows/contracts.ts +280 -0
- package/src/workflows/definition.ts +334 -0
- package/src/workflows/editor.ts +113 -0
- package/src/workflows/index.ts +71 -0
- package/src/workflows/language/binder.ts +45 -0
- package/src/workflows/language/canonical.ts +29 -0
- package/src/workflows/language/compiler.ts +396 -0
- package/src/workflows/language/expressions.ts +34 -0
- package/src/workflows/language/index.ts +20 -0
- package/src/workflows/language/references.ts +55 -0
- package/src/workflows/language/schema.ts +134 -0
- package/src/workflows/language/strict-yaml.ts +131 -0
- package/src/workflows/manifest.ts +24 -0
- package/src/workflows/module.ts +12 -0
- package/src/workflows/runtime/coordinator.ts +115 -0
- package/src/workflows/runtime/executor.ts +1003 -0
- package/src/workflows/runtime/index.ts +60 -0
- package/src/workflows/runtime/instant.ts +8 -0
- package/src/workflows/runtime/ports.ts +213 -0
- package/src/workflows/runtime/schedule.ts +203 -0
- package/src/workflows/runtime/trigger.ts +37 -0
- package/src/workflows/runtime/wake.ts +13 -0
- package/src/workflows/store/actions.ts +438 -0
- package/src/workflows/store/budget.ts +145 -0
- package/src/workflows/store/definitions.ts +345 -0
- package/src/workflows/store/events.ts +383 -0
- package/src/workflows/store/index.ts +107 -0
- package/src/workflows/store/observability.ts +594 -0
- package/src/workflows/store/runs.ts +975 -0
- package/src/workflows/store/transaction.ts +23 -0
- package/src/workflows/store/worker.ts +439 -0
- package/src/workflows/testing/conformance.ts +72 -0
- package/src/workflows/testing/index.ts +11 -0
- package/src/workflows/testing/process-fixtures.ts +275 -0
|
@@ -0,0 +1,345 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Workflows, their versions, and what those versions listen to.
|
|
3
|
+
*
|
|
4
|
+
* The one rule underneath everything here: a version is written once. Grids
|
|
5
|
+
* bumped a `revision` column on the workflow row and re-registered its
|
|
6
|
+
* schedules from a reconcile loop, which is the mechanism behind schedules that
|
|
7
|
+
* silently stop firing after a restart — nothing errors, the job just never
|
|
8
|
+
* runs again. A run that pins an immutable version cannot be redirected by an
|
|
9
|
+
* edit, and an activation that pins one cannot be left pointing at a plan that
|
|
10
|
+
* no longer exists.
|
|
11
|
+
*/
|
|
12
|
+
import { type SQL, sql } from "bun";
|
|
13
|
+
import type { WorkflowBoundPlan, WorkflowDiagnostic, WorkflowJsonValue } from "../contracts";
|
|
14
|
+
import { validateWorkflowEffectBudget } from "./budget";
|
|
15
|
+
import { withTransaction } from "./transaction";
|
|
16
|
+
|
|
17
|
+
export type WorkflowAuthor = { kind: "user" | "service_account"; id: string } | { kind: "system"; id?: undefined };
|
|
18
|
+
|
|
19
|
+
export type WorkflowRecord = {
|
|
20
|
+
id: string;
|
|
21
|
+
appId: string;
|
|
22
|
+
scopeId: string;
|
|
23
|
+
key: string;
|
|
24
|
+
name: string;
|
|
25
|
+
description: string | null;
|
|
26
|
+
activeVersionId: string | null;
|
|
27
|
+
createdAt: Date;
|
|
28
|
+
updatedAt: Date;
|
|
29
|
+
};
|
|
30
|
+
|
|
31
|
+
export type WorkflowVersionRecord = {
|
|
32
|
+
id: string;
|
|
33
|
+
workflowId: string;
|
|
34
|
+
revision: number;
|
|
35
|
+
source: string;
|
|
36
|
+
sourceHash: string;
|
|
37
|
+
plan: WorkflowBoundPlan;
|
|
38
|
+
diagnostics: WorkflowDiagnostic[];
|
|
39
|
+
languageId: string;
|
|
40
|
+
languageVersion: number;
|
|
41
|
+
manifestHash: string;
|
|
42
|
+
createdAt: Date;
|
|
43
|
+
};
|
|
44
|
+
|
|
45
|
+
/** What an activation listens for, and with what configuration. */
|
|
46
|
+
export type WorkflowActivationInput = {
|
|
47
|
+
/** Stable within the workflow — the compiler derives it from the trigger's position. */
|
|
48
|
+
key: string;
|
|
49
|
+
/** Namespaced event type, matching a declaration in the app's `workflows.ts`. */
|
|
50
|
+
eventType: string;
|
|
51
|
+
config?: WorkflowJsonValue;
|
|
52
|
+
enabled?: boolean;
|
|
53
|
+
};
|
|
54
|
+
|
|
55
|
+
export type WorkflowActivationRecord = WorkflowActivationInput & {
|
|
56
|
+
id: string;
|
|
57
|
+
workflowId: string;
|
|
58
|
+
workflowVersionId: string;
|
|
59
|
+
enabled: boolean;
|
|
60
|
+
};
|
|
61
|
+
|
|
62
|
+
type WorkflowRow = {
|
|
63
|
+
id: string;
|
|
64
|
+
app_id: string;
|
|
65
|
+
scope_id: string;
|
|
66
|
+
key: string;
|
|
67
|
+
name: string;
|
|
68
|
+
description: string | null;
|
|
69
|
+
active_version_id: string | null;
|
|
70
|
+
created_at: Date;
|
|
71
|
+
updated_at: Date;
|
|
72
|
+
};
|
|
73
|
+
|
|
74
|
+
const toWorkflow = (row: WorkflowRow): WorkflowRecord => ({
|
|
75
|
+
id: row.id,
|
|
76
|
+
appId: row.app_id,
|
|
77
|
+
scopeId: row.scope_id,
|
|
78
|
+
key: row.key,
|
|
79
|
+
name: row.name,
|
|
80
|
+
description: row.description,
|
|
81
|
+
activeVersionId: row.active_version_id,
|
|
82
|
+
createdAt: row.created_at,
|
|
83
|
+
updatedAt: row.updated_at,
|
|
84
|
+
});
|
|
85
|
+
|
|
86
|
+
const WORKFLOW_COLUMNS = "id, app_id, scope_id, key, name, description, active_version_id, created_at, updated_at";
|
|
87
|
+
|
|
88
|
+
// ─── Workflows ───────────────────────────────────────────────────────────────
|
|
89
|
+
|
|
90
|
+
export const createWorkflow = async (
|
|
91
|
+
input: { appId: string; scopeId: string; key: string; name: string; description?: string; author: WorkflowAuthor },
|
|
92
|
+
options: { db?: SQL } = {},
|
|
93
|
+
): Promise<WorkflowRecord> => {
|
|
94
|
+
const db = options.db ?? sql;
|
|
95
|
+
const [row] = await db<WorkflowRow[]>`
|
|
96
|
+
INSERT INTO workflows.workflow (app_id, scope_id, key, name, description, created_by_kind, created_by_id)
|
|
97
|
+
VALUES (${input.appId}, ${input.scopeId}, ${input.key}, ${input.name}, ${input.description ?? null},
|
|
98
|
+
${input.author.kind}, ${input.author.id ?? null}::uuid)
|
|
99
|
+
RETURNING ${db.unsafe(WORKFLOW_COLUMNS)}
|
|
100
|
+
`;
|
|
101
|
+
if (!row) throw new Error("workflow insert returned no row");
|
|
102
|
+
return toWorkflow(row);
|
|
103
|
+
};
|
|
104
|
+
|
|
105
|
+
export const getWorkflow = async (workflowId: string, options: { db?: SQL } = {}): Promise<WorkflowRecord | null> => {
|
|
106
|
+
const db = options.db ?? sql;
|
|
107
|
+
const [row] = await db<WorkflowRow[]>`SELECT ${db.unsafe(WORKFLOW_COLUMNS)} FROM workflows.workflow WHERE id = ${workflowId}::uuid`;
|
|
108
|
+
return row ? toWorkflow(row) : null;
|
|
109
|
+
};
|
|
110
|
+
|
|
111
|
+
export const listWorkflows = async (scope: { appId: string; scopeId: string }, options: { db?: SQL } = {}): Promise<WorkflowRecord[]> => {
|
|
112
|
+
const db = options.db ?? sql;
|
|
113
|
+
const rows = await db<WorkflowRow[]>`
|
|
114
|
+
SELECT ${db.unsafe(WORKFLOW_COLUMNS)} FROM workflows.workflow
|
|
115
|
+
WHERE app_id = ${scope.appId} AND scope_id = ${scope.scopeId}
|
|
116
|
+
ORDER BY name, id
|
|
117
|
+
`;
|
|
118
|
+
return rows.map(toWorkflow);
|
|
119
|
+
};
|
|
120
|
+
|
|
121
|
+
/** Renames only. The plan lives in versions, which is why there is no source here. */
|
|
122
|
+
export const renameWorkflow = async (
|
|
123
|
+
workflowId: string,
|
|
124
|
+
input: { name: string; description?: string | null },
|
|
125
|
+
options: { db?: SQL } = {},
|
|
126
|
+
): Promise<void> => {
|
|
127
|
+
const db = options.db ?? sql;
|
|
128
|
+
await db`
|
|
129
|
+
UPDATE workflows.workflow
|
|
130
|
+
SET name = ${input.name}, description = ${input.description ?? null}, updated_at = now()
|
|
131
|
+
WHERE id = ${workflowId}::uuid
|
|
132
|
+
`;
|
|
133
|
+
};
|
|
134
|
+
|
|
135
|
+
/**
|
|
136
|
+
* Drops every workflow in a scope.
|
|
137
|
+
*
|
|
138
|
+
* The kernel holds `app_id` and `scope_id` as opaque strings rather than
|
|
139
|
+
* foreign keys — `workflows` cannot reference `grids.bases` without inverting
|
|
140
|
+
* the dependency — so an app calls this when one of its scopes goes away.
|
|
141
|
+
*/
|
|
142
|
+
export const deleteWorkflowScope = async (scope: { appId: string; scopeId: string }, options: { db?: SQL } = {}): Promise<number> => {
|
|
143
|
+
return withTransaction(options.db, async (tx) => {
|
|
144
|
+
const rows = await tx<{ id: string }[]>`
|
|
145
|
+
DELETE FROM workflows.workflow WHERE app_id = ${scope.appId} AND scope_id = ${scope.scopeId} RETURNING id
|
|
146
|
+
`;
|
|
147
|
+
await tx`DELETE FROM workflows.event WHERE app_id = ${scope.appId} AND scope_id = ${scope.scopeId}`;
|
|
148
|
+
return rows.length;
|
|
149
|
+
});
|
|
150
|
+
};
|
|
151
|
+
|
|
152
|
+
// ─── Versions ────────────────────────────────────────────────────────────────
|
|
153
|
+
|
|
154
|
+
export type PublishWorkflowVersion = {
|
|
155
|
+
workflowId: string;
|
|
156
|
+
source: string;
|
|
157
|
+
plan: WorkflowBoundPlan;
|
|
158
|
+
diagnostics?: WorkflowDiagnostic[];
|
|
159
|
+
/** Caps on external effects for runs of this version. Absent dimensions are uncapped. */
|
|
160
|
+
effectBudget?: Record<string, number>;
|
|
161
|
+
/**
|
|
162
|
+
* Who runs started by these activations act as, when the occurrence has no
|
|
163
|
+
* actor of its own — a schedule tick, an observed row change.
|
|
164
|
+
*/
|
|
165
|
+
authorization?: WorkflowJsonValue;
|
|
166
|
+
author: WorkflowAuthor;
|
|
167
|
+
/** What the new version listens to. Replaces the previous version's set wholesale. */
|
|
168
|
+
activations: readonly WorkflowActivationInput[];
|
|
169
|
+
/** `false` publishes the version without making it live — a draft. */
|
|
170
|
+
activate?: boolean;
|
|
171
|
+
};
|
|
172
|
+
|
|
173
|
+
/**
|
|
174
|
+
* Writes a new version and re-points the workflow's activations to it, in one
|
|
175
|
+
* transaction.
|
|
176
|
+
*
|
|
177
|
+
* Atomic because the alternative has a window: an event arriving between
|
|
178
|
+
* deleting the old activations and inserting the new ones would match nothing
|
|
179
|
+
* and be silently dropped. The version row itself is never updated afterwards —
|
|
180
|
+
* a database trigger rejects that — so a run already executing this plan keeps
|
|
181
|
+
* executing exactly this plan.
|
|
182
|
+
*/
|
|
183
|
+
export const publishWorkflowVersion = async (input: PublishWorkflowVersion, options: { db?: SQL } = {}): Promise<WorkflowVersionRecord> => {
|
|
184
|
+
validateWorkflowEffectBudget(input.effectBudget ?? {});
|
|
185
|
+
return withTransaction(options.db, async (tx) => {
|
|
186
|
+
// Serialise concurrent publishes of the same workflow, so two of them
|
|
187
|
+
// cannot claim the same revision number or interleave their activations.
|
|
188
|
+
const [current] = await tx<{ id: string }[]>`SELECT id FROM workflows.workflow WHERE id = ${input.workflowId}::uuid FOR UPDATE`;
|
|
189
|
+
if (!current) throw new Error(`workflow ${input.workflowId} does not exist`);
|
|
190
|
+
|
|
191
|
+
const [version] = await tx<
|
|
192
|
+
{
|
|
193
|
+
id: string;
|
|
194
|
+
workflow_id: string;
|
|
195
|
+
revision: number;
|
|
196
|
+
source: string;
|
|
197
|
+
source_hash: string;
|
|
198
|
+
plan: WorkflowBoundPlan;
|
|
199
|
+
diagnostics: WorkflowDiagnostic[];
|
|
200
|
+
language_id: string;
|
|
201
|
+
language_version: number;
|
|
202
|
+
manifest_hash: string;
|
|
203
|
+
created_at: Date;
|
|
204
|
+
}[]
|
|
205
|
+
>`
|
|
206
|
+
INSERT INTO workflows.version (
|
|
207
|
+
workflow_id, revision, source, source_hash, plan, diagnostics, effect_budget,
|
|
208
|
+
language_id, language_version, manifest_hash, created_by_kind, created_by_id
|
|
209
|
+
)
|
|
210
|
+
SELECT ${input.workflowId}::uuid,
|
|
211
|
+
COALESCE(max(revision), 0) + 1,
|
|
212
|
+
${input.source}, ${input.plan.sourceHash}, ${input.plan}, ${input.diagnostics ?? []}, ${input.effectBudget ?? {}},
|
|
213
|
+
${input.plan.languageId}, ${input.plan.languageVersion}, ${input.plan.manifestHash},
|
|
214
|
+
${input.author.kind}, ${input.author.id ?? null}::uuid
|
|
215
|
+
FROM workflows.version WHERE workflow_id = ${input.workflowId}::uuid
|
|
216
|
+
RETURNING *
|
|
217
|
+
`;
|
|
218
|
+
if (!version) throw new Error("workflow version insert returned no row");
|
|
219
|
+
|
|
220
|
+
if (input.activate !== false) {
|
|
221
|
+
// Whether each key is currently enabled, so a publish carries the
|
|
222
|
+
// operator's decision forward instead of turning a disabled workflow
|
|
223
|
+
// back on.
|
|
224
|
+
const existing = await tx<{ key: string; enabled: boolean }[]>`
|
|
225
|
+
SELECT key, enabled FROM workflows.activation WHERE workflow_id = ${input.workflowId}::uuid
|
|
226
|
+
`;
|
|
227
|
+
const wasEnabled = new Map(existing.map((row) => [row.key, row.enabled]));
|
|
228
|
+
|
|
229
|
+
if (input.activations.length > 0) {
|
|
230
|
+
const rows = input.activations.map((activation) => ({
|
|
231
|
+
workflow_id: input.workflowId,
|
|
232
|
+
workflow_version_id: version.id,
|
|
233
|
+
key: activation.key,
|
|
234
|
+
event_type: activation.eventType,
|
|
235
|
+
config: activation.config ?? {},
|
|
236
|
+
authorization_snapshot: input.authorization ?? {},
|
|
237
|
+
enabled: activation.enabled ?? wasEnabled.get(activation.key) ?? true,
|
|
238
|
+
}));
|
|
239
|
+
await tx`
|
|
240
|
+
INSERT INTO workflows.activation ${tx(rows)}
|
|
241
|
+
ON CONFLICT (workflow_id, key) DO UPDATE
|
|
242
|
+
SET workflow_version_id = EXCLUDED.workflow_version_id,
|
|
243
|
+
event_type = EXCLUDED.event_type,
|
|
244
|
+
config = EXCLUDED.config,
|
|
245
|
+
authorization_snapshot = EXCLUDED.authorization_snapshot,
|
|
246
|
+
enabled = EXCLUDED.enabled,
|
|
247
|
+
updated_at = now()
|
|
248
|
+
`;
|
|
249
|
+
}
|
|
250
|
+
// A trigger removed from the source must stop firing, so anything not in
|
|
251
|
+
// this publish goes — matched by key, which is stable across versions.
|
|
252
|
+
await tx`
|
|
253
|
+
DELETE FROM workflows.activation
|
|
254
|
+
WHERE workflow_id = ${input.workflowId}::uuid AND workflow_version_id <> ${version.id}::uuid
|
|
255
|
+
`;
|
|
256
|
+
|
|
257
|
+
await tx`UPDATE workflows.workflow SET active_version_id = ${version.id}::uuid, updated_at = now() WHERE id = ${input.workflowId}::uuid`;
|
|
258
|
+
}
|
|
259
|
+
|
|
260
|
+
return {
|
|
261
|
+
id: version.id,
|
|
262
|
+
workflowId: version.workflow_id,
|
|
263
|
+
revision: version.revision,
|
|
264
|
+
source: version.source,
|
|
265
|
+
sourceHash: version.source_hash,
|
|
266
|
+
plan: version.plan,
|
|
267
|
+
diagnostics: version.diagnostics,
|
|
268
|
+
languageId: version.language_id,
|
|
269
|
+
languageVersion: version.language_version,
|
|
270
|
+
manifestHash: version.manifest_hash,
|
|
271
|
+
createdAt: version.created_at,
|
|
272
|
+
};
|
|
273
|
+
});
|
|
274
|
+
};
|
|
275
|
+
|
|
276
|
+
/** Stops a workflow without deleting it: its activations no longer match. */
|
|
277
|
+
export const setWorkflowEnabled = async (workflowId: string, enabled: boolean, options: { db?: SQL } = {}): Promise<void> => {
|
|
278
|
+
const db = options.db ?? sql;
|
|
279
|
+
await db`UPDATE workflows.activation SET enabled = ${enabled}, updated_at = now() WHERE workflow_id = ${workflowId}::uuid`;
|
|
280
|
+
};
|
|
281
|
+
|
|
282
|
+
export const listWorkflowVersions = async (
|
|
283
|
+
workflowId: string,
|
|
284
|
+
options: { db?: SQL; limit?: number } = {},
|
|
285
|
+
): Promise<WorkflowVersionRecord[]> => {
|
|
286
|
+
const db = options.db ?? sql;
|
|
287
|
+
const rows = await db<
|
|
288
|
+
{
|
|
289
|
+
id: string;
|
|
290
|
+
workflow_id: string;
|
|
291
|
+
revision: number;
|
|
292
|
+
source: string;
|
|
293
|
+
source_hash: string;
|
|
294
|
+
plan: WorkflowBoundPlan;
|
|
295
|
+
diagnostics: WorkflowDiagnostic[];
|
|
296
|
+
language_id: string;
|
|
297
|
+
language_version: number;
|
|
298
|
+
manifest_hash: string;
|
|
299
|
+
created_at: Date;
|
|
300
|
+
}[]
|
|
301
|
+
>`
|
|
302
|
+
SELECT * FROM workflows.version WHERE workflow_id = ${workflowId}::uuid
|
|
303
|
+
ORDER BY revision DESC LIMIT ${options.limit ?? 50}
|
|
304
|
+
`;
|
|
305
|
+
return rows.map((row) => ({
|
|
306
|
+
id: row.id,
|
|
307
|
+
workflowId: row.workflow_id,
|
|
308
|
+
revision: row.revision,
|
|
309
|
+
source: row.source,
|
|
310
|
+
sourceHash: row.source_hash,
|
|
311
|
+
plan: row.plan,
|
|
312
|
+
diagnostics: row.diagnostics,
|
|
313
|
+
languageId: row.language_id,
|
|
314
|
+
languageVersion: row.language_version,
|
|
315
|
+
manifestHash: row.manifest_hash,
|
|
316
|
+
createdAt: row.created_at,
|
|
317
|
+
}));
|
|
318
|
+
};
|
|
319
|
+
|
|
320
|
+
export const listWorkflowActivations = async (workflowId: string, options: { db?: SQL } = {}): Promise<WorkflowActivationRecord[]> => {
|
|
321
|
+
const db = options.db ?? sql;
|
|
322
|
+
const rows = await db<
|
|
323
|
+
{
|
|
324
|
+
id: string;
|
|
325
|
+
workflow_id: string;
|
|
326
|
+
workflow_version_id: string;
|
|
327
|
+
key: string;
|
|
328
|
+
event_type: string;
|
|
329
|
+
config: WorkflowJsonValue;
|
|
330
|
+
enabled: boolean;
|
|
331
|
+
}[]
|
|
332
|
+
>`
|
|
333
|
+
SELECT id, workflow_id, workflow_version_id, key, event_type, config, enabled
|
|
334
|
+
FROM workflows.activation WHERE workflow_id = ${workflowId}::uuid ORDER BY key
|
|
335
|
+
`;
|
|
336
|
+
return rows.map((row) => ({
|
|
337
|
+
id: row.id,
|
|
338
|
+
workflowId: row.workflow_id,
|
|
339
|
+
workflowVersionId: row.workflow_version_id,
|
|
340
|
+
key: row.key,
|
|
341
|
+
eventType: row.event_type,
|
|
342
|
+
config: row.config,
|
|
343
|
+
enabled: row.enabled,
|
|
344
|
+
}));
|
|
345
|
+
};
|