create-windy 0.9.1 → 0.10.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (253) hide show
  1. package/dist/cli.js +1691 -1151
  2. package/package.json +2 -2
  3. package/template/.agents/skills/windy-business-module/SKILL.md +33 -1
  4. package/template/.windy-template.json +6 -2
  5. package/template/AGENTS.md +4 -0
  6. package/template/README.md +2 -0
  7. package/template/apps/agent-server/Dockerfile +1 -1
  8. package/template/apps/agent-server/README.md +1 -1
  9. package/template/apps/agent-server/native/EXTENSIONS.md +2 -2
  10. package/template/apps/agent-server/native/parallel-harness.ts +2 -0
  11. package/template/apps/agent-server/native/storage-lifecycle.test.ts +2 -1
  12. package/template/apps/agent-server/package.json +42 -41
  13. package/template/apps/agent-server/plugins/downloads/README.md +1 -1
  14. package/template/apps/agent-server/plugins/drop-overlay/README.md +1 -1
  15. package/template/apps/agent-server/plugins/settings/README.md +1 -1
  16. package/template/apps/agent-server/plugins/skill-library/client-chunks.test.ts +4 -1
  17. package/template/apps/agent-server/plugins/theme/README.md +5 -1
  18. package/template/apps/agent-server/plugins/theme/source-tokens.ts +0 -1
  19. package/template/apps/agent-server/plugins/theme/tokens.json +0 -4
  20. package/template/apps/agent-server/plugins/tool-catalog/README.md +6 -3
  21. package/template/apps/agent-server/plugins/tool-catalog/discovery.mjs +13 -10
  22. package/template/apps/agent-server/plugins/tool-catalog/discovery.test.ts +68 -6
  23. package/template/apps/agent-server/runtime/compatibility.ts +7 -1
  24. package/template/apps/agent-server/runtime/dsh-engine.ts +2 -0
  25. package/template/apps/agent-server/runtime/questions-workflow.nodecheck.ts +2 -0
  26. package/template/apps/server/Dockerfile +2 -1
  27. package/template/apps/server/package.json +11 -11
  28. package/template/apps/server/scripts/validate-module-composition-once.ts +2 -0
  29. package/template/apps/server/scripts/validate-module-composition.ts +8 -4
  30. package/template/apps/server/src/admin/routes.test.ts +29 -1
  31. package/template/apps/server/src/admin/routes.ts +20 -2
  32. package/template/apps/server/src/agent/client-session/completion.ts +1 -1
  33. package/template/apps/server/src/agent/client-session/manifest-admission.ts +1 -1
  34. package/template/apps/server/src/agent/client-session/request.ts +1 -1
  35. package/template/apps/server/src/agent/context-version-routes.ts +37 -13
  36. package/template/apps/server/src/agent/run-facade.ts +1 -1
  37. package/template/apps/server/src/agent/run-input-verification.ts +1 -1
  38. package/template/apps/server/src/agent/run-routes.ts +1 -14
  39. package/template/apps/server/src/agent/run-start-preparation.ts +1 -1
  40. package/template/apps/server/src/agent/runtime-bootstrap-input.ts +2 -0
  41. package/template/apps/server/src/agent/runtime-bootstrap.ts +49 -157
  42. package/template/apps/server/src/agent/runtime-disabled-composition.ts +2 -1
  43. package/template/apps/server/src/agent/session-invalidation/authorization-revocation.ts +54 -0
  44. package/template/apps/server/src/agent/session-runtime-composition.ts +1 -51
  45. package/template/apps/server/src/agent/unavailable-routes.ts +13 -2
  46. package/template/apps/server/src/agent-workflow/runtime-composition.ts +3 -0
  47. package/template/apps/server/src/agent-workflow/service.ts +17 -1
  48. package/template/apps/server/src/ai-artifact/media-resource-route.test.ts +134 -0
  49. package/template/apps/server/src/ai-artifact/routes.ts +1 -1
  50. package/template/apps/server/src/ai-artifact/runtime.ts +12 -0
  51. package/template/apps/server/src/ai-runtime-readiness/operation-port.test-support.ts +1 -1
  52. package/template/apps/server/src/ai-runtime-readiness/operation-port.ts +8 -0
  53. package/template/apps/server/src/ai-runtime-security/internal-token.ts +14 -0
  54. package/template/apps/server/src/app/antivirus-composition.test.ts +63 -0
  55. package/template/apps/server/src/app/antivirus-composition.ts +29 -0
  56. package/template/apps/server/src/app/dsh-workbench-socket-audit.test.ts +2 -1
  57. package/template/apps/server/src/configuration/definition.ts +15 -11
  58. package/template/apps/server/src/document/facade-support.ts +2 -2
  59. package/template/apps/server/src/document/facade.ts +2 -2
  60. package/template/apps/server/src/document/output-artifact-composition.ts +9 -5
  61. package/template/apps/server/src/document/output-artifact.test-support.ts +1 -1
  62. package/template/apps/server/src/embedding/facade.ts +1 -1
  63. package/template/apps/server/src/embedding/input.ts +1 -1
  64. package/template/apps/server/src/embedding/routes.ts +1 -1
  65. package/template/apps/server/src/index.ts +60 -60
  66. package/template/apps/server/src/license/routes.ts +4 -1
  67. package/template/apps/server/src/license/runtime-business-access.test.ts +261 -0
  68. package/template/apps/server/src/media-runtime/composition.ts +157 -0
  69. package/template/apps/server/src/media-runtime/media-only-composition.ts +44 -0
  70. package/template/apps/server/src/media-runtime/module-ai-port-factory.test.ts +69 -0
  71. package/template/apps/server/src/media-runtime/module-ai-port-factory.ts +72 -0
  72. package/template/apps/server/src/{agent → media-runtime}/runtime-readiness-sources.ts +14 -6
  73. package/template/apps/server/src/media-runtime/shared-composition.ts +104 -0
  74. package/template/apps/server/src/module-composition.test.ts +22 -0
  75. package/template/apps/server/src/module-composition.ts +48 -0
  76. package/template/apps/server/src/module-host/ai-operation-port.ts +97 -30
  77. package/template/apps/server/src/module-host/ai-operation-speech-normalize.test.ts +1 -1
  78. package/template/apps/server/src/module-host/http-runtime.ts +9 -3
  79. package/template/apps/server/src/module-host/static-route-authorization.test.ts +6 -3
  80. package/template/apps/server/src/module-host/storage-authorization-binding.test.ts +4 -0
  81. package/template/apps/server/src/module-runtime-validation.ts +2 -0
  82. package/template/apps/server/src/observability/diagnostic-index.ts +26 -1
  83. package/template/apps/server/src/observability/diagnostic-repository.ts +40 -11
  84. package/template/apps/server/src/platform-http-runtime.ts +1 -1
  85. package/template/apps/server/src/runtime-feature.ts +5 -1
  86. package/template/apps/server/src/runtime.ts +3 -0
  87. package/template/apps/server/src/settings/drizzle-watermark-repository.ts +35 -4
  88. package/template/apps/server/src/settings/watermark-repository.ts +14 -0
  89. package/template/apps/server/src/settings/watermark-routes.test.ts +84 -2
  90. package/template/apps/server/src/settings/watermark-routes.ts +109 -0
  91. package/template/apps/server/src/settings/watermark-transfer.ts +79 -0
  92. package/template/apps/server/src/speech/facade-validation.ts +1 -1
  93. package/template/apps/server/src/speech/facade.ts +2 -2
  94. package/template/apps/server/src/startup-composition-validation.test.ts +32 -0
  95. package/template/apps/server/src/startup-finalization.ts +2 -0
  96. package/template/apps/server/src/startup-runtime.ts +77 -0
  97. package/template/apps/server/src/system/ai-runtime-build.ts +3 -0
  98. package/template/apps/server/src/system/ai-runtime-configuration.test.ts +36 -0
  99. package/template/apps/server/src/system/ai-runtime-configuration.ts +58 -0
  100. package/template/apps/server/src/system/diagnostic-routes.test.ts +45 -0
  101. package/template/apps/server/src/system/diagnostic-routes.ts +35 -0
  102. package/template/apps/server/src/system/environment-policy-reader.test.ts +74 -0
  103. package/template/apps/server/src/system/environment-policy-reader.ts +62 -0
  104. package/template/apps/server/src/system/feature-environment-assessment.test.ts +148 -0
  105. package/template/apps/server/src/system/feature-environment-assessment.ts +179 -0
  106. package/template/apps/server/src/system/host-diagnostics.test.ts +155 -0
  107. package/template/apps/server/src/system/host-diagnostics.ts +225 -0
  108. package/template/apps/server/src/system/menu-registry.test.ts +26 -0
  109. package/template/apps/server/src/system/menu-registry.ts +9 -7
  110. package/template/apps/server/src/system/operations.test.ts +5 -0
  111. package/template/apps/server/src/system/operations.ts +36 -12
  112. package/template/apps/server/src/system/role-authorization-postgres.integration.test.ts +181 -0
  113. package/template/apps/web/Dockerfile +7 -3
  114. package/template/apps/web/dev/dev-port.test.ts +6 -6
  115. package/template/apps/web/dev/dev-port.ts +1 -1
  116. package/template/apps/web/dev/start.ts +6 -1
  117. package/template/apps/web/index.html +1 -0
  118. package/template/apps/web/package.json +16 -16
  119. package/template/apps/web/runtime-server.test.ts +22 -1
  120. package/template/apps/web/runtime-server.ts +6 -0
  121. package/template/apps/web/src/App.vue +6 -3
  122. package/template/apps/web/src/assets/windy.svg +4 -0
  123. package/template/apps/web/src/components/auth/LoginForm.vue +2 -2
  124. package/template/apps/web/src/components/auth/PasswordChangeForm.vue +14 -3
  125. package/template/apps/web/src/components/common/FormDialog.vue +1 -1
  126. package/template/apps/web/src/components/license/LicenseFlow.webtest.ts +3 -0
  127. package/template/apps/web/src/components/license/LicenseMachineCodeQr.vue +99 -0
  128. package/template/apps/web/src/components/license/LicenseMachineCodeQr.webtest.ts +83 -0
  129. package/template/apps/web/src/components/license/LicensePairingCard.vue +1 -1
  130. package/template/apps/web/src/components/license/LicenseStatusCard.vue +14 -2
  131. package/template/apps/web/src/composables/useLoginFlow.ts +2 -2
  132. package/template/apps/web/src/composables/usePlatformSettings.ts +1 -1
  133. package/template/apps/web/src/composables/useWatermarkSettings.ts +1 -0
  134. package/template/apps/web/src/layout/AppSidebar.vue +5 -9
  135. package/template/apps/web/src/layout/AppSidebar.webtest.ts +4 -1
  136. package/template/apps/web/src/pages/auth/ChangePasswordPage.vue +67 -6
  137. package/template/apps/web/src/pages/auth/LoginPage.vue +3 -12
  138. package/template/apps/web/src/pages/configuration/components/ModuleConfigurationEditor.vue +30 -0
  139. package/template/apps/web/src/pages/configuration/components/ModuleConfigurationWorkbench.vue +25 -14
  140. package/template/apps/web/src/pages/configuration/components/TimeZoneSelect.vue +55 -0
  141. package/template/apps/web/src/pages/profile/PersonalSettingsPage.vue +64 -11
  142. package/template/apps/web/src/pages/profile/PersonalSettingsPage.webtest.ts +21 -1
  143. package/template/apps/web/src/pages/settings/BrandingSettingsSection.vue +7 -18
  144. package/template/apps/web/src/pages/settings/BrandingSettingsSection.webtest.ts +9 -4
  145. package/template/apps/web/src/pages/settings/GlobalSettingsPage.vue +51 -6
  146. package/template/apps/web/src/pages/settings/GlobalSettingsPage.webtest.ts +19 -3
  147. package/template/apps/web/src/pages/settings/WatermarkSettingsSection.vue +1 -0
  148. package/template/apps/web/src/pages/settings/WatermarkYamlTransfer.vue +211 -0
  149. package/template/apps/web/src/pages/system/DiagnosticLookupPage.vue +18 -3
  150. package/template/apps/web/src/pages/system/DiagnosticLookupPage.webtest.ts +4 -1
  151. package/template/apps/web/src/pages/system/SystemOperationsPage.vue +23 -0
  152. package/template/apps/web/src/pages/system/components/DiagnosticLogList.vue +120 -0
  153. package/template/apps/web/src/pages/system/components/OperationEnvironmentPanel.vue +237 -0
  154. package/template/apps/web/src/pages/system/components/OperationFeatureAssessmentPanel.vue +131 -0
  155. package/template/apps/web/src/pages/system/components/PagedSelectionList.vue +31 -24
  156. package/template/apps/web/src/pages/system/components/SystemResourceActions.vue +2 -1
  157. package/template/apps/web/src/pages/system/components/SystemResourceEditor.vue +11 -2
  158. package/template/apps/web/src/pages/system/components/SystemResourcePage.vue +1 -0
  159. package/template/apps/web/src/pages/system/components/SystemResourcePage.webtest.ts +6 -2
  160. package/template/apps/web/src/pages/system/components/agent-skills/AgentSkillImportDialog.vue +18 -9
  161. package/template/apps/web/src/pages/system/components/agent-workbench/SessionReplayTimeline.vue +18 -9
  162. package/template/apps/web/src/pages/system/components/agent-workbench/TestRunComposer.vue +66 -34
  163. package/template/apps/web/src/pages/system/components/agent-workbench/ToolCatalogPanel.vue +48 -33
  164. package/template/apps/web/src/pages/system/components/agent-workbench/ToolCatalogPanel.webtest.ts +9 -2
  165. package/template/apps/web/src/pages/system/components/agent-workbench/ToolRuleDetail.vue +23 -16
  166. package/template/apps/web/src/pages/system/components/dictionary-bulk/DictionaryBulkJobDetail.vue +10 -7
  167. package/template/apps/web/src/pages/system/components/user-account/RolePermissionSummary.vue +81 -57
  168. package/template/apps/web/src/pages/system/components/user-account/UserRoleSelector.vue +6 -4
  169. package/template/apps/web/src/pages/system/components/user-account/UserRoleSelector.webtest.ts +20 -4
  170. package/template/apps/web/src/pages/system/resource-config.ts +9 -0
  171. package/template/apps/web/src/pages/work-orders/WorkOrderListPage.vue +1 -1
  172. package/template/apps/web/src/router/disabled-feature-loading.webtest.ts +78 -0
  173. package/template/apps/web/src/router/index.ts +3 -6
  174. package/template/apps/web/src/router/manifest-routes.ts +2 -3
  175. package/template/apps/web/src/router/platform-admin-pages.ts +21 -62
  176. package/template/apps/web/src/router/platform-admin-route-bindings.ts +4 -4
  177. package/template/apps/web/src/services/diagnostics-api.ts +13 -1
  178. package/template/apps/web/src/services/operations-api.ts +4 -0
  179. package/template/apps/web/src/services/platform-settings-api.ts +35 -1
  180. package/template/apps/web/vite.config.ts +9 -3
  181. package/template/deploy/environment/windy.environment.example.yaml +53 -0
  182. package/template/docker-compose.yml +4 -2
  183. package/template/docs/architecture/agent-admin-workbench-implementation.md +1 -1
  184. package/template/docs/architecture/agent-admin-workbench-plan.md +1 -1
  185. package/template/docs/architecture/agent-workflow.md +8 -0
  186. package/template/docs/architecture/durable-jobs.md +17 -0
  187. package/template/docs/architecture/embedded-dsh-integration.md +1 -1
  188. package/template/docs/development/dsh-plugins.md +1 -1
  189. package/template/docs/development/performance-engineering.md +24 -0
  190. package/template/docs/operations/admin-settings-yaml.md +29 -0
  191. package/template/docs/operations/dsh-agent-migration.md +2 -2
  192. package/template/docs/operations/environment-capabilities.md +185 -0
  193. package/template/docs/platform/module-configuration.md +18 -3
  194. package/template/docs/platform/platform-authentication.md +1 -1
  195. package/template/package.json +10 -8
  196. package/template/packages/config/package.json +2 -2
  197. package/template/packages/config/src/definition.ts +14 -4
  198. package/template/packages/config/src/environment-loader.ts +27 -3
  199. package/template/packages/config/src/platform-ai-runtime.test.ts +94 -0
  200. package/template/packages/config/src/platform.ts +5 -2
  201. package/template/packages/database/drizzle/0065_durable_job_lease_snapshot_lookup.sql +1 -0
  202. package/template/packages/database/drizzle/0066_agent_source_sequence_bigint.sql +3 -0
  203. package/template/packages/database/drizzle/0067_media_runtime_access.sql +46 -0
  204. package/template/packages/database/drizzle/meta/0065_snapshot.json +15370 -0
  205. package/template/packages/database/drizzle/meta/0066_snapshot.json +15370 -0
  206. package/template/packages/database/drizzle/meta/0067_snapshot.json +15370 -0
  207. package/template/packages/database/drizzle/meta/_journal.json +21 -0
  208. package/template/packages/database/package.json +3 -3
  209. package/template/packages/database/src/schema/agent-session.ts +4 -3
  210. package/template/packages/database/src/schema/durable-jobs.ts +4 -0
  211. package/template/packages/database/src/schema/index.ts +3 -1
  212. package/template/packages/database/src/schema-durable-recovery.test.ts +21 -1
  213. package/template/packages/database/src/schema-source-sequence.test.ts +24 -0
  214. package/template/packages/example-work-order/package.json +2 -2
  215. package/template/packages/modules/package.json +1 -1
  216. package/template/packages/modules/src/admin-ui-boundary.test.ts +33 -0
  217. package/template/packages/modules/src/composition.ts +11 -28
  218. package/template/packages/modules/src/manifest.ts +2 -0
  219. package/template/packages/modules/src/menu-composition.ts +24 -0
  220. package/template/packages/modules/src/system-admin-routes.ts +2 -2
  221. package/template/packages/modules/src/system-admin-ui-catalog.ts +6 -1
  222. package/template/packages/modules/src/system-ai-api-bindings.ts +0 -16
  223. package/template/packages/modules/src/system-api-control-plane.ts +9 -1
  224. package/template/packages/modules/src/system-api-permissions.ts +7 -0
  225. package/template/packages/modules/src/system-api-watermark.ts +21 -0
  226. package/template/packages/modules/src/system-audit-actions.ts +3 -1
  227. package/template/packages/modules/src/system-features.ts +21 -3
  228. package/template/packages/modules/src/system-media-api-bindings.ts +97 -0
  229. package/template/packages/modules/src/system-module-audit-selection.ts +2 -0
  230. package/template/packages/modules/src/system-module-catalog.test.ts +13 -6
  231. package/template/packages/modules/src/system-module-catalog.ts +6 -241
  232. package/template/packages/modules/src/system-module-definitions.ts +260 -0
  233. package/template/packages/modules/src/system-modules-access.test.ts +2 -0
  234. package/template/packages/modules/src/system-modules.test.ts +7 -1
  235. package/template/packages/modules/src/system-modules.ts +25 -13
  236. package/template/packages/modules/src/system-permissions.ts +12 -0
  237. package/template/packages/server-sdk/package.json +1 -1
  238. package/template/packages/shared/index.ts +3 -0
  239. package/template/packages/shared/package.json +1 -1
  240. package/template/packages/shared/src/environment-assessment.ts +68 -0
  241. package/template/packages/shared/src/environment-policy.ts +205 -0
  242. package/template/packages/shared/src/license-console-capabilities.ts +7 -0
  243. package/template/packages/shared/src/license.ts +1 -0
  244. package/template/packages/shared/src/module-configuration.ts +2 -1
  245. package/template/scripts/operations/collect-device-info.py +230 -0
  246. package/template/apps/server/src/agent/module-ai-port-factory.ts +0 -41
  247. /package/template/apps/server/src/{agent → ai-runtime-security}/execution-grants.ts +0 -0
  248. /package/template/apps/server/src/{agent → ai-runtime-security}/idempotency-key.test.ts +0 -0
  249. /package/template/apps/server/src/{agent → ai-runtime-security}/idempotency-key.ts +0 -0
  250. /package/template/apps/server/src/{agent → ai-runtime-security}/provider-input-governance.test.ts +0 -0
  251. /package/template/apps/server/src/{agent → ai-runtime-security}/provider-input-governance.ts +0 -0
  252. /package/template/apps/server/src/{agent → media-runtime}/required-environment.ts +0 -0
  253. /package/template/apps/server/src/{agent → media-runtime}/runtime-readiness-sources.test.ts +0 -0
@@ -456,6 +456,27 @@
456
456
  "when": 1793213711851,
457
457
  "tag": "0064_dsh_skills_diagnostics",
458
458
  "breakpoints": true
459
+ },
460
+ {
461
+ "idx": 65,
462
+ "version": "7",
463
+ "when": 1793897949256,
464
+ "tag": "0065_durable_job_lease_snapshot_lookup",
465
+ "breakpoints": true
466
+ },
467
+ {
468
+ "idx": 66,
469
+ "version": "7",
470
+ "when": 1793979537210,
471
+ "tag": "0066_agent_source_sequence_bigint",
472
+ "breakpoints": true
473
+ },
474
+ {
475
+ "idx": 67,
476
+ "version": "7",
477
+ "when": 1793983613438,
478
+ "tag": "0067_media_runtime_access",
479
+ "breakpoints": true
459
480
  }
460
481
  ]
461
482
  }
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@southwind-ai/database",
3
- "version": "0.3.6",
3
+ "version": "0.3.7",
4
4
  "license": "UNLICENSED",
5
5
  "type": "module",
6
6
  "engines": {
@@ -16,7 +16,7 @@
16
16
  },
17
17
  "dependencies": {
18
18
  "@southwind-ai/shared": "workspace:^0.3.2",
19
- "drizzle-orm": "^0.45.2"
19
+ "drizzle-orm": "^0.45.4"
20
20
  },
21
21
  "exports": {
22
22
  ".": "./index.ts"
@@ -25,6 +25,6 @@
25
25
  "access": "public"
26
26
  },
27
27
  "devDependencies": {
28
- "pg": "^8.22.0"
28
+ "pg": "^8.23.1"
29
29
  }
30
30
  }
@@ -1,5 +1,6 @@
1
1
  import { sql } from "drizzle-orm";
2
2
  import {
3
+ bigint,
3
4
  check,
4
5
  doublePrecision,
5
6
  index,
@@ -148,7 +149,7 @@ export const agentContextSources = pgTable(
148
149
  sourceKind: varchar("source_kind", { length: 48 }).notNull(),
149
150
  sourceId: varchar("source_id", { length: 256 }).notNull(),
150
151
  sourceVersion: varchar("source_version", { length: 160 }).notNull(),
151
- sourceSequence: integer("source_sequence").notNull(),
152
+ sourceSequence: bigint("source_sequence", { mode: "number" }).notNull(),
152
153
  sourceDigest: varchar("source_digest", { length: 71 }).notNull(),
153
154
  validityStatus: varchar("validity_status", { length: 16 }).notNull(),
154
155
  validityReason: varchar("validity_reason", { length: 32 }),
@@ -238,7 +239,7 @@ export const agentMemorySources = pgTable(
238
239
  sourceKind: varchar("source_kind", { length: 48 }).notNull(),
239
240
  sourceId: varchar("source_id", { length: 256 }).notNull(),
240
241
  sourceVersion: varchar("source_version", { length: 160 }).notNull(),
241
- sourceSequence: integer("source_sequence").notNull(),
242
+ sourceSequence: bigint("source_sequence", { mode: "number" }).notNull(),
242
243
  sourceDigest: varchar("source_digest", { length: 71 }).notNull(),
243
244
  validityStatus: varchar("validity_status", { length: 16 }).notNull(),
244
245
  validityReason: varchar("validity_reason", { length: 32 }),
@@ -270,7 +271,7 @@ export const agentSourceInvalidations = pgTable(
270
271
  sourceKind: varchar("source_kind", { length: 48 }).notNull(),
271
272
  sourceId: varchar("source_id", { length: 256 }).notNull(),
272
273
  sourceVersion: varchar("source_version", { length: 160 }).notNull(),
273
- sequence: integer("sequence").notNull(),
274
+ sequence: bigint("sequence", { mode: "number" }).notNull(),
274
275
  sourceDigest: varchar("source_digest", { length: 71 }),
275
276
  cause: varchar("cause", { length: 32 }).notNull(),
276
277
  status: varchar("status", { length: 24 }).notNull().default("pending"),
@@ -147,6 +147,10 @@ export const durableJobLeases = pgTable(
147
147
  .on(table.stageId)
148
148
  .where(sql`${table.status} = 'active'`),
149
149
  index("idx_durable_job_leases_expiry").on(table.status, table.expiresAt),
150
+ index("idx_durable_job_leases_job_acquired").on(
151
+ table.jobId,
152
+ table.acquiredAt,
153
+ ),
150
154
  check("ck_durable_job_leases_fencing", sql`${table.fencingToken} > 0`),
151
155
  ],
152
156
  );
@@ -41,9 +41,11 @@ export * from "./agent-session-receipt.js";
41
41
  export * from "./agent-session.js";
42
42
  export * from "./client-agent.js";
43
43
  export * from "./client-agent-workflow-artifact.js";
44
+ // @windy-module system.agent end
45
+ // @windy-module system.media-runtime begin
44
46
  export * from "./embedding-runtime.js";
45
47
  export * from "./ai-output-artifacts.js";
46
- // @windy-module system.agent end
48
+ // @windy-module system.media-runtime end
47
49
 
48
50
  // @windy-module system.agent begin
49
51
  export * from "./agent-skills.js";
@@ -1,7 +1,7 @@
1
1
  // @windy-module system.scheduler begin
2
2
  import { describe, expect, test } from "bun:test";
3
3
  import { getTableConfig } from "drizzle-orm/pg-core";
4
- import { durableJobRecoveries } from "./schema/index.js";
4
+ import { durableJobLeases, durableJobRecoveries } from "./schema/index.js";
5
5
 
6
6
  describe("durable job recovery schema", () => {
7
7
  test("人工恢复事实按任务与外部请求幂等", async () => {
@@ -27,5 +27,25 @@ describe("durable job recovery schema", () => {
27
27
  'CREATE UNIQUE INDEX "uk_durable_job_recoveries_idempotency"',
28
28
  );
29
29
  });
30
+ test("历史租约查找索引覆盖所有状态并支持按获取时间排序", async () => {
31
+ const name = "idx_durable_job_leases_job_acquired";
32
+ const index = getTableConfig(durableJobLeases).indexes.find(
33
+ ({ config }) => config.name === name,
34
+ );
35
+ expect(index?.config.columns).toEqual([
36
+ expect.objectContaining({ name: "job_id" }),
37
+ expect.objectContaining({ name: "acquired_at" }),
38
+ ]);
39
+ expect(index?.config.where).toBeUndefined();
40
+ const migration = await Bun.file(
41
+ new URL(
42
+ "../drizzle/0065_durable_job_lease_snapshot_lookup.sql",
43
+ import.meta.url,
44
+ ),
45
+ ).text();
46
+ expect(migration).toMatch(
47
+ /CREATE INDEX "idx_durable_job_leases_job_acquired" ON "durable_job_leases" USING btree \("job_id","acquired_at"\);/,
48
+ );
49
+ });
30
50
  });
31
51
  // @windy-module system.scheduler end
@@ -0,0 +1,24 @@
1
+ // @windy-module system.agent begin
2
+ import { describe, expect, test } from "bun:test";
3
+ import {
4
+ agentContextSources,
5
+ agentMemorySources,
6
+ agentSourceInvalidations,
7
+ } from "./schema/agent-session.js";
8
+
9
+ describe("来源序号持久化范围", () => {
10
+ test("来源坐标使用 bigint,读取毫秒序号仍为精确 number", () => {
11
+ for (const column of [
12
+ agentContextSources.sourceSequence,
13
+ agentMemorySources.sourceSequence,
14
+ agentSourceInvalidations.sequence,
15
+ ]) {
16
+ expect(column.getSQLType()).toBe("bigint");
17
+ expect(column.mapFromDriverValue("1793979283424")).toBe(1793979283424);
18
+ expect(column.mapFromDriverValue(String(Number.MAX_SAFE_INTEGER))).toBe(
19
+ Number.MAX_SAFE_INTEGER,
20
+ );
21
+ }
22
+ });
23
+ });
24
+ // @windy-module system.agent end
@@ -10,8 +10,8 @@
10
10
  "@southwind-ai/modules": "workspace:*",
11
11
  "@southwind-ai/server-sdk": "workspace:*",
12
12
  "@southwind-ai/shared": "workspace:*",
13
- "drizzle-orm": "^0.45.2",
14
- "zod": "^4.4.3"
13
+ "drizzle-orm": "^0.45.4",
14
+ "zod": "^4.6.7"
15
15
  },
16
16
  "peerDependencies": {
17
17
  "vue": "^3.5.0"
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@southwind-ai/modules",
3
- "version": "0.3.2",
3
+ "version": "0.3.3",
4
4
  "license": "UNLICENSED",
5
5
  "type": "module",
6
6
  "engines": {
@@ -0,0 +1,33 @@
1
+ import { expect, test } from "bun:test";
2
+
3
+ // Inspect the resolved graph before tree-shaking: Vite dev serves these imports
4
+ // even when production could eliminate unused exports.
5
+ test("browser admin UI entry does not traverse full platform assembly", async () => {
6
+ const loaded: string[] = [];
7
+ const result = await Bun.build({
8
+ entrypoints: [import.meta.dir + "/admin-ui-entry.ts"],
9
+ target: "browser",
10
+ write: false,
11
+ plugins: [
12
+ {
13
+ name: "record-browser-dependencies",
14
+ setup(build) {
15
+ build.onLoad({ filter: /\.[cm]?[jt]s$/ }, (args) => {
16
+ loaded.push(args.path.split("/").at(-1)!);
17
+ return undefined;
18
+ });
19
+ },
20
+ },
21
+ ],
22
+ });
23
+ expect(result.success).toBe(true);
24
+ expect(loaded).toContain("system-module-definitions.ts");
25
+ expect(loaded).not.toContain("system-module-catalog.ts");
26
+ expect(loaded).not.toContain("system-modules.ts");
27
+ expect(
28
+ loaded.filter((name) =>
29
+ /^system-agent-|^system-ai-|^system-api-/.test(name),
30
+ ),
31
+ ).toEqual([]);
32
+ expect(loaded).not.toContain("system-audit-actions.ts");
33
+ });
@@ -1,4 +1,3 @@
1
- import type { MenuNode } from "@southwind-ai/shared";
2
1
  import type {
3
2
  ModuleImplementationBindings,
4
3
  ModuleManifest,
@@ -10,7 +9,11 @@ import {
10
9
  validateCapabilityKeyAlignment,
11
10
  } from "./capability-guard-validation.js";
12
11
  import { validateImplementationBindings } from "./implementation-bindings.js";
13
- import { composeModuleMenus } from "./menu-composition.js";
12
+ import {
13
+ composeModuleMenus,
14
+ flattenMenus,
15
+ validateMenuRoutes,
16
+ } from "./menu-composition.js";
14
17
  import { validateCapabilityCatalogs } from "./catalog-validation.js";
15
18
  import {
16
19
  snapshotModuleManifestSecrets,
@@ -125,9 +128,13 @@ export function validateModuleComposition(
125
128
  validateImplementationBindings(
126
129
  {
127
130
  adminRoutes: adminRoutes.map(({ key }) => key),
128
- apiRoutes: apiRoutes.map(apiRouteKey),
131
+ apiRoutes: apiRoutes
132
+ .map(apiRouteKey)
133
+ .filter((key) => !implementations.unavailableApiRoutes?.has(key)),
129
134
  tasks: tasks.map(({ key }) => key),
130
- tools: tools.map(({ key }) => key),
135
+ tools: tools
136
+ .map(({ key }) => key)
137
+ .filter((key) => !implementations.unavailableTools?.has(key)),
131
138
  providers: providers.map(({ key }) => key),
132
139
  },
133
140
  aiOperations,
@@ -304,26 +311,6 @@ function validateReferences(
304
311
  }
305
312
  }
306
313
 
307
- function validateMenuRoutes(
308
- menus: readonly MenuNode[],
309
- routes: readonly ModuleManifest["adminRoutes"][number][],
310
- ): void {
311
- const byPath = new Map(routes.map((route) => [route.path, route]));
312
- for (const menu of menus) {
313
- if (!menu.path) continue;
314
- const route = byPath.get(menu.path);
315
- if (!route)
316
- throw new Error(`菜单 ${menu.key} 缺少 Admin Route:${menu.path}`);
317
- if (
318
- route.directAccess !== "admin-admission" &&
319
- (route.permissionKey !== menu.permissionKey ||
320
- route.featureKey !== menu.featureKey)
321
- ) {
322
- throw new Error(`菜单 ${menu.key} 与 Admin Route Guard 不一致`);
323
- }
324
- }
325
- }
326
-
327
314
  function validateSchemaMigrations(
328
315
  schemas: readonly ModuleManifest["schemaExports"][number][],
329
316
  ): void {
@@ -342,7 +329,3 @@ function unique(label: string, values: readonly string[]): Set<string> {
342
329
  }
343
330
  return result;
344
331
  }
345
-
346
- function flattenMenus(menus: readonly MenuNode[]): MenuNode[] {
347
- return menus.flatMap((menu) => [menu, ...flattenMenus(menu.children || [])]);
348
- }
@@ -291,6 +291,8 @@ export interface ModuleManifest {
291
291
  export type ModuleFactory = () => ModuleManifest;
292
292
 
293
293
  export interface ModuleImplementationBindings {
294
+ unavailableApiRoutes?: ReadonlySet<string>;
295
+ unavailableTools?: ReadonlySet<string>;
294
296
  adminRoutes?: readonly string[];
295
297
  apiRoutes?: readonly string[];
296
298
  tasks?: readonly string[];
@@ -52,3 +52,27 @@ function assertSameMenuShell(left: MenuNode, right: MenuNode): void {
52
52
  }
53
53
  }
54
54
  }
55
+
56
+ export function validateMenuRoutes(
57
+ menus: readonly MenuNode[],
58
+ routes: readonly ModuleManifest["adminRoutes"][number][],
59
+ ): void {
60
+ const byPath = new Map(routes.map((route) => [route.path, route]));
61
+ for (const menu of menus) {
62
+ if (!menu.path) continue;
63
+ const route = byPath.get(menu.path);
64
+ if (!route)
65
+ throw new Error(`菜单 ${menu.key} 缺少 Admin Route:${menu.path}`);
66
+ if (
67
+ route.directAccess !== "admin-admission" &&
68
+ (route.permissionKey !== menu.permissionKey ||
69
+ route.featureKey !== menu.featureKey)
70
+ ) {
71
+ throw new Error(`菜单 ${menu.key} 与 Admin Route Guard 不一致`);
72
+ }
73
+ }
74
+ }
75
+
76
+ export function flattenMenus(menus: readonly MenuNode[]): MenuNode[] {
77
+ return menus.flatMap((menu) => [menu, ...flattenMenus(menu.children || [])]);
78
+ }
@@ -129,7 +129,7 @@ export const systemAdminRoutes: ModuleManifest["adminRoutes"] = [
129
129
  "system.diagnostics",
130
130
  ),
131
131
  // @windy-module system.audit end
132
- // @windy-module system.agent begin
132
+ // @windy-module system.agent-ui begin
133
133
  route(
134
134
  "system.agent-tools",
135
135
  "/admin/system/agent-tools",
@@ -186,7 +186,7 @@ export const systemAdminRoutes: ModuleManifest["adminRoutes"] = [
186
186
  "system.agent-workbench.use",
187
187
  "system.agent-workbench",
188
188
  ),
189
- // @windy-module system.agent end
189
+ // @windy-module system.agent-ui end
190
190
  // @windy-module system.operations begin
191
191
  route(
192
192
  "system.ops",
@@ -1,6 +1,6 @@
1
1
  import type { AdminUiManifest } from "./admin-ui-manifest.js";
2
2
  import { systemAdminRoutes } from "./system-admin-routes.js";
3
- import { systemModuleDefinitions } from "./system-module-catalog.js";
3
+ import { systemModuleDefinitions } from "./system-module-definitions.js";
4
4
 
5
5
  const definitions = [
6
6
  ["system", ["system.feature", "system.ui-components"]],
@@ -30,10 +30,14 @@ const definitions = [
30
30
  // @windy-module system.storage begin
31
31
  ["system.storage", []],
32
32
  // @windy-module system.storage end
33
+ // @windy-module system.media-runtime begin
34
+ ["system.media-runtime", []],
35
+ // @windy-module system.media-runtime end
33
36
  // @windy-module system.agent begin
34
37
  [
35
38
  "system.agent",
36
39
  [
40
+ // @windy-module system.agent-ui begin
37
41
  "system.agent-tools",
38
42
  "system.agent-debug",
39
43
  "system.agent-skill",
@@ -41,6 +45,7 @@ const definitions = [
41
45
  "system.agent-session",
42
46
  "system.ai-runtime",
43
47
  "system.agent-workflow",
48
+ // @windy-module system.agent-ui end
44
49
  ],
45
50
  ],
46
51
  // @windy-module system.agent end
@@ -22,15 +22,6 @@ export function systemAiControlPlaneBindings(): ApiPermissionBinding[] {
22
22
  );
23
23
  const read = [
24
24
  "/api/agent/workflows/readiness",
25
- "/api/internal/ai/artifacts",
26
- "/api/document/runs/:runId/events",
27
- "/api/document/runs/:runId/result",
28
- "/api/speech/runs/:runId/events",
29
- "/api/speech/runs/:runId/result",
30
- "/api/speech/runs/:runId/artifact",
31
- "/api/embeddings/runs/:runId/events",
32
- "/api/embeddings/runs/:runId/result",
33
- "/api/internal/embeddings/runs/:runId/artifacts/:itemId",
34
25
  "/api/agent/runs/:runId/events",
35
26
  "/api/agent/runs/:runId/result",
36
27
  ].map((path) =>
@@ -44,13 +35,6 @@ export function systemAiControlPlaneBindings(): ApiPermissionBinding[] {
44
35
  ),
45
36
  );
46
37
  const execute = [
47
- "/api/document/runs",
48
- "/api/document/runs/:runId/cancel",
49
- "/api/speech/runs",
50
- "/api/speech/runs/:runId/cancel",
51
- "/api/embeddings",
52
- "/api/embeddings/runs",
53
- "/api/embeddings/runs/:runId/cancel",
54
38
  "/api/agent/runs",
55
39
  "/api/agent/runs/:runId/cancel",
56
40
  "/api/agent/runs/:runId/attach",
@@ -3,6 +3,9 @@ import { binding } from "./system-api-binding.js";
3
3
  // @windy-module system.agent begin
4
4
  import { systemAiControlPlaneBindings } from "./system-ai-api-bindings.js";
5
5
  // @windy-module system.agent end
6
+ // @windy-module system.media-runtime begin
7
+ import { systemMediaApiBindings } from "./system-media-api-bindings.js";
8
+ // @windy-module system.media-runtime end
6
9
 
7
10
  /**
8
11
  * 不走资源 CRUD 的平台入口仍必须进入 Manifest。
@@ -17,13 +20,18 @@ export function systemControlPlaneApiPermissionBindings(): ApiPermissionBinding[
17
20
  // @windy-module system.agent begin
18
21
  ...systemAiControlPlaneBindings(),
19
22
  // @windy-module system.agent end
23
+ // @windy-module system.media-runtime begin
24
+ ...systemMediaApiBindings(),
25
+ // @windy-module system.media-runtime end
20
26
  // @windy-module system.license begin
27
+ // 基础运行投影不依赖管理权限或管理 Feature;Handler 仍强制 user 登录态。
21
28
  binding(
22
29
  "GET",
23
30
  "/api/license/runtime",
24
31
  "system.license.read",
25
- "system.license",
32
+ undefined,
26
33
  "data.read",
34
+ true,
27
35
  ),
28
36
  binding(
29
37
  "POST",
@@ -15,6 +15,13 @@ import { systemControlPlaneApiPermissionBindings } from "./system-api-control-pl
15
15
  export function systemApiPermissionBindings(): ApiPermissionBinding[] {
16
16
  return [
17
17
  // @windy-module system.audit begin
18
+ binding(
19
+ "GET",
20
+ "/api/system/diagnostics",
21
+ "system.diagnostics.read",
22
+ "system.diagnostics",
23
+ "diagnostic.read",
24
+ ),
18
25
  binding(
19
26
  "GET",
20
27
  "/api/system/diagnostics/:diagnosticId",
@@ -25,5 +25,26 @@ export function watermarkApiPermissionBindings(): ApiPermissionBinding[] {
25
25
  "system.watermark",
26
26
  "config.update",
27
27
  ),
28
+ binding(
29
+ "GET",
30
+ "/api/system/settings/watermark/yaml",
31
+ "system.watermark.read",
32
+ "system.watermark",
33
+ "data.read",
34
+ ),
35
+ binding(
36
+ "POST",
37
+ "/api/system/settings/watermark/yaml/preview",
38
+ "system.watermark.manage",
39
+ "system.watermark",
40
+ "data.read",
41
+ ),
42
+ binding(
43
+ "POST",
44
+ "/api/system/settings/watermark/yaml",
45
+ "system.watermark.manage",
46
+ "system.watermark",
47
+ "config.update",
48
+ ),
28
49
  ];
29
50
  }
@@ -85,6 +85,9 @@ export const systemAuditActions: ModuleManifest["auditActions"] = [
85
85
  "file.upload.abort",
86
86
  "file.download",
87
87
  // @windy-module system.storage end
88
+ // @windy-module system.media-runtime begin
89
+ "agent.operation.execute",
90
+ // @windy-module system.media-runtime end
88
91
  // @windy-module system.agent begin
89
92
  {
90
93
  key: "system.agent-tools.read",
@@ -113,7 +116,6 @@ export const systemAuditActions: ModuleManifest["auditActions"] = [
113
116
  },
114
117
  "agent.mcp.access",
115
118
  "agent.tool.execute",
116
- "agent.operation.execute",
117
119
  {
118
120
  key: "agent.session.read",
119
121
  label: "读取 Agent 长期会话",
@@ -13,8 +13,8 @@ const standardAndAdvanced = ["standard", "advanced"].map(
13
13
  export const systemFeatures: ModuleManifest["features"] = [
14
14
  feature(
15
15
  "system.admin",
16
- "Windy 管理面",
17
- "平台管理员、运维与授权审计人员使用的控制面准入能力。",
16
+ "Windy 管理面板",
17
+ "允许平台管理员、运维人员和获授权的审计人员访问 Windy 管理面板。",
18
18
  ),
19
19
  feature("system.runtime", "运行状态", "健康、就绪与指标等部署运行状态入口。"),
20
20
  feature(
@@ -93,7 +93,11 @@ export const systemFeatures: ModuleManifest["features"] = [
93
93
  "审计日志",
94
94
  "记录关键配置、权限拒绝与业务操作,支持安全追溯。",
95
95
  ),
96
- feature("system.diagnostics", "错误诊断", "按诊断编号查询脱敏失败索引。"),
96
+ feature(
97
+ "system.diagnostics",
98
+ "错误诊断",
99
+ "分页查看脱敏失败日志,也可按诊断编号定位记录。",
100
+ ),
97
101
  // @windy-module system.audit end
98
102
  // @windy-module system.storage begin
99
103
  feature(
@@ -102,6 +106,20 @@ export const systemFeatures: ModuleManifest["features"] = [
102
106
  "受控文件上传、续传、下载、过期和底层对象生命周期。",
103
107
  ),
104
108
  // @windy-module system.storage end
109
+ // @windy-module system.media-runtime begin
110
+ feature(
111
+ "system.ai-artifact",
112
+ "AI 文件引用",
113
+ "受控运行时读取已授权的输入文件。",
114
+ ),
115
+ feature(
116
+ "system.document",
117
+ "文档识别与 OCR",
118
+ "控制文档识别与 OCR运行时和业务入口。",
119
+ ),
120
+ feature("system.speech", "语音处理", "控制语音处理运行时和业务入口。"),
121
+ feature("system.embedding", "向量嵌入", "控制向量嵌入运行时和业务入口。"),
122
+ // @windy-module system.media-runtime end
105
123
  // @windy-module system.agent begin
106
124
  feature(
107
125
  "system.agent",
@@ -0,0 +1,97 @@
1
+ import type { ApiPermissionBinding } from "@southwind-ai/shared";
2
+ import { binding } from "./system-api-binding.js";
3
+
4
+ export function systemMediaApiBindings(): ApiPermissionBinding[] {
5
+ return [
6
+ binding(
7
+ "GET",
8
+ "/api/internal/ai/artifacts",
9
+ "system.ai-artifact.read",
10
+ "system.ai-artifact",
11
+ "data.read",
12
+ true,
13
+ ),
14
+ ...outputArtifactBindings(),
15
+ ...runtimeBindings(
16
+ "system.document",
17
+ ["/api/document/runs/:runId/events", "/api/document/runs/:runId/result"],
18
+ ["/api/document/runs", "/api/document/runs/:runId/cancel"],
19
+ ),
20
+ ...runtimeBindings(
21
+ "system.speech",
22
+ [
23
+ "/api/speech/runs/:runId/events",
24
+ "/api/speech/runs/:runId/result",
25
+ "/api/speech/runs/:runId/artifact",
26
+ ],
27
+ ["/api/speech/runs", "/api/speech/runs/:runId/cancel"],
28
+ ),
29
+ ...runtimeBindings(
30
+ "system.embedding",
31
+ [
32
+ "/api/embeddings/runs/:runId/events",
33
+ "/api/embeddings/runs/:runId/result",
34
+ "/api/internal/embeddings/runs/:runId/artifacts/:itemId",
35
+ ],
36
+ [
37
+ "/api/embeddings",
38
+ "/api/embeddings/runs",
39
+ "/api/embeddings/runs/:runId/cancel",
40
+ ],
41
+ ),
42
+ ];
43
+ }
44
+
45
+ function runtimeBindings(
46
+ feature: "system.document" | "system.speech" | "system.embedding",
47
+ read: readonly string[],
48
+ execute: readonly string[],
49
+ ): ApiPermissionBinding[] {
50
+ return [
51
+ ...read.map((path) =>
52
+ binding(
53
+ "GET",
54
+ path,
55
+ `${feature}.read`,
56
+ feature,
57
+ "data.read",
58
+ path.startsWith("/api/internal/"),
59
+ ),
60
+ ),
61
+ ...execute.map((path) =>
62
+ binding(
63
+ "POST",
64
+ path,
65
+ `${feature}.read`,
66
+ feature,
67
+ "agent.operation.execute",
68
+ false,
69
+ ),
70
+ ),
71
+ ];
72
+ }
73
+
74
+ function outputArtifactBindings(): ApiPermissionBinding[] {
75
+ const root = "/api/internal/ai/output-artifacts";
76
+ const routes = [
77
+ ["GET", ""],
78
+ ["GET", "/health/ready"],
79
+ ["POST", "/scopes/:scope/grants/:generation/accept"],
80
+ ["POST", "/scopes/:scope/artifacts"],
81
+ ["PUT", "/scopes/:scope/artifacts/:artifactId/parts/:partNumber"],
82
+ ["POST", "/scopes/:scope/artifacts/:artifactId/complete"],
83
+ ["POST", "/scopes/:scope/seal"],
84
+ ["DELETE", "/scopes/:scope/open"],
85
+ ["DELETE", "/scopes/:scope"],
86
+ ] as const;
87
+ return routes.map(([method, suffix]) =>
88
+ binding(
89
+ method,
90
+ root + suffix,
91
+ "system.ai-artifact.read",
92
+ "system.ai-artifact",
93
+ method === "GET" ? "data.read" : "agent.operation.execute",
94
+ true,
95
+ ),
96
+ );
97
+ }
@@ -15,6 +15,8 @@ export function selectSystemAuditActions(
15
15
  const key = auditActionKey(action);
16
16
  if (name === "system.identity")
17
17
  return key === "system.user-directory.query";
18
+ if (key === "agent.operation.execute")
19
+ return name === "system.media-runtime";
18
20
  if (name === "system.agent") return agentActions.has(key);
19
21
  return (
20
22
  name === "system" &&