@dxos/plugin-routine 0.10.0 → 0.11.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 (320) hide show
  1. package/PLUGIN.mdl +18 -13
  2. package/dist/lib/RoutinePlugin.mjs +2 -0
  3. package/dist/lib/RoutinePlugin.node.mjs +894 -0
  4. package/dist/lib/RoutinePlugin.node.mjs.map +1 -0
  5. package/dist/lib/RoutinePlugin.workerd.mjs +20 -0
  6. package/dist/lib/RoutinePlugin.workerd.mjs.map +1 -0
  7. package/dist/lib/capabilities/node.mjs +12 -0
  8. package/dist/lib/capabilities/node.mjs.map +1 -0
  9. package/dist/lib/capabilities.mjs +14 -0
  10. package/dist/lib/capabilities.mjs.map +1 -0
  11. package/dist/lib/chunk-RoutineArticle.mjs +79 -0
  12. package/dist/lib/chunk-RoutineArticle.mjs.map +1 -0
  13. package/dist/lib/chunk-RoutineCompanion.mjs +192 -0
  14. package/dist/lib/chunk-RoutineCompanion.mjs.map +1 -0
  15. package/dist/lib/chunk-RoutinePlugin.mjs +38 -0
  16. package/dist/lib/chunk-RoutinePlugin.mjs.map +1 -0
  17. package/dist/lib/chunk-RoutineSettings.mjs +50 -0
  18. package/dist/lib/chunk-RoutineSettings.mjs.map +1 -0
  19. package/dist/lib/chunk-RoutineTraceCompanion.mjs +208 -0
  20. package/dist/lib/chunk-RoutineTraceCompanion.mjs.map +1 -0
  21. package/dist/lib/chunk-SkillArticle.mjs +28 -0
  22. package/dist/lib/chunk-SkillArticle.mjs.map +1 -0
  23. package/dist/lib/chunk-app-graph-builder.mjs +71 -0
  24. package/dist/lib/chunk-app-graph-builder.mjs.map +1 -0
  25. package/dist/lib/chunk-create-object.mjs +23 -0
  26. package/dist/lib/chunk-create-object.mjs.map +1 -0
  27. package/dist/lib/chunk-create-routine.mjs +34 -0
  28. package/dist/lib/chunk-create-routine.mjs.map +1 -0
  29. package/dist/lib/chunk-create-trigger-from-template.mjs +48 -0
  30. package/dist/lib/chunk-create-trigger-from-template.mjs.map +1 -0
  31. package/dist/lib/chunk-layer-specs.mjs +179 -0
  32. package/dist/lib/chunk-layer-specs.mjs.map +1 -0
  33. package/dist/lib/{neutral/chunk-HLO4LYXT.mjs → chunk-meta.mjs} +19 -27
  34. package/dist/lib/chunk-meta.mjs.map +1 -0
  35. package/dist/lib/chunk-operation-handler.mjs +11 -0
  36. package/dist/lib/chunk-operation-handler.mjs.map +1 -0
  37. package/dist/lib/chunk-paths.mjs +11 -0
  38. package/dist/lib/chunk-paths.mjs.map +1 -0
  39. package/dist/lib/chunk-react-surface.mjs +64 -0
  40. package/dist/lib/chunk-react-surface.mjs.map +1 -0
  41. package/dist/lib/chunk-registry-sync.mjs +104 -0
  42. package/dist/lib/chunk-registry-sync.mjs.map +1 -0
  43. package/dist/lib/chunk-run-routine.mjs +57 -0
  44. package/dist/lib/chunk-run-routine.mjs.map +1 -0
  45. package/dist/lib/chunk-templates.mjs +37 -0
  46. package/dist/lib/chunk-templates.mjs.map +1 -0
  47. package/dist/lib/chunk-trigger-runtime-controller.mjs +73 -0
  48. package/dist/lib/chunk-trigger-runtime-controller.mjs.map +1 -0
  49. package/dist/lib/chunk-types.mjs +149 -0
  50. package/dist/lib/chunk-types.mjs.map +1 -0
  51. package/dist/lib/chunk-util.mjs +142 -0
  52. package/dist/lib/chunk-util.mjs.map +1 -0
  53. package/dist/lib/components.mjs +1645 -0
  54. package/dist/lib/components.mjs.map +1 -0
  55. package/dist/lib/containers.mjs +11 -0
  56. package/dist/lib/containers.mjs.map +1 -0
  57. package/dist/lib/hooks.mjs +37 -0
  58. package/dist/lib/hooks.mjs.map +1 -0
  59. package/dist/lib/index.mjs +5 -0
  60. package/dist/lib/meta.mjs +2 -0
  61. package/dist/lib/operations.mjs +7 -0
  62. package/dist/lib/operations.mjs.map +1 -0
  63. package/dist/lib/plugin.mjs +9 -0
  64. package/dist/lib/plugin.mjs.map +1 -0
  65. package/dist/lib/testing.mjs +2 -0
  66. package/dist/lib/translations.mjs +110 -0
  67. package/dist/lib/translations.mjs.map +1 -0
  68. package/dist/lib/types.mjs +2 -0
  69. package/dist/types/src/RoutinePlugin.d.ts.map +1 -1
  70. package/dist/types/src/RoutinePlugin.node.d.ts.map +1 -1
  71. package/dist/types/src/RoutinePlugin.workerd.d.ts.map +1 -1
  72. package/dist/types/src/capabilities/app-graph-builder.d.ts +1 -1
  73. package/dist/types/src/capabilities/create-object.d.ts +1 -1
  74. package/dist/types/src/capabilities/index.d.ts +0 -1
  75. package/dist/types/src/capabilities/index.d.ts.map +1 -1
  76. package/dist/types/src/capabilities/layer-specs.d.ts +1 -1
  77. package/dist/types/src/capabilities/operation-handler.d.ts +1 -1
  78. package/dist/types/src/capabilities/react-surface.d.ts +1 -1
  79. package/dist/types/src/capabilities/react-surface.d.ts.map +1 -1
  80. package/dist/types/src/capabilities/registry-sync.d.ts +1 -1
  81. package/dist/types/src/capabilities/templates.d.ts +1 -1
  82. package/dist/types/src/capabilities/trigger-runtime-controller.d.ts +1 -1
  83. package/dist/types/src/commands/trigger/create/{queue.d.ts → feed.d.ts} +2 -2
  84. package/dist/types/src/commands/trigger/create/feed.d.ts.map +1 -0
  85. package/dist/types/src/commands/trigger/update/{queue.d.ts → feed.d.ts} +2 -2
  86. package/dist/types/src/commands/trigger/update/feed.d.ts.map +1 -0
  87. package/dist/types/src/commands/trigger/util.d.ts +1 -1
  88. package/dist/types/src/commands/trigger/util.d.ts.map +1 -1
  89. package/dist/types/src/components/InstructionsEditor/InstructionsEditor.d.ts +7 -5
  90. package/dist/types/src/components/InstructionsEditor/InstructionsEditor.d.ts.map +1 -1
  91. package/dist/types/src/components/InstructionsEditor/InstructionsEditor.stories.d.ts +3 -3
  92. package/dist/types/src/components/InstructionsEditor/InstructionsEditor.stories.d.ts.map +1 -1
  93. package/dist/types/src/components/RoutineCard/RoutineCard.d.ts +9 -0
  94. package/dist/types/src/components/RoutineCard/RoutineCard.d.ts.map +1 -0
  95. package/dist/types/src/components/RoutineCard/RoutineCard.stories.d.ts +21 -0
  96. package/dist/types/src/components/RoutineCard/RoutineCard.stories.d.ts.map +1 -0
  97. package/dist/types/src/components/RoutineCard/index.d.ts +2 -0
  98. package/dist/types/src/components/RoutineCard/index.d.ts.map +1 -0
  99. package/dist/types/src/components/RoutineForm/RoutineForm.d.ts +7 -2
  100. package/dist/types/src/components/RoutineForm/RoutineForm.d.ts.map +1 -1
  101. package/dist/types/src/components/Schedule/Schedule.d.ts +2 -26
  102. package/dist/types/src/components/Schedule/Schedule.d.ts.map +1 -1
  103. package/dist/types/src/components/Schedule/days.d.ts +24 -0
  104. package/dist/types/src/components/Schedule/days.d.ts.map +1 -0
  105. package/dist/types/src/components/Schedule/describe-schedule.d.ts +3 -0
  106. package/dist/types/src/components/Schedule/describe-schedule.d.ts.map +1 -0
  107. package/dist/types/src/components/Schedule/index.d.ts +2 -0
  108. package/dist/types/src/components/Schedule/index.d.ts.map +1 -1
  109. package/dist/types/src/components/TemplateEditor/TemplateEditor.d.ts +1 -1
  110. package/dist/types/src/components/TemplateEditor/TemplateEditor.d.ts.map +1 -1
  111. package/dist/types/src/components/TriggerEditor/TriggerEditor.d.ts +1 -2
  112. package/dist/types/src/components/TriggerEditor/TriggerEditor.d.ts.map +1 -1
  113. package/dist/types/src/components/TriggerEditor/TriggerKindSelector.d.ts +5 -2
  114. package/dist/types/src/components/TriggerEditor/TriggerKindSelector.d.ts.map +1 -1
  115. package/dist/types/src/components/TriggerEditor/trigger-kind-icon.d.ts +5 -0
  116. package/dist/types/src/components/TriggerEditor/trigger-kind-icon.d.ts.map +1 -0
  117. package/dist/types/src/components/index.d.ts +1 -1
  118. package/dist/types/src/components/index.d.ts.map +1 -1
  119. package/dist/types/src/containers/RoutineArticle/RoutineArticle.d.ts +5 -10
  120. package/dist/types/src/containers/RoutineArticle/RoutineArticle.d.ts.map +1 -1
  121. package/dist/types/src/containers/RoutineArticle/RoutineArticle.stories.d.ts +6 -2
  122. package/dist/types/src/containers/RoutineArticle/RoutineArticle.stories.d.ts.map +1 -1
  123. package/dist/types/src/containers/RoutineCompanion/RoutineCompanion.d.ts +4 -12
  124. package/dist/types/src/containers/RoutineCompanion/RoutineCompanion.d.ts.map +1 -1
  125. package/dist/types/src/containers/RoutineCompanion/RoutineCompanion.stories.d.ts.map +1 -1
  126. package/dist/types/src/containers/RoutineSettings/RoutineSettings.d.ts +4 -8
  127. package/dist/types/src/containers/RoutineSettings/RoutineSettings.d.ts.map +1 -1
  128. package/dist/types/src/containers/RoutineTraceCompanion/RoutineTraceCompanion.d.ts +5 -3
  129. package/dist/types/src/containers/RoutineTraceCompanion/RoutineTraceCompanion.d.ts.map +1 -1
  130. package/dist/types/src/containers/RoutineTraceCompanion/RoutineTraceCompanion.stories.d.ts.map +1 -1
  131. package/dist/types/src/containers/RoutineTraceCompanion/useRoutineRuns.d.ts +1 -1
  132. package/dist/types/src/containers/RoutineTraceCompanion/useRoutineRuns.d.ts.map +1 -1
  133. package/dist/types/src/containers/SkillArticle/SkillArticle.d.ts +4 -1
  134. package/dist/types/src/containers/SkillArticle/SkillArticle.d.ts.map +1 -1
  135. package/dist/types/src/hooks/useTriggerRuntimeControls.d.ts +1 -1
  136. package/dist/types/src/hooks/useTriggerRuntimeControls.d.ts.map +1 -1
  137. package/dist/types/src/index.d.ts +1 -0
  138. package/dist/types/src/index.d.ts.map +1 -1
  139. package/dist/types/src/operations/run-routine.d.ts.map +1 -1
  140. package/dist/types/src/operations/run-routine.test.d.ts +2 -0
  141. package/dist/types/src/operations/run-routine.test.d.ts.map +1 -0
  142. package/dist/types/src/paths.d.ts.map +1 -1
  143. package/dist/types/src/templates/index.d.ts +1 -1
  144. package/dist/types/src/templates/index.d.ts.map +1 -1
  145. package/dist/types/src/testing/test-functions.d.ts +30 -6
  146. package/dist/types/src/testing/test-functions.d.ts.map +1 -1
  147. package/dist/types/src/translations.d.ts.map +1 -1
  148. package/dist/types/src/types/RoutineCapabilities.d.ts +9 -3
  149. package/dist/types/src/types/RoutineCapabilities.d.ts.map +1 -1
  150. package/dist/types/src/types/RoutineOperation.d.ts +2 -3
  151. package/dist/types/src/types/RoutineOperation.d.ts.map +1 -1
  152. package/dist/types/src/types/index.d.ts +0 -1
  153. package/dist/types/src/types/index.d.ts.map +1 -1
  154. package/dist/types/src/util/index.d.ts +1 -0
  155. package/dist/types/src/util/index.d.ts.map +1 -1
  156. package/dist/types/src/util/routines-for-object.d.ts +6 -3
  157. package/dist/types/src/util/routines-for-object.d.ts.map +1 -1
  158. package/dist/types/src/util/wire.d.ts +21 -0
  159. package/dist/types/src/util/wire.d.ts.map +1 -0
  160. package/dist/types/src/util/wire.test.d.ts +2 -0
  161. package/dist/types/src/util/wire.test.d.ts.map +1 -0
  162. package/dist/types/tsconfig.tsbuildinfo +1 -1
  163. package/dx.config.ts +3 -2
  164. package/package.json +73 -71
  165. package/src/RoutinePlugin.node.ts +1 -2
  166. package/src/RoutinePlugin.tsx +2 -4
  167. package/src/RoutinePlugin.workerd.ts +1 -2
  168. package/src/capabilities/app-graph-builder.ts +9 -7
  169. package/src/capabilities/create-object.ts +2 -2
  170. package/src/capabilities/index.ts +0 -1
  171. package/src/capabilities/layer-specs.ts +78 -12
  172. package/src/capabilities/{react-surface.tsx → react-surface.ts} +18 -22
  173. package/src/capabilities/trigger-runtime-controller.test.ts +12 -18
  174. package/src/capabilities/trigger-runtime-controller.ts +22 -25
  175. package/src/commands/trigger/create/{queue.ts → feed.ts} +1 -1
  176. package/src/commands/trigger/create/index.ts +2 -2
  177. package/src/commands/trigger/update/{queue.ts → feed.ts} +1 -1
  178. package/src/commands/trigger/update/index.ts +2 -2
  179. package/src/commands/trigger/util.ts +1 -2
  180. package/src/components/InstructionsEditor/InstructionsEditor.stories.tsx +7 -6
  181. package/src/components/InstructionsEditor/InstructionsEditor.tsx +31 -19
  182. package/src/components/RoutineCard/RoutineCard.stories.tsx +95 -0
  183. package/src/components/RoutineCard/RoutineCard.tsx +60 -0
  184. package/src/components/{MasterDetail → RoutineCard}/index.ts +1 -1
  185. package/src/components/RoutineForm/RoutineForm.tsx +60 -52
  186. package/src/components/Schedule/Schedule.stories.tsx +1 -1
  187. package/src/components/Schedule/Schedule.tsx +4 -73
  188. package/src/components/Schedule/days.ts +18 -0
  189. package/src/components/Schedule/describe-schedule.ts +64 -0
  190. package/src/components/Schedule/index.ts +2 -0
  191. package/src/components/TemplateEditor/TemplateEditor.stories.tsx +1 -1
  192. package/src/components/TemplateEditor/TemplateForm.tsx +1 -1
  193. package/src/components/TriggerEditor/TriggerEditor.stories.tsx +3 -3
  194. package/src/components/TriggerEditor/TriggerEditor.tsx +79 -66
  195. package/src/components/TriggerEditor/TriggerKindSelector.tsx +4 -30
  196. package/src/components/TriggerEditor/trigger-kind-icon.ts +38 -0
  197. package/src/components/index.ts +1 -1
  198. package/src/containers/RoutineArticle/RoutineArticle.stories.tsx +78 -19
  199. package/src/containers/RoutineArticle/RoutineArticle.tsx +8 -4
  200. package/src/containers/RoutineCompanion/RoutineCompanion.stories.tsx +5 -4
  201. package/src/containers/RoutineCompanion/RoutineCompanion.tsx +11 -7
  202. package/src/containers/RoutineSettings/RoutineSettings.tsx +22 -33
  203. package/src/containers/RoutineTraceCompanion/RoutineTraceCompanion.stories.tsx +6 -5
  204. package/src/containers/RoutineTraceCompanion/RoutineTraceCompanion.tsx +3 -1
  205. package/src/containers/RoutineTraceCompanion/useRoutineRuns.ts +3 -5
  206. package/src/containers/SkillArticle/SkillArticle.tsx +2 -0
  207. package/src/hooks/useTriggerRuntimeControls.ts +2 -2
  208. package/src/index.ts +1 -0
  209. package/src/operations/create-routine.ts +1 -1
  210. package/src/operations/create-trigger-from-template.ts +2 -2
  211. package/src/operations/run-routine.test.ts +150 -0
  212. package/src/operations/run-routine.ts +18 -2
  213. package/src/paths.ts +5 -5
  214. package/src/templates/index.ts +5 -3
  215. package/src/translations.ts +5 -6
  216. package/src/types/RoutineCapabilities.ts +10 -4
  217. package/src/types/RoutineOperation.ts +7 -6
  218. package/src/types/index.ts +0 -1
  219. package/src/util/index.ts +1 -0
  220. package/src/util/routines-for-object.test.ts +37 -5
  221. package/src/util/routines-for-object.ts +33 -8
  222. package/src/util/wire.test.ts +77 -0
  223. package/src/util/wire.ts +76 -0
  224. package/dist/lib/neutral/RoutineArticle-UNTMV4CC.mjs +0 -95
  225. package/dist/lib/neutral/RoutineArticle-UNTMV4CC.mjs.map +0 -7
  226. package/dist/lib/neutral/RoutineCompanion-ZZ6WMY7I.mjs +0 -249
  227. package/dist/lib/neutral/RoutineCompanion-ZZ6WMY7I.mjs.map +0 -7
  228. package/dist/lib/neutral/RoutinePlugin.mjs +0 -10
  229. package/dist/lib/neutral/RoutinePlugin.mjs.map +0 -7
  230. package/dist/lib/neutral/RoutinePlugin.node.mjs +0 -1133
  231. package/dist/lib/neutral/RoutinePlugin.node.mjs.map +0 -7
  232. package/dist/lib/neutral/RoutinePlugin.workerd.mjs +0 -36
  233. package/dist/lib/neutral/RoutinePlugin.workerd.mjs.map +0 -7
  234. package/dist/lib/neutral/RoutineSettings-ZJOM4F3S.mjs +0 -48
  235. package/dist/lib/neutral/RoutineSettings-ZJOM4F3S.mjs.map +0 -7
  236. package/dist/lib/neutral/RoutineTraceCompanion-5U6R7LJE.mjs +0 -236
  237. package/dist/lib/neutral/RoutineTraceCompanion-5U6R7LJE.mjs.map +0 -7
  238. package/dist/lib/neutral/SkillArticle-WWDNKW2Z.mjs +0 -27
  239. package/dist/lib/neutral/SkillArticle-WWDNKW2Z.mjs.map +0 -7
  240. package/dist/lib/neutral/app-graph-builder-FALWLZTI.mjs +0 -90
  241. package/dist/lib/neutral/app-graph-builder-FALWLZTI.mjs.map +0 -7
  242. package/dist/lib/neutral/capabilities/index.mjs +0 -25
  243. package/dist/lib/neutral/capabilities/index.mjs.map +0 -7
  244. package/dist/lib/neutral/capabilities/node.mjs +0 -19
  245. package/dist/lib/neutral/capabilities/node.mjs.map +0 -7
  246. package/dist/lib/neutral/chunk-674LDIUJ.mjs +0 -9
  247. package/dist/lib/neutral/chunk-674LDIUJ.mjs.map +0 -7
  248. package/dist/lib/neutral/chunk-HLO4LYXT.mjs.map +0 -7
  249. package/dist/lib/neutral/chunk-J5LGTIGS.mjs +0 -10
  250. package/dist/lib/neutral/chunk-J5LGTIGS.mjs.map +0 -7
  251. package/dist/lib/neutral/chunk-P3TDQKOO.mjs +0 -8
  252. package/dist/lib/neutral/chunk-P3TDQKOO.mjs.map +0 -7
  253. package/dist/lib/neutral/chunk-R7J2MU2M.mjs +0 -263
  254. package/dist/lib/neutral/chunk-R7J2MU2M.mjs.map +0 -7
  255. package/dist/lib/neutral/chunk-WLNL77C7.mjs +0 -14
  256. package/dist/lib/neutral/chunk-WLNL77C7.mjs.map +0 -7
  257. package/dist/lib/neutral/chunk-YGWSAKLD.mjs +0 -65
  258. package/dist/lib/neutral/chunk-YGWSAKLD.mjs.map +0 -7
  259. package/dist/lib/neutral/components/index.mjs +0 -1921
  260. package/dist/lib/neutral/components/index.mjs.map +0 -7
  261. package/dist/lib/neutral/containers/index.mjs +0 -17
  262. package/dist/lib/neutral/containers/index.mjs.map +0 -7
  263. package/dist/lib/neutral/create-object-V23KVDMJ.mjs +0 -25
  264. package/dist/lib/neutral/create-object-V23KVDMJ.mjs.map +0 -7
  265. package/dist/lib/neutral/create-routine-6QBY6TWF.mjs +0 -38
  266. package/dist/lib/neutral/create-routine-6QBY6TWF.mjs.map +0 -7
  267. package/dist/lib/neutral/create-trigger-from-template-U3KNS77V.mjs +0 -70
  268. package/dist/lib/neutral/create-trigger-from-template-U3KNS77V.mjs.map +0 -7
  269. package/dist/lib/neutral/hooks/index.mjs +0 -47
  270. package/dist/lib/neutral/hooks/index.mjs.map +0 -7
  271. package/dist/lib/neutral/index.mjs +0 -27
  272. package/dist/lib/neutral/index.mjs.map +0 -7
  273. package/dist/lib/neutral/layer-specs-2TWJU5HI.mjs +0 -135
  274. package/dist/lib/neutral/layer-specs-2TWJU5HI.mjs.map +0 -7
  275. package/dist/lib/neutral/meta.json +0 -1
  276. package/dist/lib/neutral/meta.mjs +0 -8
  277. package/dist/lib/neutral/meta.mjs.map +0 -7
  278. package/dist/lib/neutral/navigation-resolver-KQIWUH6F.mjs +0 -18
  279. package/dist/lib/neutral/navigation-resolver-KQIWUH6F.mjs.map +0 -7
  280. package/dist/lib/neutral/operation-handler-QKLJSDCQ.mjs +0 -13
  281. package/dist/lib/neutral/operation-handler-QKLJSDCQ.mjs.map +0 -7
  282. package/dist/lib/neutral/operations/index.mjs +0 -8
  283. package/dist/lib/neutral/operations/index.mjs.map +0 -7
  284. package/dist/lib/neutral/plugin.mjs +0 -16
  285. package/dist/lib/neutral/plugin.mjs.map +0 -7
  286. package/dist/lib/neutral/react-surface-GMO7I7YE.mjs +0 -67
  287. package/dist/lib/neutral/react-surface-GMO7I7YE.mjs.map +0 -7
  288. package/dist/lib/neutral/registry-sync-DYPOC7ZG.mjs +0 -86
  289. package/dist/lib/neutral/registry-sync-DYPOC7ZG.mjs.map +0 -7
  290. package/dist/lib/neutral/run-routine-AEWO6SYD.mjs +0 -37
  291. package/dist/lib/neutral/run-routine-AEWO6SYD.mjs.map +0 -7
  292. package/dist/lib/neutral/templates-IIUCEBAX.mjs +0 -49
  293. package/dist/lib/neutral/templates-IIUCEBAX.mjs.map +0 -7
  294. package/dist/lib/neutral/testing.mjs +0 -8
  295. package/dist/lib/neutral/testing.mjs.map +0 -7
  296. package/dist/lib/neutral/translations.mjs +0 -115
  297. package/dist/lib/neutral/translations.mjs.map +0 -7
  298. package/dist/lib/neutral/trigger-runtime-controller-WIDDFGQT.mjs +0 -77
  299. package/dist/lib/neutral/trigger-runtime-controller-WIDDFGQT.mjs.map +0 -7
  300. package/dist/lib/neutral/types/index.mjs +0 -17
  301. package/dist/lib/neutral/types/index.mjs.map +0 -7
  302. package/dist/types/src/capabilities/navigation-resolver.d.ts +0 -5
  303. package/dist/types/src/capabilities/navigation-resolver.d.ts.map +0 -1
  304. package/dist/types/src/commands/trigger/create/queue.d.ts.map +0 -1
  305. package/dist/types/src/commands/trigger/update/queue.d.ts.map +0 -1
  306. package/dist/types/src/components/MasterDetail/MasterDetail.d.ts +0 -51
  307. package/dist/types/src/components/MasterDetail/MasterDetail.d.ts.map +0 -1
  308. package/dist/types/src/components/MasterDetail/MasterDetail.stories.d.ts +0 -16
  309. package/dist/types/src/components/MasterDetail/MasterDetail.stories.d.ts.map +0 -1
  310. package/dist/types/src/components/MasterDetail/index.d.ts +0 -2
  311. package/dist/types/src/components/MasterDetail/index.d.ts.map +0 -1
  312. package/dist/types/src/types/Routine.d.ts +0 -55
  313. package/dist/types/src/types/Routine.d.ts.map +0 -1
  314. package/dist/types/src/types/Routine.test.d.ts +0 -2
  315. package/dist/types/src/types/Routine.test.d.ts.map +0 -1
  316. package/src/capabilities/navigation-resolver.ts +0 -21
  317. package/src/components/MasterDetail/MasterDetail.stories.tsx +0 -100
  318. package/src/components/MasterDetail/MasterDetail.tsx +0 -175
  319. package/src/types/Routine.test.ts +0 -51
  320. package/src/types/Routine.ts +0 -144
@@ -0,0 +1 @@
1
+ {"version":3,"file":"components.mjs","names":[],"sources":["../../src/components/InstructionsEditor/InstructionsEditor.tsx","../../src/components/Schedule/cron.ts","../../src/components/Schedule/types.ts","../../src/components/Schedule/days.ts","../../src/components/Schedule/describe-schedule.ts","../../src/components/Schedule/Schedule.tsx","../../src/components/TriggerEditor/trigger-kind-icon.ts","../../src/components/TriggerEditor/TriggerKindSelector.tsx","../../src/components/TriggerEditor/TriggerEditor.tsx","../../src/components/RoutineForm/RoutineForm.tsx","../../src/components/CreateRoutinePanel/CreateRoutinePanel.tsx","../../src/components/RoutineCard/RoutineCard.tsx","../../src/components/TemplateEditor/extensions/handlebars-extension.ts","../../src/components/TemplateEditor/extensions/xml-extension.ts","../../src/components/TemplateEditor/TemplateEditor.tsx"],"sourcesContent":["//\n// Copyright 2026 DXOS.org\n//\n\nimport * as Option from 'effect/Option';\nimport React, { useCallback, useMemo } from 'react';\n\nimport { Instructions, Skill } from '@dxos/compute';\nimport { type Database, Entity, Obj, Type } from '@dxos/echo';\nimport { HiddenAnnotation } from '@dxos/echo/Annotation';\nimport { Form } from '@dxos/react-ui-form';\n\nconst INSTRUCTIONS_SCHEMA = Type.getSchema(Instructions.Instructions);\n\n// Owned-routine action fields surfaced by default — the prompt text and the agent's `skills`. The\n// context `objects` are excluded here so a routine form doesn't show a second, divergent list beside\n// its owning subject; a surface that owns the context concern (e.g. a project's Context section)\n// opts in via `fields`.\nconst DEFAULT_FIELDS: readonly string[] = ['text', 'skills'];\n\nexport type InstructionsEditorProps = {\n db?: Database.Database; // TODO(burdon): Should not be optional if instructions are not.\n instructions: Instructions.Instructions;\n readonly?: boolean;\n /** Instructions schema fields rendered AND written back; others are left untouched. */\n fields?: readonly string[];\n};\n\n/**\n * Sub-form: edits the owned Instructions in place — by default its `text` (Markdown) and `skills`,\n * both fields of the Instructions schema. A bare Form.Root + FieldSet (no Viewport) keeps these\n * fields left-aligned with the sibling general/action forms; only the rendered fields are written\n * back so a partial editor never clobbers the rest of the object.\n */\nexport const InstructionsEditor = ({\n db: dbProp,\n instructions,\n readonly,\n fields = DEFAULT_FIELDS,\n}: InstructionsEditorProps) => {\n // A draft routine is not yet attached to a database, so fall back to the explicit `db` for ref queries.\n const db = dbProp ?? Obj.getDatabase(instructions);\n\n const defaultValues = useMemo<Partial<Instructions.Instructions>>(\n () => ({ ...Obj.getSnapshot(instructions) }),\n [instructions],\n );\n\n const fieldSet = useMemo(() => new Set(fields), [fields]);\n const handleValuesChanged = useCallback(\n (values: Partial<Instructions.Instructions>, { isValid }: { isValid: boolean }) => {\n // Skip while invalid (e.g. an empty ref slot just added by the skills array field) so a partial\n // selection isn't persisted; the write lands once the slot is filled.\n if (!isValid) {\n return;\n }\n\n Obj.update(instructions, (instructions) => {\n if (fieldSet.has('text') && values.text) {\n instructions.text = values.text;\n }\n if (fieldSet.has('skills')) {\n instructions.skills = [...(values.skills ?? [])];\n }\n if (fieldSet.has('objects')) {\n instructions.objects = [...(values.objects ?? [])];\n }\n });\n },\n [instructions, fieldSet],\n );\n\n return (\n <Form.Root\n key={instructions.id}\n schema={INSTRUCTIONS_SCHEMA}\n db={db}\n readonly={readonly}\n defaultValues={defaultValues}\n getOptions={getRefOptions}\n onValuesChanged={handleValuesChanged}\n >\n <Form.FieldSet filter={(props) => props.filter((prop) => fieldSet.has(prop.name.toString()))} />\n </Form.Root>\n );\n};\n\n// System objects (e.g. SpaceProperties) carry `HiddenAnnotation` on their type; they are infrastructure,\n// not user content, so they are excluded from the context picker.\nconst isSystemObject = (object: Entity.Any): boolean => {\n if (!Obj.isObject(object)) {\n return false;\n }\n const typeEntity = Obj.getType(object);\n if (!typeEntity) {\n return false;\n }\n\n return HiddenAnnotation.get(Type.getSchema(typeEntity)).pipe(Option.getOrElse(() => false));\n};\n\n// Ref-picker options shared by the routine form's skill and object fields: surface a secondary line\n// per candidate — a Skill's registry key, otherwise the object's typename — and sort by label, so the\n// pickers present refs consistently. Falls back to the type placeholder (then URI) for unlabelled objects,\n// matching the default RefField; system objects are excluded.\nconst getRefOptions = (\n results: Entity.Any[],\n { getTypePlaceholder }: { getTypePlaceholder?: (typename: string) => string } = {},\n): { id: string; label: string; description?: string }[] =>\n results\n .filter((entity) => !isSystemObject(entity))\n .map((entity) => {\n const id = Entity.getURI(entity, { prefer: 'named' });\n const typename = Entity.getTypename(entity);\n const label = Entity.getLabel(entity) ?? (typename ? getTypePlaceholder?.(typename) : undefined) ?? id;\n const description = Obj.instanceOf(Skill.Skill, entity) ? Obj.getMeta(entity).key : typename;\n return { id, label, description };\n })\n .sort((left, right) => left.label.localeCompare(right.label));\n","//\n// Copyright 2025 DXOS.org\n//\n\nimport cronstrue from 'cronstrue';\n\nimport type { ScheduleValue } from './Schedule';\nimport type { CronSpecType, DayOfWeek } from './types';\n\nconst DOW_MAP: Record<DayOfWeek, number> = {\n sun: 0,\n mon: 1,\n tue: 2,\n wed: 3,\n thu: 4,\n fri: 5,\n sat: 6,\n};\n\n/**\n * Derives a 5-field standard cron expression from a decomposed CronSpec value.\n * Fields: minute hour day-of-month month day-of-week\n */\nexport const toCron = (value: CronSpecType): string => {\n switch (value.frequency) {\n case 'minutely':\n return `*/${value.interval} * * * *`;\n\n case 'hourly':\n return `${value.minute} */${value.interval} * * *`;\n\n case 'daily':\n return `${value.minute} ${value.hour} * * *`;\n\n case 'weekly': {\n const dow = value.daysOfWeek.length > 0 ? value.daysOfWeek.map((d) => DOW_MAP[d]).join(',') : '*';\n return `${value.minute} ${value.hour} * * ${dow}`;\n }\n\n case 'monthly': {\n const dom = value.daysOfMonth.length > 0 ? value.daysOfMonth.join(',') : '*';\n return `${value.minute} ${value.hour} ${dom} * *`;\n }\n\n case 'custom':\n return value.cronExpression || '* * * * *';\n }\n};\n\nconst DOW_REVERSE: Partial<Record<string, DayOfWeek>> = {\n '0': 'sun',\n '1': 'mon',\n '2': 'tue',\n '3': 'wed',\n '4': 'thu',\n '5': 'fri',\n '6': 'sat',\n // Both 0 and 7 represent Sunday in standard cron.\n '7': 'sun',\n};\n\n/** Returns a non-negative integer if the token is a valid decimal integer, otherwise undefined. */\nconst parseUInt = (token: string): number | undefined => (/^\\d+$/.test(token) ? Number(token) : undefined);\n\n/** Returns the parsed integer if it falls within [min, max], otherwise undefined. */\nconst parseBoundedUInt = (token: string, min: number, max: number): number | undefined => {\n const value = parseUInt(token);\n return value !== undefined && value >= min && value <= max ? value : undefined;\n};\n\n/**\n * Parses a 5-field cron expression into a CronSpec value.\n * Recognises common patterns (minutely, hourly, daily, weekly, monthly) and falls back to `custom`.\n */\nexport const fromCron = (cron: string): CronSpecType => {\n const parts = cron.trim().split(/\\s+/);\n if (parts.length !== 5) {\n return { frequency: 'custom', cronExpression: cron };\n }\n\n const [minute, hour, dom, month, dow] = parts;\n\n // minutely: */N * * * *\n const minutelyMatch = minute.match(/^\\*\\/(\\d+)$/);\n if (minutelyMatch && hour === '*' && dom === '*' && month === '*' && dow === '*') {\n return { frequency: 'minutely', interval: parseInt(minutelyMatch[1]) };\n }\n\n // hourly: M */N * * *\n const hourlyMatch = hour.match(/^\\*\\/(\\d+)$/);\n const minuteNum = parseBoundedUInt(minute, 0, 59);\n if (hourlyMatch && dom === '*' && month === '*' && dow === '*' && minuteNum !== undefined) {\n return { frequency: 'hourly', interval: parseInt(hourlyMatch[1]), minute: minuteNum };\n }\n\n const hourNum = parseBoundedUInt(hour, 0, 23);\n if (minuteNum === undefined || hourNum === undefined) {\n return { frequency: 'custom', cronExpression: cron };\n }\n\n // weekly: M H * * DOW[,DOW...] (numeric DOW values only; all tokens must be valid)\n if (dom === '*' && month === '*' && dow !== '*') {\n const tokens = dow.split(',');\n const days = tokens.map((d) => DOW_REVERSE[d]).filter((d): d is DayOfWeek => d != null);\n if (days.length === tokens.length && days.length > 0) {\n return { frequency: 'weekly', daysOfWeek: days, hour: hourNum, minute: minuteNum };\n }\n return { frequency: 'custom', cronExpression: cron };\n }\n\n // monthly: M H DOM[,DOM...] * * (all tokens must be valid integers in 1-31)\n if (dom !== '*' && month === '*' && dow === '*') {\n const tokens = dom.split(',');\n const days = tokens.map((d) => parseBoundedUInt(d, 1, 31)).filter((d): d is number => d !== undefined);\n if (days.length === tokens.length && days.length > 0) {\n return { frequency: 'monthly', daysOfMonth: days, hour: hourNum, minute: minuteNum };\n }\n return { frequency: 'custom', cronExpression: cron };\n }\n\n // daily: M H * * *\n if (dom === '*' && month === '*' && dow === '*') {\n return { frequency: 'daily', hour: hourNum, minute: minuteNum };\n }\n\n return { frequency: 'custom', cronExpression: cron };\n};\n\n/**\n * Returns a human-readable description of a cron expression, e.g. \"At 09:00 on Monday\".\n * Falls back to the raw expression string on parse errors.\n */\nexport const describeCron = (cron: string): string => {\n try {\n return cronstrue.toString(cron, { throwExceptionOnParseError: true });\n } catch {\n return cron;\n }\n};\n\n//\n// Schedule <-> cron bridge.\n//\n\nconst pad = (value: number): string => String(value).padStart(2, '0');\n\nconst splitTime = (time: string): { hour: number; minute: number } => {\n const [hour, minute] = time.split(':').map(Number);\n return { hour: Number.isFinite(hour) ? hour : 0, minute: Number.isFinite(minute) ? minute : 0 };\n};\n\nconst joinTime = (hour: number, minute: number): string => `${pad(hour)}:${pad(minute)}`;\n\n/**\n * Convert a recurring {@link ScheduleValue} to a 5-field cron expression. The one-time `once` kind has no\n * cron representation and returns `undefined`.\n */\nexport const scheduleToCron = (value: ScheduleValue): string | undefined => {\n switch (value.kind) {\n case 'hourly':\n return toCron({ frequency: 'hourly', interval: 1, minute: value.minute });\n case 'daily': {\n const { hour, minute } = splitTime(value.time);\n return toCron({ frequency: 'daily', hour, minute });\n }\n case 'weekly': {\n const { hour, minute } = splitTime(value.time);\n return toCron({ frequency: 'weekly', daysOfWeek: value.days, hour, minute });\n }\n case 'monthly': {\n const { hour, minute } = splitTime(value.time);\n return toCron({ frequency: 'monthly', daysOfMonth: [value.day], hour, minute });\n }\n case 'custom':\n return toCron({ frequency: 'custom', cronExpression: value.cron });\n }\n};\n\n//\n// Minimum-interval constraint.\n//\n\nconst MINUTE_SECONDS = 60;\nconst HOUR_SECONDS = 60 * 60;\nconst DAY_SECONDS = 24 * HOUR_SECONDS;\n\n/** Upper bound for a Schedule minimum interval: a 5-field cron's coarsest single-field cadence is hourly. */\nexport const MAX_MIN_INTERVAL_SECONDS = HOUR_SECONDS;\n\n/** Parses a comma-separated list of bounded integers; returns undefined if any token is not a plain integer in range. */\nconst parseList = (field: string, min: number, max: number): number[] | undefined => {\n const tokens = field.split(',');\n const values = tokens\n .map((token) => parseBoundedUInt(token, min, max))\n .filter((value): value is number => value !== undefined);\n return values.length === tokens.length && values.length > 0 ? values : undefined;\n};\n\n/**\n * Smallest cyclic gap between values in a field whose domain wraps at `span` (60 for minutes, 24 for hours),\n * or Infinity for a single value. The wrap is required so e.g. minutes `0,59` register their 1-unit gap\n * (59 → 0 of the next cycle), not just the 59-unit one.\n */\nconst minGap = (values: number[], span: number): number => {\n const sorted = [...new Set(values)].sort((lhs, rhs) => lhs - rhs);\n if (sorted.length <= 1) {\n return Number.POSITIVE_INFINITY;\n }\n let gap = Number.POSITIVE_INFINITY;\n for (let index = 0; index < sorted.length; index++) {\n const next = index === sorted.length - 1 ? sorted[0] + span : sorted[index + 1];\n gap = Math.min(gap, next - sorted[index]);\n }\n return gap;\n};\n\n/** Step value of a `*\\/N`, `M/N`, or `A-B/N` field (the cadence between fires), or undefined if not a step form. */\nconst parseStep = (field: string, max: number): number | undefined => {\n const match = field.match(/^(?:\\*|\\d+(?:-\\d+)?)\\/(\\d+)$/);\n return match ? parseBoundedUInt(match[1], 1, max) : undefined;\n};\n\n/** Minimum seconds between fires implied by a cron's hour field (independent of minute granularity). */\nconst hourIntervalSeconds = (hour: string): number => {\n const step = parseStep(hour, 23);\n if (step !== undefined) {\n return step * HOUR_SECONDS;\n }\n if (hour === '*') {\n return HOUR_SECONDS;\n }\n const hours = parseList(hour, 0, 23);\n if (hours) {\n return hours.length > 1 ? minGap(hours, 24) * HOUR_SECONDS : DAY_SECONDS;\n }\n return Number.POSITIVE_INFINITY;\n};\n\n/**\n * Best-effort minimum seconds between consecutive fires of a 5-field cron expression. Recognises the patterns\n * a too-frequent schedule can take (`* …`, `*\\/N …`, explicit minute/hour lists); returns Infinity for\n * expressions it cannot analyse, so unrecognised crons are treated as satisfying any minimum.\n */\nexport const cronIntervalSeconds = (cron: string): number => {\n const parts = cron.trim().split(/\\s+/);\n if (parts.length !== 5) {\n return Number.POSITIVE_INFINITY;\n }\n\n const [minute, hour] = parts;\n const minuteStep = parseStep(minute, 59);\n if (minuteStep !== undefined) {\n return minuteStep * MINUTE_SECONDS;\n }\n if (minute === '*') {\n return MINUTE_SECONDS;\n }\n\n const minutes = parseList(minute, 0, 59);\n if (minutes) {\n const minuteGap = minutes.length > 1 ? minGap(minutes, 60) * MINUTE_SECONDS : Number.POSITIVE_INFINITY;\n return Math.min(minuteGap, hourIntervalSeconds(hour));\n }\n\n return Number.POSITIVE_INFINITY;\n};\n\n/**\n * Rewrites a cron's minute field so it fires no more often than `minIntervalSeconds`. Used to clamp a custom\n * expression; leaves non-5-field expressions untouched since their cadence cannot be reasoned about.\n */\nconst clampCronMinute = (cron: string, minIntervalSeconds: number): string => {\n const parts = cron.trim().split(/\\s+/);\n if (parts.length !== 5) {\n return cron;\n }\n const stepMinutes = Math.ceil(minIntervalSeconds / MINUTE_SECONDS);\n // A step that spans the whole minute range fires only at minute 0; express that as the hourly cadence.\n parts[0] = stepMinutes >= 60 ? '0' : `*/${stepMinutes}`;\n return parts.join(' ');\n};\n\n/** Minimum seconds between fires for a recurring {@link ScheduleValue}. */\nexport const scheduleIntervalSeconds = (value: ScheduleValue): number => {\n switch (value.kind) {\n case 'hourly':\n return HOUR_SECONDS;\n case 'daily':\n return DAY_SECONDS;\n // Consecutive selected weekdays sit one day apart at closest.\n case 'weekly':\n return DAY_SECONDS;\n // Approximate the shortest month to stay conservative.\n case 'monthly':\n return 28 * DAY_SECONDS;\n case 'custom':\n return cronIntervalSeconds(value.cron);\n }\n};\n\n/**\n * Coerces a schedule so it fires no more often than `minIntervalSeconds`. Only `custom` expressions can exceed\n * the limit (structured kinds are hourly or slower), so clamping rewrites the cron's minute field; all other\n * values pass through unchanged.\n */\nexport const clampSchedule = (value: ScheduleValue, minIntervalSeconds: number): ScheduleValue => {\n if (value.kind !== 'custom' || cronIntervalSeconds(value.cron) >= minIntervalSeconds) {\n return value;\n }\n return { kind: 'custom', cron: clampCronMinute(value.cron, minIntervalSeconds) };\n};\n\n/**\n * Convert a cron expression to a recurring {@link ScheduleValue}. Patterns that Schedule cannot model exactly\n * (sub-hourly intervals, multi-day months, etc.) fall back to the `custom` kind preserving the raw expression.\n */\nexport const cronToSchedule = (cron: string): ScheduleValue => {\n const spec = fromCron(cron);\n switch (spec.frequency) {\n case 'hourly':\n // Schedule's hourly runs at the top of every hour; a non-unit interval can't be modelled.\n return spec.interval === 1 ? { kind: 'hourly', minute: spec.minute } : { kind: 'custom', cron };\n case 'daily':\n return { kind: 'daily', time: joinTime(spec.hour, spec.minute) };\n case 'weekly':\n return { kind: 'weekly', time: joinTime(spec.hour, spec.minute), days: [...spec.daysOfWeek] };\n case 'monthly':\n // Schedule models a single day-of-month; multiple days remain custom.\n return spec.daysOfMonth.length === 1\n ? { kind: 'monthly', day: spec.daysOfMonth[0], time: joinTime(spec.hour, spec.minute) }\n : { kind: 'custom', cron };\n case 'minutely':\n case 'custom':\n default:\n return { kind: 'custom', cron };\n }\n};\n","//\n// Copyright 2025 DXOS.org\n//\n\nimport * as Schema from 'effect/Schema';\n\nexport const MinutelySpec = Schema.Struct({\n frequency: Schema.Literal('minutely').annotations({ title: 'Frequency' }),\n interval: Schema.Number.pipe(Schema.int(), Schema.between(1, 59)).annotations({\n title: 'Every (minutes)',\n description: '1–59',\n }),\n});\n\nexport const HourlySpec = Schema.Struct({\n frequency: Schema.Literal('hourly').annotations({ title: 'Frequency' }),\n interval: Schema.Number.pipe(Schema.int(), Schema.between(1, 23)).annotations({\n title: 'Every (hours)',\n description: '1–23',\n }),\n minute: Schema.Number.pipe(Schema.int(), Schema.between(0, 59)).annotations({\n title: 'At minute',\n description: '0–59',\n }),\n});\n\nexport const DailySpec = Schema.Struct({\n frequency: Schema.Literal('daily').annotations({ title: 'Frequency' }),\n hour: Schema.Number.pipe(Schema.int(), Schema.between(0, 23)).annotations({\n title: 'Hour',\n description: '0–23',\n }),\n minute: Schema.Number.pipe(Schema.int(), Schema.between(0, 59)).annotations({\n title: 'Minute',\n description: '0–59',\n }),\n});\n\n// Named day-of-week literals for UX clarity; cron.ts maps them to numeric DOW values.\nexport const DayOfWeek = Schema.Literal('sun', 'mon', 'tue', 'wed', 'thu', 'fri', 'sat');\nexport type DayOfWeek = Schema.Schema.Type<typeof DayOfWeek>;\n\nexport const WeeklySpec = Schema.Struct({\n frequency: Schema.Literal('weekly').annotations({ title: 'Frequency' }),\n daysOfWeek: Schema.Array(DayOfWeek.annotations({ title: 'Day' })).annotations({ title: 'Days of week' }),\n hour: Schema.Number.pipe(Schema.int(), Schema.between(0, 23)).annotations({\n title: 'Hour',\n description: '0–23',\n }),\n minute: Schema.Number.pipe(Schema.int(), Schema.between(0, 59)).annotations({\n title: 'Minute',\n description: '0–59',\n }),\n});\n\nexport const MonthlySpec = Schema.Struct({\n frequency: Schema.Literal('monthly').annotations({ title: 'Frequency' }),\n daysOfMonth: Schema.Array(\n Schema.Number.pipe(Schema.int(), Schema.between(1, 31)).annotations({ title: 'Day' }),\n ).annotations({\n title: 'Days of month',\n }),\n hour: Schema.Number.pipe(Schema.int(), Schema.between(0, 23)).annotations({\n title: 'Hour',\n description: '0–23',\n }),\n minute: Schema.Number.pipe(Schema.int(), Schema.between(0, 59)).annotations({\n title: 'Minute',\n description: '0–59',\n }),\n});\n\nexport const CustomSpec = Schema.Struct({\n frequency: Schema.Literal('custom').annotations({ title: 'Frequency' }),\n cronExpression: Schema.String.annotations({\n title: 'Cron expression',\n description: 'e.g. 0 9 * * MON-FRI',\n }),\n});\n\nexport const CronSpec = Schema.Union(\n MinutelySpec,\n HourlySpec,\n DailySpec,\n WeeklySpec,\n MonthlySpec,\n CustomSpec,\n).annotations({ title: '' });\n\nexport type CronSpecType = Schema.Schema.Type<typeof CronSpec>;\nexport type Frequency = CronSpecType['frequency'];\n\nexport const FrequencyDefaults: { [K in Frequency]: Extract<CronSpecType, { frequency: K }> } = {\n minutely: {\n frequency: 'minutely',\n interval: 15,\n },\n hourly: {\n frequency: 'hourly',\n interval: 1,\n minute: 0,\n },\n daily: {\n frequency: 'daily',\n hour: 9,\n minute: 0,\n },\n weekly: {\n frequency: 'weekly',\n daysOfWeek: ['mon'],\n hour: 9,\n minute: 0,\n },\n monthly: {\n frequency: 'monthly',\n daysOfMonth: [1],\n hour: 9,\n minute: 0,\n },\n custom: {\n frequency: 'custom',\n cronExpression: '* * * * *',\n },\n};\n","//\n// Copyright 2025 DXOS.org\n//\n\n// Shared by `Schedule.tsx` and `describe-schedule.ts`: a value import between those two would close a\n// runtime cycle, and react-refresh only fast-refreshes a module whose exports are all components.\n\nexport const Days = [\n { value: 'mon', label: 'Mon' },\n { value: 'tue', label: 'Tue' },\n { value: 'wed', label: 'Wed' },\n { value: 'thu', label: 'Thu' },\n { value: 'fri', label: 'Fri' },\n { value: 'sat', label: 'Sat' },\n { value: 'sun', label: 'Sun' },\n] as const;\n\nexport type Day = (typeof Days)[number]['value'];\n","//\n// Copyright 2026 DXOS.org\n//\n\nimport { describeCron } from './cron';\nimport { type Day, Days } from './days';\nimport { type ScheduleValue } from './Schedule';\n\n// Kept out of `Schedule.tsx`: react-refresh only fast-refreshes a module whose\n// exports are all components, so values exported beside them force a full page reload on\n// every edit.\n\n/** Human-readable summary of the schedule, suitable for the header. */\n// TODO(wittjosiah): Just use cronstrue for all cases?\nconst DAY_NAMES: Record<Day, string> = {\n mon: 'Monday',\n tue: 'Tuesday',\n wed: 'Wednesday',\n thu: 'Thursday',\n fri: 'Friday',\n sat: 'Saturday',\n sun: 'Sunday',\n};\n\nconst withZone = (text: string, timezone?: string): string => (timezone ? `${text} ${timezone}` : text);\n\nconst formatTime = (time: string): string => {\n const [h, m] = time.split(':').map(Number);\n if (Number.isNaN(h) || Number.isNaN(m)) {\n return time;\n }\n\n const period = h < 12 ? 'AM' : 'PM';\n const hour = h % 12 === 0 ? 12 : h % 12;\n return `${hour}:${String(m).padStart(2, '0')} ${period}`;\n};\n\nexport const describeSchedule = (value: ScheduleValue, timezone?: string): string => {\n switch (value.kind) {\n // case 'once':\n // return value.date\n // ? `Runs once at ${formatTime(value.date.slice(11))} on ${value.date.slice(0, 10)}`\n // : 'Runs once';\n case 'hourly':\n return `Runs every hour at minute ${value.minute}`;\n case 'daily':\n return withZone(`Runs every day at ${formatTime(value.time)}`, timezone);\n case 'weekly': {\n const days =\n value.days.length === 0\n ? 'no days'\n : value.days.length === 1\n ? DAY_NAMES[value.days[0]]\n : Days.filter((d) => value.days.includes(d.value))\n .map((d) => d.label)\n .join(', ');\n return withZone(`Runs every ${days} at ${formatTime(value.time)}`, timezone);\n }\n case 'monthly':\n return withZone(`Runs monthly on day ${value.day} at ${formatTime(value.time)}`, timezone);\n case 'custom':\n return withZone(describeCron(value.cron), timezone);\n }\n};\n","//\n// Copyright 2026 DXOS.org\n//\n\nimport React, { type PropsWithChildren, createContext, forwardRef, useCallback, useContext, useState } from 'react';\n\nimport { invariant } from '@dxos/invariant';\nimport {\n Input,\n ThemedClassName,\n ToggleGroup,\n ToggleGroupItem,\n composable,\n composableProps,\n useTranslation,\n} from '@dxos/react-ui';\nimport { mx } from '@dxos/ui-theme';\n\nimport { meta } from '#meta';\n\nimport { MAX_MIN_INTERVAL_SECONDS, clampSchedule, fromCron, scheduleIntervalSeconds, scheduleToCron } from './cron';\nimport { type Day, Days } from './days';\nimport { describeSchedule } from './describe-schedule';\n\n//\n// Value model.\n//\n\nexport const ScheduleKinds = [\n // TODO(burdon): Once cannot be converted to a cron expression.\n // 'once',\n 'hourly',\n 'daily',\n 'weekly',\n 'monthly',\n 'custom',\n] as const;\n\nexport type ScheduleKind = (typeof ScheduleKinds)[number];\n\nconst isScheduleKind = (value: string): value is ScheduleKind => (ScheduleKinds as readonly string[]).includes(value);\n\n/** Discriminated schedule value. Times are `HH:mm` (24h); `once.date` is `YYYY-MM-DDTHH:mm`. */\nexport type ScheduleValue =\n // | { kind: 'once'; date?: string }\n | { kind: 'hourly'; minute: number }\n | { kind: 'daily'; time: string }\n | { kind: 'weekly'; time: string; days: Day[] }\n | { kind: 'monthly'; day: number; time: string }\n | { kind: 'custom'; cron: string };\n\nconst DEFAULT_TIME = '08:00';\n\n/** Default minimum interval: a schedule may fire at most once every 60s (the finest 5-field cron granularity). */\nconst DEFAULT_MIN_INTERVAL_SECONDS = 60;\n\n/** Clamp a requested minimum interval to the achievable range; a 5-field cron cannot fire more often than every minute or require slower than hourly. */\nconst normalizeMinInterval = (minInterval: number): number => {\n // Guard non-finite input (NaN/Infinity) so the clamp can't yield NaN and produce a `*/NaN` cron.\n const finite = Number.isFinite(minInterval) ? minInterval : DEFAULT_MIN_INTERVAL_SECONDS;\n return Math.min(MAX_MIN_INTERVAL_SECONDS, Math.max(DEFAULT_MIN_INTERVAL_SECONDS, Math.round(finite)));\n};\n\nconst KIND_LABEL_KEYS: Record<ScheduleKind, string> = {\n // once: 'schedule.kind.once.label',\n hourly: 'schedule.kind.hourly.label',\n daily: 'schedule.kind.daily.label',\n weekly: 'schedule.kind.weekly.label',\n monthly: 'schedule.kind.monthly.label',\n custom: 'schedule.kind.custom.label',\n};\n\nconst DEFAULTS: { [K in ScheduleKind]: Extract<ScheduleValue, { kind: K }> } = {\n // once: {\n // kind: 'once',\n // },\n hourly: {\n kind: 'hourly',\n minute: 0,\n },\n daily: {\n kind: 'daily',\n time: DEFAULT_TIME,\n },\n weekly: {\n kind: 'weekly',\n time: DEFAULT_TIME,\n days: ['mon'],\n },\n monthly: {\n kind: 'monthly',\n day: 1,\n time: DEFAULT_TIME,\n },\n custom: {\n kind: 'custom',\n cron: '0 9 * * 1',\n },\n};\n\nconst pad = (value: number): string => String(value).padStart(2, '0');\n\n/**\n * Switch to a different kind, preserving the current schedule's timing by routing it through its cron\n * representation. The cron is the canonical carrier: each target kind reuses whatever fields it supports\n * (time-of-day, weekdays, day-of-month), falling back to the kind's default for fields the cron doesn't hold.\n */\nconst switchKind = (current: ScheduleValue, kind: ScheduleKind): ScheduleValue => {\n const cron = scheduleToCron(current);\n const spec = cron ? fromCron(cron) : undefined;\n // Fall back to the shared default time (not midnight) when the source cron carries no time-of-day,\n // so switching from e.g. hourly to daily lands on a sensible hour rather than 00:00.\n const [defaultHour, defaultMinute] = DEFAULT_TIME.split(':').map(Number);\n const minute = spec && 'minute' in spec ? spec.minute : defaultMinute;\n const hour = spec && 'hour' in spec ? spec.hour : defaultHour;\n const time = `${pad(hour)}:${pad(minute)}`;\n switch (kind) {\n case 'hourly':\n return { kind: 'hourly', minute };\n case 'daily':\n return { kind: 'daily', time };\n case 'weekly':\n return { kind: 'weekly', time, days: spec?.frequency === 'weekly' ? [...spec.daysOfWeek] : DEFAULTS.weekly.days };\n case 'monthly':\n return { kind: 'monthly', time, day: spec?.frequency === 'monthly' ? spec.daysOfMonth[0] : DEFAULTS.monthly.day };\n case 'custom':\n return { kind: 'custom', cron: cron ?? DEFAULTS.custom.cron };\n }\n};\n\n//\n// Context\n//\n\ntype ScheduleContextValue = {\n value: ScheduleValue;\n onValueChange: (value: ScheduleValue) => void;\n kinds: readonly ScheduleKind[];\n /** Minimum seconds between fires; schedules that would fire more often are clamped. */\n minInterval: number;\n timezone?: string;\n};\n\nconst ScheduleContext = createContext<ScheduleContextValue | null>(null);\n\nconst useScheduleContext = (consumer: string): ScheduleContextValue => {\n const context = useContext(ScheduleContext);\n invariant(context, `${consumer} must be used within Schedule.Root`);\n return context;\n};\n\n//\n// Root\n//\n\nexport type ScheduleRootProps = ThemedClassName<\n PropsWithChildren<{\n value?: ScheduleValue;\n /** Timezone abbreviation shown in the summary, e.g. `EDT`. */\n timezone?: string;\n defaultValue?: ScheduleValue;\n onValueChange?: (value: ScheduleValue) => void;\n /** Restrict which frequency tabs are offered (defaults to all kinds). */\n kinds?: readonly ScheduleKind[];\n /**\n * Minimum seconds between fires (default 60). Schedules that would fire more often are clamped, and\n * frequency tabs that cannot satisfy it are hidden. Capped to the hourly cadence a 5-field cron can model.\n */\n minInterval?: number;\n }>\n>;\n\n/**\n * Schedule picker root: provides the shared {@link Column} grid (all rows align to the same gutters)\n * and the schedule state context. Controllable via `value`/`onValueChange`, or self-managing via\n * `defaultValue`. Compose with `Schedule.Header`, `Schedule.Kind`, `Schedule.Body`, `Schedule.Description`.\n */\nconst ScheduleRoot = composable<HTMLDivElement, ScheduleRootProps>(\n (\n {\n children,\n value: valueProp,\n defaultValue,\n onValueChange,\n kinds = ScheduleKinds,\n minInterval: minIntervalProp = DEFAULT_MIN_INTERVAL_SECONDS,\n timezone,\n ...props\n },\n forwardedRef,\n ) => {\n const minInterval = normalizeMinInterval(minIntervalProp);\n const [value, setValue] = useState<ScheduleValue>(() =>\n clampSchedule(valueProp ?? defaultValue ?? DEFAULTS.weekly, minInterval),\n );\n\n const handleValueChange = useCallback(\n (next: ScheduleValue) => {\n const clamped = clampSchedule(next, minInterval);\n setValue(clamped);\n onValueChange?.(clamped);\n },\n [onValueChange, minInterval],\n );\n\n // Only offer frequencies whose cadence can satisfy the minimum; `custom` always stays (it is clamped on edit).\n const allowedKinds = kinds.filter(\n (kind) => kind === 'custom' || scheduleIntervalSeconds(DEFAULTS[kind]) >= minInterval,\n );\n\n return (\n <ScheduleContext.Provider\n value={{\n value: clampSchedule(valueProp ?? value, minInterval),\n onValueChange: handleValueChange,\n kinds: allowedKinds,\n minInterval,\n timezone,\n }}\n >\n <div {...composableProps(props, { classNames: 'flex flex-col gap-y-3' })} ref={forwardedRef}>\n {children}\n </div>\n </ScheduleContext.Provider>\n );\n },\n);\n\nScheduleRoot.displayName = 'Schedule.Root';\n\n//\n// Header\n//\n\nexport type ScheduleHeaderProps = { classNames?: string };\n\n/**\n * Summary row laid out on the shared grid: the icon in the leading gutter (column 1), the schedule\n * description (or `children`) in the center column, and an optional close button in the trailing gutter\n * (column 3).\n */\nconst ScheduleHeader = forwardRef<HTMLDivElement, ScheduleHeaderProps>(({ classNames }, forwardedRef) => {\n const { t } = useTranslation(meta.profile.key);\n const { value, timezone } = useScheduleContext('Schedule.Header');\n return <p className={mx('grow truncate text-description', classNames)}>{describeSchedule(value, timezone)}</p>;\n});\n\nScheduleHeader.displayName = 'Schedule.Header';\n\n//\n// Kind\n//\n\nexport type ScheduleKindProps = ThemedClassName;\n\n/** Segmented frequency tabs (Once / Hourly / Daily / Weekly / Custom). */\nconst ScheduleKindRow = forwardRef<HTMLDivElement, ScheduleKindProps>(({ classNames }, forwardedRef) => {\n const { t } = useTranslation(meta.profile.key);\n const { value, onValueChange, kinds } = useScheduleContext('Schedule.Kind');\n const handleKindChange = useCallback(\n (kind: string) => {\n if (isScheduleKind(kind)) {\n onValueChange(switchKind(value, kind));\n }\n },\n [value, onValueChange],\n );\n\n return (\n <ToggleGroup\n classNames='overflow-x-auto scrollbar-none'\n type='single'\n value={value.kind}\n onValueChange={handleKindChange}\n >\n {kinds.map((kind) => (\n <ToggleGroupItem key={kind} value={kind}>\n {t(KIND_LABEL_KEYS[kind])}\n </ToggleGroupItem>\n ))}\n </ToggleGroup>\n );\n});\n\nScheduleKindRow.displayName = 'Schedule.Kind';\n\n//\n// Body\n//\n\nexport type ScheduleBodyProps = ThemedClassName;\n\n/** Per-kind editor for the active frequency. Rendered as a 3-column row so editors can use the gutters. */\nconst ScheduleBody = forwardRef<HTMLDivElement, ScheduleBodyProps>(({ classNames }, forwardedRef) => {\n const { value, onValueChange } = useScheduleContext('Schedule.Body');\n return <ScheduleEditor value={value} onChange={onValueChange} />;\n});\n\nScheduleBody.displayName = 'Schedule.Body';\n\n//\n// Namespace.\n//\n\nexport const Schedule = {\n Root: ScheduleRoot,\n Header: ScheduleHeader,\n Kind: ScheduleKindRow,\n Body: ScheduleBody,\n};\n\n//\n// Per-kind editors.\n//\n\nconst Field = ({ label, children, classNames }: ThemedClassName<PropsWithChildren<{ label: string }>>) => (\n <label className={mx('flex items-center gap-2 shrink-0', classNames)}>\n <span className='text-sm'>{label}</span>\n {children}\n </label>\n);\n\nconst ScheduleEditor = ({ value, onChange }: { value: ScheduleValue; onChange: (value: ScheduleValue) => void }) => {\n const { t } = useTranslation(meta.profile.key);\n switch (value.kind) {\n // case 'once':\n // `Input.Root` renders no DOM, so the trigger (column 1) and the field (center) become direct children\n // of `Schedule.Body`'s row while still sharing the input context that wires the picker to the field.\n // return (\n // <Input.Root>\n // <div>\n // <Field label={t('schedule.at.label')}>\n // <Input.DateTime\n // classNames='min-w-0 overflow-hidden'\n // hourCycle={12}\n // value={value.date ?? ''}\n // onValueChange={(date) => onChange({ kind: 'once', date: date || undefined })}\n // />\n // <Input.TriggerIcon />\n // </Field>\n // </div>\n // </Input.Root>\n // );\n\n case 'hourly':\n return (\n <Field label={t('schedule.minute.label')}>\n <Input.Root>\n <Input.TextInput\n type='number'\n min={0}\n max={59}\n step={1}\n classNames='w-15'\n value={String(value.minute)}\n onChange={(event) => {\n const minute = Math.min(59, Math.max(0, Math.round(Number(event.target.value) || 0)));\n onChange({ kind: 'hourly', minute });\n }}\n />\n </Input.Root>\n </Field>\n );\n\n case 'daily':\n return (\n <Field label={t('schedule.at.label')}>\n <Input.Root>\n <Input.Time hourCycle={12} value={value.time} onValueChange={(time) => onChange({ kind: 'daily', time })} />\n </Input.Root>\n </Field>\n );\n\n case 'weekly':\n return (\n <div className='@container dx-inline-size-container min-w-0 flex justify-between items-center gap-2 overflow-x-auto scrollbar-none'>\n <Field label={t('schedule.at.label')}>\n <Input.Root>\n <Input.Time hourCycle={12} value={value.time} onValueChange={(time) => onChange({ ...value, time })} />\n </Input.Root>\n </Field>\n <div className='flex shrink-0 items-center gap-2'>\n <span className='shrink-0 text-sm'>{t('schedule.on.label')}</span>\n <div className='grid w-max shrink-0 grid-cols-7 gap-x-2'>\n {Days.map(({ value: day, label }) => {\n const checked = value.days.includes(day);\n return (\n <div key={day} className='flex shrink-0 items-center gap-1'>\n <Input.Root>\n <Input.Checkbox\n checked={checked}\n onCheckedChange={(next) => {\n // Preserve the canonical `Days` order so the summary reads naturally.\n const nextDays = next\n ? Days.map((d) => d.value).filter((d) => d === day || value.days.includes(d))\n : value.days.filter((d) => d !== day);\n // A weekly schedule must keep at least one day; an empty set serializes to `*`\n // (every day), silently broadening execution. Ignore the uncheck in that case.\n onChange({ ...value, days: nextDays.length > 0 ? nextDays : value.days });\n }}\n />\n <Input.Label classNames='hidden @min-[32rem]:inline-block text-xs uppercase'>{label}</Input.Label>\n <Input.Label classNames='inline-block @min-[32rem]:hidden text-xs'>{label.charAt(0)}</Input.Label>\n </Input.Root>\n </div>\n );\n })}\n </div>\n </div>\n </div>\n );\n\n case 'monthly':\n return (\n <div className='flex items-center gap-3'>\n <Field label={t('schedule.day.label')}>\n <Input.Root>\n <Input.TextInput\n type='number'\n min={1}\n max={31}\n step={1}\n classNames='w-15'\n value={String(value.day)}\n onChange={(event) => {\n const day = Math.min(31, Math.max(1, Math.round(Number(event.target.value) || 1)));\n onChange({ ...value, day });\n }}\n />\n </Input.Root>\n </Field>\n <Field label={t('schedule.at.label')}>\n <Input.Root>\n <Input.Time hourCycle={12} value={value.time} onValueChange={(time) => onChange({ ...value, time })} />\n </Input.Root>\n </Field>\n </div>\n );\n\n case 'custom':\n return (\n <Field label={t('schedule.cron.label')}>\n <Input.Root>\n <Input.TextInput\n classNames='w-50 tabular-nums'\n placeholder='0 9 * * MON-FRI'\n value={value.cron}\n onChange={(event) => onChange({ kind: 'custom', cron: event.target.value })}\n />\n </Input.Root>\n </Field>\n );\n }\n};\n\n//\n// Summary.\n//\n","//\n// Copyright 2026 DXOS.org\n//\n\nimport { type TriggerKind, type TriggerKindOption } from './TriggerKindSelector';\n\n// Kept out of `TriggerKindSelector.tsx`: react-refresh only fast-refreshes a module whose\n// exports are all components, so values exported beside them force a full page reload on\n// every edit.\n\n/** Icon for a trigger kind, shared by the picker rows and the selected-variant editor header. */\nexport const OPTIONS: readonly TriggerKindOption[] = [\n {\n kind: 'timer',\n icon: 'ph--clock-countdown--regular',\n },\n {\n kind: 'feed',\n icon: 'ph--cards-three--regular',\n },\n {\n kind: 'subscription',\n icon: 'ph--funnel--regular',\n },\n {\n kind: 'webhook',\n icon: 'ph--webhooks-logo--regular',\n disabled: true,\n },\n {\n kind: 'email',\n icon: 'ph--envelope--regular',\n disabled: true,\n },\n];\n\nexport const getTriggerKindIcon = (kind: TriggerKind): string =>\n OPTIONS.find((option) => option.kind === kind)?.icon ?? 'ph--lightning--regular';\n","//\n// Copyright 2026 DXOS.org\n//\n\nimport React, { useCallback } from 'react';\n\nimport { Icon, useTranslation } from '@dxos/react-ui';\nimport { Listbox } from '@dxos/react-ui-list';\n\nimport { meta } from '#meta';\n\nimport { OPTIONS } from './trigger-kind-icon';\n\n/** Trigger spec kinds surfaced as selectable variants. Matches the discriminants of `Trigger.Spec`. */\nexport type TriggerKind = 'timer' | 'feed' | 'subscription' | 'webhook' | 'email';\n\nexport type TriggerKindOption = {\n kind: TriggerKind;\n icon: string;\n disabled?: boolean;\n};\n\n// Ordered as presented; labels and descriptions are resolved from translations keyed by `kind`.\n\nexport type TriggerKindSelectorProps = {\n onChange: (kind: TriggerKind) => void;\n};\n\n/**\n * Single-select list of pluggable trigger variants (Schedule / Feed / Query / Webhook / Email): each row\n * shows an icon, title and description. Built on {@link Listbox} (role=listbox/option, arrow-key navigation);\n * selecting a row emits its kind. Selection is transient — the parent swaps in the variant editor on change.\n */\nexport const TriggerKindSelector = ({ onChange }: TriggerKindSelectorProps) => {\n const { t } = useTranslation(meta.profile.key);\n const handleValueChange = useCallback(\n (id: string) => {\n const option = OPTIONS.find((option) => option.kind === id);\n if (option) {\n onChange(option.kind);\n }\n },\n [onChange],\n );\n\n return (\n <Listbox.Root onValueChange={handleValueChange}>\n <Listbox.Content classNames='gap-1' aria-label={t('trigger-kind.placeholder')}>\n {OPTIONS.map(({ kind, icon, disabled }) => (\n <Listbox.Item key={kind} id={kind} disabled={disabled} classNames='dx-input-surface rounded-sm'>\n <Listbox.ItemContent\n icon={<Icon icon={icon} size={5} classNames='text-description' />}\n title={<span className='font-medium'>{t(`trigger-kind.${kind}.label`)}</span>}\n description={t(`trigger-kind.${kind}.description`)}\n />\n </Listbox.Item>\n ))}\n </Listbox.Content>\n </Listbox.Root>\n );\n};\n","//\n// Copyright 2026 DXOS.org\n//\n\nimport * as Schema from 'effect/Schema';\nimport React, { useCallback, useMemo, useState } from 'react';\n\nimport { Routine, Trigger } from '@dxos/compute';\nimport { type Database, DXN, Feed, Filter, Obj, Query, Ref, Scope, Type } from '@dxos/echo';\nimport { useQuery } from '@dxos/echo-react';\nimport { IconButton, Input, ThemedClassName, useTranslation } from '@dxos/react-ui';\nimport { Form, type FormFieldMap, type FormFieldRendererProps, SelectField } from '@dxos/react-ui-form';\nimport { ParentLabelAnnotation } from '@dxos/schema';\nimport { mx } from '@dxos/ui-theme';\n\nimport { meta } from '#meta';\n\nimport { wireTriggers } from '../../util';\nimport {\n FrequencyDefaults,\n Schedule,\n type ScheduleKind,\n type ScheduleValue,\n cronToSchedule,\n scheduleToCron,\n toCron,\n} from '../Schedule';\nimport { type TriggerKind, TriggerKindSelector } from './TriggerKindSelector';\n\n// A recurring trigger fires on a cron, so the one-time `once` kind is not offered here.\nconst RECURRING_KINDS = ['hourly', 'daily', 'weekly', 'monthly', 'custom'] as const satisfies readonly ScheduleKind[];\n\n// `enabled` is extended onto every spec form so it renders inline with the kind's fields.\nconst EnabledForm = Type.getSchema(Trigger.Trigger).pipe(Schema.pick('enabled', 'remote'));\n\n// Scoped trigger form, modeled as a top-level discriminated union (one member per pluggable variant) so the\n// Form renders the chosen kind's fields as one flat field set (no nested, bordered sub-fieldset). The kind\n// itself is chosen by `TriggerKindPicker` (a radio-card list) rather than a select. The feed field carries\n// ParentLabelAnnotation so the built-in RefField labels feed options by their parent object (e.g. the mailbox).\nconst TimerSpecForm = Schema.extend(\n Schema.Struct({\n kind: Schema.Literal('timer'),\n cron: Schema.String.pipe(Schema.annotations({ title: 'Schedule (cron)' }), Schema.optional),\n }),\n EnabledForm,\n);\n\nconst SubscriptionSpecForm = Schema.extend(\n Schema.Struct({\n kind: Schema.Literal('subscription'),\n // The object type to watch; converted to a `Filter.type` query. `typename` renders via a custom select of\n // the space/registry types (see `TypeSelectField`); `deep`/`delay` map to the subscription's options.\n typename: Schema.String.pipe(Schema.annotations({ title: 'Type' }), Schema.optional),\n deep: Schema.Boolean.pipe(Schema.annotations({ title: 'Nested' }), Schema.optional),\n delay: Schema.Number.pipe(Schema.annotations({ title: 'Delay (ms)' }), Schema.optional),\n }),\n EnabledForm,\n);\n\nconst WebhookSpecForm = Schema.extend(\n Schema.Struct({\n kind: Schema.Literal('webhook'),\n method: Schema.String.pipe(Schema.annotations({ title: 'Method' }), Schema.optional),\n port: Schema.Number.pipe(Schema.annotations({ title: 'Port' }), Schema.optional),\n }),\n EnabledForm,\n);\n\nconst FeedSpecForm = Schema.extend(\n Schema.Struct({\n kind: Schema.Literal('feed'),\n feed: Ref.Ref(Feed.Feed).pipe(\n ParentLabelAnnotation.set(true),\n Schema.annotations({ title: 'Feed' }),\n Schema.optional,\n ),\n }),\n EnabledForm,\n);\n\nconst EmailSpecForm = Schema.extend(\n Schema.Struct({\n kind: Schema.Literal('email'),\n }),\n EnabledForm,\n);\n\nconst TriggerForm = Schema.Union(TimerSpecForm, SubscriptionSpecForm, WebhookSpecForm, FeedSpecForm, EmailSpecForm);\ntype TriggerFormValues = Schema.Schema.Type<typeof TriggerForm>;\n\n// Flat view of the form values: `Partial<TriggerFormValues>` collapses a discriminated union to its common\n// key alone (`kind`), so reach the variant fields through this all-optional shape instead. `Partial<T>` is\n// assignable to it, so handlers/helpers can accept the Form's value verbatim and still read the variant fields.\ntype TriggerFormInput = {\n readonly kind?: TriggerKind;\n readonly enabled?: boolean;\n readonly cron?: string;\n readonly method?: string;\n readonly port?: number;\n readonly feed?: Ref.Ref<Feed.Feed>;\n readonly typename?: string;\n readonly deep?: boolean;\n readonly delay?: number;\n};\n\n/** Project a trigger spec onto the form's discriminated-union members. */\nconst triggerFormValues = (spec?: Trigger.Spec): TriggerFormInput => {\n switch (spec?.kind) {\n case 'subscription':\n // The watched typename is preserved in `query.raw` so the Type select can round-trip it.\n return {\n kind: 'subscription',\n typename: spec.query?.raw,\n deep: spec.options?.deep,\n delay: spec.options?.delay,\n };\n case 'feed':\n return {\n kind: 'feed',\n feed: spec.feed,\n };\n case 'webhook':\n return {\n kind: 'webhook',\n method: spec.method,\n port: spec.port,\n };\n case 'email':\n return {\n kind: 'email',\n };\n case 'timer':\n return {\n kind: 'timer',\n cron: spec.cron,\n };\n default:\n // No spec yet: leave the kind unset so the editor shows the variant picker (nothing selected).\n return {};\n }\n};\n\n// Fallback cron used when no schedule has been set yet.\nconst DEFAULT_TIMER_CRON = toCron(FrequencyDefaults.daily);\n\n/** Build the subscription query: filter by the chosen type, or match everything until one is picked. */\nconst subscriptionQuery = (typename?: string): Query.Any =>\n typename ? Query.select(Filter.type(DXN.make(typename))) : Query.select(Filter.everything());\n\n/** Build a trigger spec from the form's values. */\nconst triggerFormSpec = (values: TriggerFormInput): Trigger.Spec => {\n switch (values.kind) {\n case 'subscription': {\n const hasOptions = values.deep != null || values.delay != null;\n return {\n kind: 'subscription',\n // Carry the typename in `raw` so the editor can recover the Type selection on reopen.\n query: { raw: values.typename, ast: subscriptionQuery(values.typename).ast },\n options: hasOptions ? { deep: values.deep, delay: values.delay } : undefined,\n };\n }\n case 'feed':\n return {\n kind: 'feed',\n feed: values.feed,\n };\n case 'webhook':\n return Trigger.specWebhook({ method: values.method, port: values.port });\n case 'email':\n return Trigger.specEmail();\n case 'timer':\n default:\n return Trigger.specTimer(values.cron || DEFAULT_TIMER_CRON);\n }\n};\n\nexport type TriggerEditorProps = ThemedClassName<{\n db: Database.Database;\n routine: Routine.Routine;\n trigger?: Trigger.Trigger;\n /** Render the trigger for display only (no variant picker, clear, or field edits). */\n readonly?: boolean;\n}>;\n\nexport const TriggerEditor = ({ classNames, db, routine, trigger, readonly }: TriggerEditorProps) => {\n const { t } = useTranslation(meta.profile.key);\n const { defaultValues, fieldMap, kind, reset, handleValuesChanged } = useTriggerForm(routine, trigger);\n\n return (\n <>\n <Form.Root\n // Remount when the bound trigger changes or its spec kind changes (including reset to no kind),\n // so the uncontrolled form re-reads `defaultValues`; stable while editing fields within a kind.\n key={`${trigger?.id ?? 'new'}:${trigger?.spec?.kind ?? 'none'}`}\n schema={TriggerForm}\n db={db}\n readonly={readonly}\n fieldMap={fieldMap}\n defaultValues={defaultValues}\n onValuesChanged={handleValuesChanged}\n >\n {/* TODO(burdon): Generalize Form handling (indented section) for discriminated unions. */}\n <Form.Content classNames={mx(kind && 'pb-2 dx-card-surface border border-separator rounded-xs', classNames)}>\n {kind ? (\n <>\n <div className='flex items-center'>\n <Input.Root>\n <Input.Label classNames='pl-2 grow truncate'>{t(`trigger-kind.${kind}.label`)}</Input.Label>\n </Input.Root>\n {!readonly && (\n <IconButton\n variant='ghost'\n icon='ph--x--regular'\n iconOnly\n square\n label={t('trigger-kind.clear.label')}\n onClick={reset}\n />\n )}\n </div>\n <Form.FieldSet classNames='px-2' />\n </>\n ) : (\n <Form.FieldSet />\n )}\n\n {/* Currently, email triggers have no configuration; surface an explanatory note instead of an empty body. */}\n {kind === 'email' && <p className='px-2 text-sm text-description'>{t('trigger-kind.email-note.message')}</p>}\n </Form.Content>\n </Form.Root>\n </>\n );\n};\n\n/** Selects the ECHO object type to watch (subscription `typename`) from the space + registry schemas. */\nconst TypeSelectField = (props: FormFieldRendererProps) => {\n const types = useQuery(props.db, Query.select(Filter.type(Type.Type)).from(Scope.space(), Scope.registry()));\n const options = useMemo(\n () =>\n types\n .filter((type) => !Type.isTypeKind(type))\n .map((type) => Type.getTypename(type))\n .filter((typename): typename is string => !!typename)\n .map((typename) => ({ value: typename, label: typename })),\n [types],\n );\n return <SelectField {...props} options={options} />;\n};\n\nTypeSelectField.displayName = 'TriggerEditor.TypeSelectField';\n\n/** Edits the cron via the Schedule picker (recurring kinds only) with a live cronstrue description below it. */\nconst CronField = (props: FormFieldRendererProps) => {\n const cron = (props.getValue() as string | undefined) || DEFAULT_TIMER_CRON;\n // Read once per mount; the Schedule owns its state and emits cron changes via `handleChange`.\n const initial = useMemo(() => cronToSchedule(cron), []);\n\n const handleChange = useCallback(\n (value: ScheduleValue) => {\n const next = scheduleToCron(value);\n if (next) {\n props.onValueChange(props.type, next);\n }\n },\n [props.type, props.onValueChange],\n );\n\n // TODO(wittjosiah): Add read-only support.\n return (\n <Schedule.Root kinds={RECURRING_KINDS} defaultValue={initial} onValueChange={handleChange}>\n <Schedule.Header />\n <Schedule.Kind />\n <Schedule.Body />\n </Schedule.Root>\n );\n};\n\nCronField.displayName = 'TriggerEditor.CronField';\n\n/** Form state for the Trigger section: the chosen variant spec, plus create-on-first-edit handler. */\nconst useTriggerForm = (routine: Routine.Routine, trigger?: Trigger.Trigger) => {\n const methodOptions = useMemo(\n () => [\n { value: 'GET', label: 'GET' },\n { value: 'POST', label: 'POST' },\n ],\n [],\n );\n\n const fieldMap = useMemo<FormFieldMap>(\n () => ({\n // Show the variant picker only until a kind is chosen; once selected the row is replaced by that\n // variant's editor (the kind field renders nothing).\n kind: (props) =>\n props.getValue() ? null : <TriggerKindSelector onChange={(next) => props.onValueChange(props.type, next)} />,\n cron: (props) => <CronField {...props} />,\n method: (props) => <SelectField {...props} options={methodOptions} />,\n typename: (props) => <TypeSelectField {...props} />,\n }),\n [methodOptions],\n );\n\n // Seed from the trigger's current spec/enabled; a trigger with no spec starts with no kind (picker).\n // Depend on `spec`/`enabled` (not just `trigger` identity) so an in-place clear/change recomputes the\n // seed — the Form re-reads it on remount (keyed by `spec.kind`), reverting to the picker on reset.\n const defaultValues = useMemo<Partial<TriggerFormValues>>(\n () => ({\n ...triggerFormValues(trigger?.spec),\n enabled: trigger?.enabled,\n remote: trigger?.remote,\n }),\n [trigger, trigger?.spec, trigger?.enabled, trigger?.remote],\n );\n\n // Mirror the active kind: gates the variant picker (shown only while unset) and the variant-specific notes.\n const [kind, setKind] = useState<TriggerKind | undefined>(() => triggerFormValues(trigger?.spec).kind);\n\n // Revert the kind selection: clear the trigger's spec. Clearing changes `spec.kind`, which is part of\n // the Form's `key`, so the form remounts and re-reads `defaultValues` (picker reappears) — no nonce needed.\n const reset = useCallback(() => {\n setKind(undefined);\n if (trigger) {\n Obj.update(trigger, (trigger) => {\n trigger.spec = undefined;\n });\n }\n }, [trigger]);\n\n const handleValuesChanged = useCallback(\n (values: Partial<TriggerFormValues>) => {\n // Ignore changes until a kind is picked, so the unselected picker never seeds a default trigger.\n if (!values.kind) {\n return;\n }\n\n const spec = triggerFormSpec(values);\n // `triggerFormSpec` maps `values.kind` 1:1 onto `spec.kind`; use the already-narrowed form kind so\n // the state stays typed as the selectable `TriggerKind` subset (the wider `Trigger.Spec` union now\n // also carries the invoke-only `manual` kind, which the form never produces).\n setKind(values.kind);\n const enabled = values.enabled === true;\n const remote = values.remote;\n // Edit the spec, `enabled`, and `remote` on the trigger directly from the form values.\n // The trigger's `function` and `input` (including the instructions binding and any operation-specific\n // bindings like `{ magazine }`) are wired once by `makeRoutine`, so they are not re-derived here.\n if (trigger) {\n Obj.update(trigger, (trigger) => {\n // The subscription spec's QueryAST is deeply readonly while the live ECHO draft's `spec` is mutable;\n // the structures are identical at runtime, so a readonly->mutable boundary coercion is required here\n // (mirrors commands/trigger/update/subscription.ts).\n trigger.spec = spec as typeof trigger.spec;\n trigger.enabled = enabled;\n trigger.remote = remote;\n });\n } else {\n // Defensive: the draft normally carries an owned trigger already (see `makeRoutine`). If absent,\n // create one in memory and attach it to the routine graph — nothing is persisted until save.\n const created = Trigger.make({ spec, enabled, remote });\n Obj.setParent(created, routine);\n Obj.update(routine, (routine) => {\n routine.triggers.push(Ref.make(created));\n });\n // Wire the new trigger's `function`/`input` to dispatch the routine's action (RunInstructions binds the\n // owned instructions; an operation binds directly).\n wireTriggers(routine);\n }\n },\n [routine, trigger],\n );\n\n return {\n defaultValues,\n fieldMap,\n kind,\n reset,\n handleValuesChanged,\n };\n};\n","//\n// Copyright 2026 DXOS.org\n//\n\nimport * as Schema from 'effect/Schema';\nimport React, { type PropsWithChildren, useCallback, useMemo } from 'react';\n\nimport { Instructions, Operation, Routine, Trigger } from '@dxos/compute';\nimport { type Database, DXN, Entity, Filter, Obj, Query, Ref, Scope, Type } from '@dxos/echo';\nimport { useObject, useQuery } from '@dxos/echo-react';\nimport { ToggleGroup, ToggleGroupItem, composable, composableProps, useTranslation } from '@dxos/react-ui';\nimport { Form, type FormFieldMap, RefField } from '@dxos/react-ui-form';\n\nimport { meta } from '#meta';\n\nimport { wireTriggers } from '../../util';\nimport { InstructionsEditor } from '../InstructionsEditor';\nimport { TriggerEditor } from '../TriggerEditor';\n\n//\n// Main (general) form — the outer form; actions and triggers are sub-forms within its content.\n//\n\n// Pick the editable general fields from the Routine schema rather than redeclaring them.\nconst GeneralForm = Type.getSchema(Routine.Routine).pipe(Schema.pick('name', 'description'));\ntype GeneralForm = Schema.Schema.Type<typeof GeneralForm>;\n\nexport type RoutineFormProps = {\n db: Database.Database;\n routine: Routine.Routine;\n /** Render the form for display only (e.g. an enabled routine, locked until disabled). */\n readonly?: boolean;\n /** Commit the edit session; when set, the form renders a Save/Cancel action row (the companion's create flow). */\n onSave?: () => void;\n /** Discard the edit session. */\n onCancel?: () => void;\n};\n\n/**\n * Composite routine form: the general fields (name + description) are the outer {@link Form},\n * with the Actions and Triggers sections rendered as sub-forms inside its content:\n * - Actions — Operation/Instructions variants chosen via a button group (single action; `spec` isn't an array).\n * - Triggers — the {@link TriggerEditor}.\n *\n * The sub-forms read and autosave the routine's owned instructions and primary trigger directly off the\n * `routine` graph (live editing); `readonly` displays them without edit affordances. The optional Save/Cancel\n * row is used only by the companion's create-from-template flow.\n *\n * Created with `composable()` so it carries the COMPOSABLE marker and can be the child of\n * `Panel.Content asChild` (forwards ref and merges layout props onto the scroll viewport).\n */\nexport const RoutineForm = composable<HTMLDivElement, RoutineFormProps>(\n ({ db, routine, readonly = false, onSave, onCancel, ...props }, forwardedRef) => {\n const { t } = useTranslation(meta.profile.key);\n const [auto, updateAuto] = useObject(routine);\n const trigger = usePrimaryTrigger(routine);\n\n // Read once per routine identity; the uncontrolled form owns edits after mount.\n const defaultValues = useMemo<Partial<GeneralForm>>(\n () => ({ name: auto.name, description: auto.description }),\n [routine],\n );\n\n const handleValuesChanged = useCallback(\n (values: Partial<GeneralForm>) => {\n updateAuto((routine) => {\n routine.name = values.name;\n routine.description = values.description;\n });\n },\n [updateAuto],\n );\n\n // TODO(burdon): Could this be rewritten a single form with custom fields?\n return (\n <Form.Root\n schema={GeneralForm}\n readonly={readonly}\n defaultValues={defaultValues}\n onValuesChanged={handleValuesChanged}\n onSave={onSave}\n onCancel={onCancel}\n >\n <Form.Viewport scroll {...composableProps(props)} ref={forwardedRef}>\n <Form.Content>\n <Form.FieldSet />\n\n <Section title={t('actions.title')}>\n <ActionEditor db={db} routine={routine} readonly={readonly} />\n </Section>\n\n {/* TODO(burdon): Support multiple triggers. */}\n <Section title={t('triggers.title')}>\n <TriggerEditor db={db} routine={routine} trigger={trigger} readonly={readonly} />\n </Section>\n\n {/* Save/Cancel for the edit session (the sub-forms autosave to the in-memory clones as they change). */}\n {onSave && <Form.Actions />}\n </Form.Content>\n </Form.Viewport>\n </Form.Root>\n );\n },\n);\n\n/** Lightweight labelled grouping for a sub-form (no `Settings` chrome). */\nconst Section = ({ title, children }: PropsWithChildren<{ title: string }>) => (\n <div className='flex flex-col mbs-4'>\n <Form.Label standalone label={title} />\n {children}\n </div>\n);\n\n//\n// Actions\n//\n\n/**\n * Single action: an Operation (the routine's `spec.runnable`) or an owned Instructions edited inline. The\n * action kind is derived from the routine's `spec` — an absent spec means \"operation, none chosen yet\" (a\n * scaffolded routine always carries an instructions spec, so the only way to clear it is switching to an\n * operation). `makeRoutine` establishes the owned-instructions wiring when the routine is scaffolded.\n */\nconst ActionEditor = ({\n db,\n routine: routineProp,\n readonly,\n}: {\n db: Database.Database;\n routine: Routine.Routine;\n readonly?: boolean;\n}) => {\n const operations = useOperations(db);\n const [routine, updateRoutine] = useObject(routineProp);\n\n // Classification is read off `spec.kind` (no dereference); the owned instructions object is then resolved in\n // place to hand to the editor (an owned ref is always locally resolvable, and the parent `useObject` re-renders\n // this when `spec` changes). An absent spec means \"runnable, none chosen yet\" — a scaffolded routine always\n // carries an instructions spec, so the only way to clear it is switching to a runnable action.\n const kind = routine.spec?.kind ?? 'runnable';\n const operationRef = Routine.runnableRef(routine);\n const instructions = Routine.instructionsRef(routine)?.target;\n\n const handleOperationChange = useCallback(\n (operation?: Ref.Ref<Operation.PersistentOperation>) => {\n updateRoutine((routine) => {\n routine.spec = operation ? { kind: 'runnable', runnable: operation } : undefined;\n });\n // Keep the owned trigger's `function`/`input` in sync with the new action.\n wireTriggers(routineProp);\n },\n [updateRoutine, routineProp],\n );\n\n const handleKindChange = useCallback(\n (next: Routine.Kind) => {\n updateRoutine((routine) => {\n if (next === 'runnable') {\n // Switch to an operation action; the operation is chosen via the picker below. A previously-owned\n // instructions stays parented to the routine (cascade-deleted with it) but is no longer the action.\n routine.spec = undefined;\n } else if (routine.spec?.kind !== 'instructions') {\n // Seed an owned instructions action (the executing operation is the implicit RunInstructions).\n const instructions = Instructions.make({});\n Obj.setParent(instructions, routine);\n routine.spec = { kind: 'instructions', instructions: Ref.make(instructions) };\n }\n });\n // Re-wire the owned trigger to dispatch the new action (RunInstructions vs the operation).\n wireTriggers(routineProp);\n },\n [updateRoutine, routineProp],\n );\n\n return (\n <div className='flex flex-col'>\n {!readonly && <ActionKindToggle value={kind} onChange={handleKindChange} />}\n {kind === 'runnable' ? (\n <OperationEditor\n db={db}\n operations={operations}\n operation={operationRef}\n onChange={handleOperationChange}\n readonly={readonly}\n />\n ) : instructions ? (\n <InstructionsEditor db={db} instructions={instructions} readonly={readonly} />\n ) : null}\n </div>\n );\n};\n\nconst ActionKindToggle = ({ value, onChange }: { value: Routine.Kind; onChange: (kind: Routine.Kind) => void }) => {\n const { t } = useTranslation(meta.profile.key);\n return (\n // `type='single'` emits `''` when the selected item is clicked again (toggled off); ignore that and any\n // other non-kind value so it can't fall through and overwrite the current action.\n <ToggleGroup\n type='single'\n value={value}\n onValueChange={(next) => {\n if (next === 'instructions' || next === 'runnable') {\n onChange(next);\n }\n }}\n >\n <ToggleGroupItem value='instructions'>{t('action-kind.instructions.label')}</ToggleGroupItem>\n <ToggleGroupItem value='runnable'>{t('action-kind.operation.label')}</ToggleGroupItem>\n </ToggleGroup>\n );\n};\n\nconst OperationActionForm = Schema.Struct({\n operation: Ref.Ref(Operation.PersistentOperation).pipe(Schema.annotations({ title: 'Operation' }), Schema.optional),\n});\ntype OperationActionValues = Schema.Schema.Type<typeof OperationActionForm>;\n\n// Operation picker options: surface each operation's registry key (plugin/id) as the option's secondary\n// line and sort by name. The `id` derivation mirrors the RefField default so a selected operation ref\n// still matches its option.\nconst getOperationOptions = (results: Entity.Any[]): { id: string; label: string; description?: string }[] =>\n results\n // Hide internal operations: only operations annotated visible are user-bindable as trigger actions.\n .filter((operation) => !Obj.instanceOf(Operation.PersistentOperation, operation) || Operation.isVisible(operation))\n .map((operation) => {\n const id = Entity.getURI(operation, { prefer: 'named' });\n const name = Entity.getLabel(operation) ?? id;\n const key = Obj.instanceOf(Operation.PersistentOperation, operation) ? Operation.getKey(operation) : undefined;\n return { id, label: name, description: key };\n })\n .sort((left, right) => left.label.localeCompare(right.label));\n\n/** Sub-form: ref picker for an Operation. Draws options from the queried operation set (space + registry). */\nconst OperationEditor = ({\n db,\n operations,\n operation,\n onChange,\n readonly,\n}: {\n db: Database.Database;\n operations: ReturnType<typeof useOperations>;\n operation?: Ref.Ref<Operation.PersistentOperation>;\n onChange?: (operation?: Ref.Ref<Operation.PersistentOperation>) => void;\n readonly?: boolean;\n}) => {\n const fieldMap = useMemo<FormFieldMap>(\n () => ({\n operation: (props) => (\n <RefField {...props} db={db} useResults={() => operations} getOptions={getOperationOptions} />\n ),\n }),\n [db, operations],\n );\n const defaultValues = useMemo<Partial<OperationActionValues>>(() => ({ operation }), [operation]);\n const handleValuesChanged = useCallback(\n (values: Partial<OperationActionValues>) => onChange?.(values.operation),\n [onChange],\n );\n\n return (\n <Form.Root\n schema={OperationActionForm}\n db={db}\n readonly={readonly}\n defaultValues={defaultValues}\n fieldMap={fieldMap}\n onValuesChanged={handleValuesChanged}\n >\n <Form.FieldSet />\n </Form.Root>\n );\n};\n\n//\n// Hooks\n//\n\n/** Operations available to bind as an action (space-resident plus registry / plugin-provided). */\nconst useOperations = (db: Database.Database) =>\n useQuery(\n db,\n Query.select(Filter.type(DXN.make(Type.getTypename(Operation.PersistentOperation)))).from(\n Scope.space(),\n Scope.registry(),\n ),\n );\n\n/** Subscribe to the routine and derive its primary (first) trigger. */\nconst usePrimaryTrigger = (routine: Routine.Routine): Trigger.Trigger | undefined => {\n const [snapshot] = useObject(routine);\n return useMemo(() => {\n for (const ref of snapshot.triggers) {\n const target = ref.target;\n if (Obj.instanceOf(Trigger.Trigger, target)) {\n return target;\n }\n }\n return undefined;\n }, [snapshot.triggers]);\n};\n","//\n// Copyright 2026 DXOS.org\n//\n\nimport React, { useCallback, useMemo } from 'react';\n\nimport { useCapabilities } from '@dxos/app-framework/ui';\nimport { type SpaceCapabilities } from '@dxos/plugin-space';\nimport { useTranslation } from '@dxos/react-ui';\nimport { SearchList, useSearchListResults } from '@dxos/react-ui-search';\n\nimport { meta } from '#meta';\nimport { RoutineCapabilities } from '#types';\n\nexport type CreateRoutinePanelProps = SpaceCapabilities.CreateObjectCustomPanelProps & {\n /** Optional override (primarily for stories/tests). Defaults to RoutineCapabilities.Template. */\n templates?: RoutineCapabilities.Template[];\n};\n\n/**\n * Create panel for routines: a SearchList picker over contributed templates. Selecting one submits\n * `{ templateId }`; plugin-routine's CreateObjectEntry.createObject resolves the templateId and runs the\n * template's `scaffold`.\n */\nexport const CreateRoutinePanel = ({ onCreateObject, templates: templatesProp }: CreateRoutinePanelProps) => {\n const { t } = useTranslation(meta.profile.key);\n const capabilityTemplates = useCapabilities(RoutineCapabilities.Template);\n const templates = templatesProp ?? capabilityTemplates;\n // The global create dialog has no subject, so subject-required templates (e.g. CRM, which needs a\n // Mailbox) are excluded; they are offered from the relevant object's Automation companion instead.\n const sorted = useMemo(\n () =>\n [...templates]\n .filter((template) => template.appliesTo?.(undefined) ?? true)\n .sort((a, b) => a.label.localeCompare(b.label)),\n [templates],\n );\n const { results, handleSearch } = useSearchListResults({ items: sorted, extract: (template) => template.label });\n\n const handleSelect = useCallback(\n (templateId: string) => {\n void onCreateObject({ templateId });\n },\n [onCreateObject],\n );\n\n return (\n <SearchList.Root onSearch={handleSearch}>\n <SearchList.Input\n classNames='mb-form-gap'\n autoFocus\n data-testid='create-automation-panel.template-input'\n placeholder={t('create-panel.template.placeholder')}\n />\n <SearchList.Viewport>\n {results.map((template) => (\n <SearchList.Item\n key={template.id}\n value={template.id}\n label={template.label}\n icon={template.icon ?? 'ph--lightning--regular'}\n onSelect={() => handleSelect(template.id)}\n />\n ))}\n </SearchList.Viewport>\n </SearchList.Root>\n );\n};\n","//\n// Copyright 2026 DXOS.org\n//\n\nimport React from 'react';\n\nimport { type AppSurface } from '@dxos/app-toolkit/ui';\nimport { type Routine, type Trigger } from '@dxos/compute';\nimport { useObject } from '@dxos/echo-react';\nimport { Card, Icon, useTranslation } from '@dxos/react-ui';\n\nimport { meta } from '#meta';\n\nimport { cronToSchedule, describeSchedule } from '../Schedule';\n\nexport type RoutineCardProps = AppSurface.ObjectCardProps<Routine.Routine>;\n\n/**\n * Compact preview of a {@link Routine.Routine}: when it runs. Rendered into the\n * `AppSurface.CardContent` slot — Card.Root is supplied by the surface host (the project article's\n * gallery, popovers, related-objects), so this emits Card.Body only. Without it a routine falls back\n * to the generic form preview, which renders its `spec`/`triggers` internals rather than a summary.\n */\nexport const RoutineCard = ({ subject }: RoutineCardProps) => {\n const { t } = useTranslation(meta.profile.key);\n const [routine] = useObject(subject);\n // MVP enforces at most one trigger; the summary describes it.\n const [trigger] = useObject(routine.triggers.at(0));\n\n // Active means the same thing as in the routines list: a trigger exists and is switched on.\n const active = trigger?.enabled === true;\n\n return (\n <Card.Body>\n <Card.Row>\n {/* The gutter is reserved either way so the summary stays aligned across cards. */}\n <Card.Block>{active && <Icon icon='ph--check-circle--regular' classNames='text-green-text' />}</Card.Block>\n <Card.Text variant='description' classNames='line-clamp-2'>\n {describeTrigger(trigger?.spec, t)}\n </Card.Text>\n </Card.Row>\n </Card.Body>\n );\n};\n\nRoutineCard.displayName = 'RoutineCard';\n\n/**\n * The same sentence the trigger editor shows above the schedule picker. Non-timer kinds have no\n * parameters worth summarizing, so they reuse the kind description from the trigger-kind picker.\n */\nconst describeTrigger = (spec: Trigger.Spec | undefined, t: (key: string) => string): string => {\n if (!spec) {\n return t('add-trigger-first.message');\n }\n\n return spec.kind === 'timer'\n ? describeSchedule(cronToSchedule(spec.cron))\n : t(`trigger-kind.${spec.kind}.description`);\n};\n","//\n// Copyright 2025 DXOS.org\n//\n\nimport {\n type CompletionContext,\n type CompletionResult,\n autocompletion,\n completionKeymap,\n} from '@codemirror/autocomplete';\nimport { type Extension, RangeSetBuilder } from '@codemirror/state';\nimport {\n Decoration,\n type DecorationSet,\n type EditorView,\n ViewPlugin,\n type ViewUpdate,\n WidgetType,\n keymap,\n} from '@codemirror/view';\n\nimport { Domino, mx } from '@dxos/ui';\n\nexport type HandlebarsOptions = {};\n\n/**\n * Simple Handlebars plugin for CodeMirror.\n * Supports:\n * - Comments: {{! comment }}\n * - Commands: {{#command}} {{/command}}\n * - Variables: {{var}}\n * - Commands with variables: {{#each items}} {{/each}}\n */\nexport const handlebars = (_: HandlebarsOptions = {}): Extension => {\n return [\n handlebarsHighlightPlugin,\n autocompletion({\n activateOnTyping: true,\n aboveCursor: true,\n closeOnBlur: true,\n override: [handlebarsCompletions],\n }),\n keymap.of(completionKeymap),\n ];\n};\n\nconst regex = {\n // {{! comment }}\n comment: /\\{\\{!\\s*[^}]*\\}\\}/g,\n\n // {{var}}\n brackets: /\\{\\{[^}]*\\}\\}/g,\n\n // {{#command}} {{/command}}\n command: /\\{\\{[#/]([^}]+)\\}\\}/g,\n\n // {{var}}\n var: /\\{\\{(?!\\s*!)(\\w[^}]*)\\}\\}/g,\n\n // @echo://space/id or @dxn:nsid\n dxn: /@?(?:echo:\\/{1,3}[\\w/]+|dxn:[\\w.-]+)/g,\n\n // example.com/path/xxx\n url: /[\\w.-]+\\.[\\w.-]+\\/[\\w/]+/g,\n};\n\nconst tagPadding = 'mx-0.5 px-1 rounded-xs';\n\n/**\n * ViewPlugin that decorates Handlebars syntax.\n */\nconst handlebarsHighlightPlugin = ViewPlugin.fromClass(\n class {\n decorations: DecorationSet;\n\n constructor(view: EditorView) {\n this.decorations = this.buildDecorations(view);\n }\n\n update(update: ViewUpdate) {\n if (update.docChanged || update.viewportChanged || update.selectionSet) {\n this.decorations = this.buildDecorations(update.view);\n }\n }\n\n // NOTE: Decorations may clash with other extensions (e.g., markdown).\n buildDecorations(view: EditorView) {\n const selection = view.state.selection.main;\n const decorations: Array<{\n from: number;\n to: number;\n decoration: Decoration;\n }> = [];\n\n for (const { from, to } of view.visibleRanges) {\n const text = view.state.doc.sliceString(from, to);\n\n // Match DXN.\n {\n let match;\n while ((match = regex.dxn.exec(text)) !== null) {\n const start = from + match.index;\n const end = start + match[0].length;\n // Only show widget if selection doesn't overlap with the match range.\n const overlaps = selection.to > start && selection.from <= end;\n if (!overlaps) {\n decorations.push({\n from: start,\n to: end,\n decoration: Decoration.widget({\n widget: new DXNWidget(match[0]),\n }),\n });\n }\n }\n }\n\n // Match URLs.\n {\n let match;\n while ((match = regex.url.exec(text)) !== null) {\n const start = from + match.index;\n const end = start + match[0].length;\n decorations.push({\n from: start,\n to: end,\n decoration: Decoration.mark({\n class: mx('dx-tag--blue', tagPadding),\n }),\n });\n }\n }\n\n // Match brackets: {{ and }}.\n {\n let match;\n while ((match = regex.brackets.exec(text)) !== null) {\n const start = from + match.index;\n const end = start + match[0].length;\n decorations.push({\n from: start,\n to: end,\n decoration: Decoration.mark({ class: 'text-subdued' }),\n });\n }\n }\n\n // Match commands: {{#command}} and {{/command}}.\n {\n let match;\n while ((match = regex.command.exec(text)) !== null) {\n const start = from + match.index + 2;\n let end = start + match[0].length - 4;\n const text = view.state.doc.sliceString(start, end);\n const parts = text.split(/\\s+/);\n if (parts.length > 1) {\n const idx = start + parts[0].length;\n decorations.push({\n from: idx,\n to: end,\n decoration: Decoration.mark({ class: 'text-green-text' }),\n });\n end = idx;\n }\n decorations.push({\n from: start,\n to: end,\n decoration: Decoration.mark({ class: 'text-blue-text' }),\n });\n }\n }\n\n // Match variables: {{var}}.\n {\n let match;\n while ((match = regex.var.exec(text)) !== null) {\n const start = from + match.index + 2;\n const end = start + match[0].length - 4;\n decorations.push({\n from: start,\n to: end,\n decoration: Decoration.mark({ class: 'text-green-text' }),\n });\n }\n }\n }\n\n // Sort decorations by position to satisfy RangeSetBuilder requirements.\n decorations.sort((a, b) => a.from - b.from || a.to - b.to);\n\n // Add sorted decorations to builder.\n const builder = new RangeSetBuilder<Decoration>();\n for (const { from, to, decoration } of decorations) {\n builder.add(from, to, decoration);\n }\n\n return builder.finish();\n }\n },\n {\n decorations: (v) => v.decorations,\n },\n);\n\nclass DXNWidget extends WidgetType {\n constructor(private readonly _identifier: string) {\n super();\n }\n\n override ignoreEvent() {\n return false;\n }\n\n override eq(other: this) {\n return this._identifier === other._identifier;\n }\n\n override toDOM() {\n const text = this._identifier\n .split(':')\n .map((part) => {\n const len = 16;\n const plen = 4;\n if (part.length > len) {\n return `[${part.slice(0, plen)}…${part.slice(-plen)}]`;\n }\n return part;\n })\n .join(':');\n return Domino.of('span').classNames(mx('font-mono dx-tag--blue', tagPadding)).text(text).root;\n }\n}\n\n// TODO(burdon): Pass in variables.\nconst variables = ['this'];\nconst commands = ['this', 'each', 'if', 'unless', 'with'];\n\n/**\n * Provides completions for Handlebars variables.\n */\nfunction handlebarsCompletions(context: CompletionContext): CompletionResult | null {\n const match = context.matchBefore(/\\{\\{[^}]*/);\n if (!match || match.from === match.to) {\n return null;\n }\n\n let type = 'variable';\n let text = match.text.slice(2);\n let from = match.from + 2;\n let matches = [];\n if (text.startsWith('#') || text.startsWith('/')) {\n const idx = text.lastIndexOf(' ');\n if (idx !== -1) {\n type = 'variable';\n matches = variables;\n text = text.slice(idx + 1);\n from += idx + 1;\n } else {\n type = 'command';\n text = text.slice(1);\n matches = commands;\n from += 1;\n }\n } else {\n type = 'variable';\n matches = variables;\n }\n\n const options = matches.filter((name) => name.startsWith(text)).map((name) => ({ type, label: name }));\n return {\n from,\n options,\n };\n}\n","//\n// Copyright 2025 DXOS.org\n//\n\nimport { syntaxTree } from '@codemirror/language';\nimport { type Extension, RangeSetBuilder } from '@codemirror/state';\nimport { Decoration, type DecorationSet, type EditorView, ViewPlugin, type ViewUpdate } from '@codemirror/view';\n\nexport type XmlOptions = {};\n\n/**\n * XML decorator plugin for CodeMirror.\n * Decorates XML tags with monospace font using the XML language grammar.\n */\nexport const xmlDecorator = (_: XmlOptions = {}): Extension => {\n return [xmlDecoratorPlugin];\n};\n\n/**\n * ViewPlugin that decorates XML tags using syntax tree.\n */\nconst xmlDecoratorPlugin = ViewPlugin.fromClass(\n class {\n decorations: DecorationSet;\n\n constructor(view: EditorView) {\n this.decorations = this.buildDecorations(view);\n }\n\n update(update: ViewUpdate) {\n if (update.docChanged || update.viewportChanged) {\n this.decorations = this.buildDecorations(update.view);\n }\n }\n\n buildDecorations(view: EditorView) {\n const builder = new RangeSetBuilder<Decoration>();\n\n for (const { from, to } of view.visibleRanges) {\n syntaxTree(view.state).iterate({\n from,\n to,\n enter: (node) => {\n // Decorate XML elements (opening tags, closing tags, self-closing tags).\n if (\n node.name === 'HTMLTag' ||\n node.name === 'OpenTag' ||\n node.name === 'CloseTag' ||\n node.name === 'SelfClosingTag' ||\n node.name === 'Element'\n ) {\n builder.add(node.from, node.to, Decoration.mark({ class: 'font-mono text-subdued' }));\n }\n },\n });\n }\n\n return builder.finish();\n }\n },\n {\n decorations: (v) => v.decorations,\n },\n);\n","//\n// Copyright 2025 DXOS.org\n//\n\nimport { defaultHighlightStyle, syntaxHighlighting } from '@codemirror/language';\nimport { composeRefs } from '@radix-ui/react-compose-refs';\nimport React from 'react';\n\nimport { type Ref } from '@dxos/echo';\nimport { Doc } from '@dxos/echo-doc';\nimport { useThemeContext, useTranslation } from '@dxos/react-ui';\nimport { composable, composableProps } from '@dxos/react-ui';\nimport { useTextEditor } from '@dxos/react-ui-editor';\nimport { type Text } from '@dxos/schema';\nimport {\n createBasicExtensions,\n createDataExtensions,\n createMarkdownExtensions,\n createThemeExtensions,\n decorateMarkdown,\n} from '@dxos/ui-editor';\nimport { isNonNullable } from '@dxos/util';\n\nimport { meta } from '#meta';\n\nimport { handlebars, xmlDecorator } from './extensions';\n\nexport type TemplateEditorProps = {\n id: string;\n /** Markdown + Handlebars source text. */\n source?: Ref.Ref<Text.Text>;\n lineNumbers?: boolean;\n};\n\nexport const TemplateEditor = composable<HTMLDivElement, TemplateEditorProps>(\n ({ classNames, id, source, lineNumbers = true, ...props }, forwardedRef) => {\n const { t } = useTranslation(meta.profile.key);\n const { themeMode } = useThemeContext();\n const { parentRef } = useTextEditor(() => {\n const target = source?.target;\n if (!target) {\n return {};\n }\n\n return {\n initialValue: target.content ?? '',\n extensions: [\n createDataExtensions({ id, text: Doc.createAccessor(target, ['content']) }),\n createBasicExtensions({\n bracketMatching: false,\n lineNumbers,\n lineWrapping: true,\n placeholder: t('template.placeholder'),\n }),\n createThemeExtensions({ themeMode }),\n createMarkdownExtensions(),\n decorateMarkdown(),\n handlebars(),\n // xml(),\n // NOTE: Since we're using markdown only HTML nodes are parsed.\n xmlDecorator(),\n syntaxHighlighting(defaultHighlightStyle),\n ].filter(isNonNullable),\n };\n }, [themeMode, source?.target, lineNumbers]);\n\n return (\n <div\n {...composableProps(props, {\n role: 'none',\n classNames: ['h-full overflow-hidden', classNames],\n })}\n ref={composeRefs(parentRef, forwardedRef)}\n />\n );\n },\n);\n"],"mappings":"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"}
@@ -0,0 +1,11 @@
1
+ import { lazy } from "react";
2
+ //#region src/containers/index.ts
3
+ var RoutineArticle = lazy(() => import("./chunk-RoutineArticle.mjs"));
4
+ var RoutineTraceCompanion = lazy(() => import("./chunk-RoutineTraceCompanion.mjs"));
5
+ var RoutineSettings = lazy(() => import("./chunk-RoutineSettings.mjs"));
6
+ var RoutineCompanion = lazy(() => import("./chunk-RoutineCompanion.mjs"));
7
+ var SkillArticle = lazy(() => import("./chunk-SkillArticle.mjs"));
8
+ //#endregion
9
+ export { RoutineArticle, RoutineCompanion, RoutineSettings, RoutineTraceCompanion, SkillArticle };
10
+
11
+ //# sourceMappingURL=containers.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"containers.mjs","names":[],"sources":["../../src/containers/index.ts"],"sourcesContent":["//\n// Copyright 2025 DXOS.org\n//\n\nimport { type ComponentType, lazy } from 'react';\n\nexport const RoutineArticle: ComponentType<any> = lazy(() => import('./RoutineArticle'));\nexport const RoutineTraceCompanion: ComponentType<any> = lazy(() => import('./RoutineTraceCompanion'));\nexport const RoutineSettings: ComponentType<any> = lazy(() => import('./RoutineSettings'));\nexport const RoutineCompanion: ComponentType<any> = lazy(() => import('./RoutineCompanion'));\nexport const SkillArticle: ComponentType<any> = lazy(() => import('./SkillArticle'));\n"],"mappings":";;AAMA,IAAa,iBAAqC,WAAW,OAAO,6BAAmB;AACvF,IAAa,wBAA4C,WAAW,OAAO,oCAA0B;AACrG,IAAa,kBAAsC,WAAW,OAAO,8BAAoB;AACzF,IAAa,mBAAuC,WAAW,OAAO,+BAAqB;AAC3F,IAAa,eAAmC,WAAW,OAAO,2BAAiB"}
@@ -0,0 +1,37 @@
1
+ import { Trigger } from "@dxos/compute";
2
+ import { Filter, Query } from "@dxos/echo";
3
+ import * as Effect from "effect/Effect";
4
+ import { useEffect, useState } from "react";
5
+ import { useQuery } from "@dxos/echo-react";
6
+ import { useSpaceCallback } from "@dxos/app-framework/ui";
7
+ import { Atom, useAtomValue } from "@effect-atom/atom-react";
8
+ import { TriggerDispatcher } from "@dxos/compute-runtime";
9
+ //#region src/hooks/useTriggerRuntimeControls.ts
10
+ var useTriggerRuntimeControls = (db) => {
11
+ const triggers = useQuery(db, Query.select(Filter.type(Trigger.Trigger)).debugLabel("plugin-routine.useTriggerRuntimeControls"));
12
+ const [dispatcher, setDispatcher] = useState(void 0);
13
+ const init = useSpaceCallback(db?.spaceId, [TriggerDispatcher], Effect.fnUntraced(function* () {
14
+ const dispatcher = yield* TriggerDispatcher;
15
+ setDispatcher(dispatcher);
16
+ }));
17
+ useEffect(() => {
18
+ init();
19
+ }, []);
20
+ const state = useAtomValue(dispatcher?.state ?? Atom.make(void 0));
21
+ const start = useSpaceCallback(db?.spaceId, [TriggerDispatcher], Effect.fnUntraced(function* () {
22
+ yield* (yield* TriggerDispatcher).start();
23
+ }));
24
+ const stop = useSpaceCallback(db?.spaceId, [TriggerDispatcher], Effect.fnUntraced(function* () {
25
+ yield* (yield* TriggerDispatcher).stop();
26
+ }));
27
+ return {
28
+ triggers,
29
+ state,
30
+ start: () => void start(),
31
+ stop: () => void stop()
32
+ };
33
+ };
34
+ //#endregion
35
+ export { useTriggerRuntimeControls };
36
+
37
+ //# sourceMappingURL=hooks.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"hooks.mjs","names":[],"sources":["../../src/hooks/useTriggerRuntimeControls.ts"],"sourcesContent":["//\n// Copyright 2025 DXOS.org\n//\n\nimport { Atom, useAtomValue } from '@effect-atom/atom-react';\nimport type * as Context from 'effect/Context';\nimport * as Effect from 'effect/Effect';\nimport { useEffect, useState } from 'react';\n\nimport { useSpaceCallback } from '@dxos/app-framework/ui';\nimport { Trigger } from '@dxos/compute';\nimport { TriggerDispatcher, type TriggerDispatcherState } from '@dxos/compute-runtime';\nimport { type Database, Filter, Query } from '@dxos/echo';\nimport { useQuery } from '@dxos/echo-react';\n\ninterface TriggerRuntimeControls {\n triggers: Trigger.Trigger[];\n state: TriggerDispatcherState | undefined;\n start: () => void;\n stop: () => void;\n}\n\nexport const useTriggerRuntimeControls = (db: Database.Database | undefined): TriggerRuntimeControls => {\n const triggers = useQuery(\n db,\n Query.select(Filter.type(Trigger.Trigger)).debugLabel('plugin-routine.useTriggerRuntimeControls'),\n );\n\n const [dispatcher, setDispatcher] = useState<Context.Tag.Service<TriggerDispatcher> | undefined>(undefined);\n\n const init = useSpaceCallback(\n db?.spaceId,\n [TriggerDispatcher],\n Effect.fnUntraced(function* () {\n const dispatcher = yield* TriggerDispatcher;\n setDispatcher(dispatcher);\n }),\n );\n\n useEffect(() => {\n void init();\n }, []);\n\n const state = useAtomValue(dispatcher?.state ?? Atom.make(undefined));\n\n const start = useSpaceCallback(\n db?.spaceId,\n [TriggerDispatcher],\n Effect.fnUntraced(function* () {\n const dispatcher = yield* TriggerDispatcher;\n yield* dispatcher.start();\n }),\n );\n\n const stop = useSpaceCallback(\n db?.spaceId,\n [TriggerDispatcher],\n Effect.fnUntraced(function* () {\n const dispatcher = yield* TriggerDispatcher;\n yield* dispatcher.stop();\n }),\n );\n\n return {\n triggers,\n state,\n start: () => void start(),\n stop: () => void stop(),\n };\n};\n"],"mappings":";;;;;;;;;AAsBA,IAAa,6BAA6B,OAA8D;CACtG,MAAM,WAAW,SACf,IACA,MAAM,OAAO,OAAO,KAAK,QAAQ,OAAO,CAAC,CAAC,CAAC,WAAW,0CAA0C,CAClG;CAEA,MAAM,CAAC,YAAY,iBAAiB,SAA6D,KAAA,CAAS;CAE1G,MAAM,OAAO,iBACX,IAAI,SACJ,CAAC,iBAAiB,GAClB,OAAO,WAAW,aAAa;EAC7B,MAAM,aAAa,OAAO;EAC1B,cAAc,UAAU;CAC1B,CAAC,CACH;CAEA,gBAAgB;EACd,KAAU;CACZ,GAAG,CAAC,CAAC;CAEL,MAAM,QAAQ,aAAa,YAAY,SAAS,KAAK,KAAK,KAAA,CAAS,CAAC;CAEpE,MAAM,QAAQ,iBACZ,IAAI,SACJ,CAAC,iBAAiB,GAClB,OAAO,WAAW,aAAa;EAE7B,QAAO,OADmB,kBAAA,CACR,MAAM;CAC1B,CAAC,CACH;CAEA,MAAM,OAAO,iBACX,IAAI,SACJ,CAAC,iBAAiB,GAClB,OAAO,WAAW,aAAa;EAE7B,QAAO,OADmB,kBAAA,CACR,KAAK;CACzB,CAAC,CACH;CAEA,OAAO;EACL;EACA;EACA,aAAa,KAAK,MAAM;EACxB,YAAY,KAAK,KAAK;CACxB;AACF"}
@@ -0,0 +1,5 @@
1
+ import { a as RoutineCapabilities_exports, c as TriggerTemplate, r as RoutineOperation_exports, s as AutomationAction } from "./chunk-types.mjs";
2
+ import { t as meta } from "./chunk-meta.mjs";
3
+ import { n as getRoutinesSettingsPath, t as getRoutinesPath } from "./chunk-paths.mjs";
4
+ import { a as connectedRoutinesQuery, i as runInstructionsRef, n as wireTriggers, o as routineReferencesObject, r as isRunInstructions, s as routinesForObject, t as makeRoutine } from "./chunk-util.mjs";
5
+ export { AutomationAction, RoutineCapabilities_exports as RoutineCapabilities, RoutineOperation_exports as RoutineOperation, TriggerTemplate, connectedRoutinesQuery, getRoutinesPath, getRoutinesSettingsPath, isRunInstructions, makeRoutine, meta, routineReferencesObject, routinesForObject, runInstructionsRef, wireTriggers };
@@ -0,0 +1,2 @@
1
+ import { t as meta } from "./chunk-meta.mjs";
2
+ export { meta };
@@ -0,0 +1,7 @@
1
+ import { OperationHandlerSet } from "@dxos/compute";
2
+ //#region src/operations/index.ts
3
+ var RoutineOperationHandlerSet = OperationHandlerSet.lazy(() => import("./chunk-create-trigger-from-template.mjs"), () => import("./chunk-create-routine.mjs"), () => import("./chunk-run-routine.mjs"));
4
+ //#endregion
5
+ export { RoutineOperationHandlerSet };
6
+
7
+ //# sourceMappingURL=operations.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"operations.mjs","names":[],"sources":["../../src/operations/index.ts"],"sourcesContent":["//\n// Copyright 2025 DXOS.org\n//\n\nimport { OperationHandlerSet } from '@dxos/compute';\n\nexport const RoutineOperationHandlerSet = OperationHandlerSet.lazy(\n () => import('./create-trigger-from-template'),\n () => import('./create-routine'),\n () => import('./run-routine'),\n);\n"],"mappings":";;AAMA,IAAa,6BAA6B,oBAAoB,WACtD,OAAO,mDACP,OAAO,qCACP,OAAO,0BACf"}
@@ -0,0 +1,9 @@
1
+ import { t as meta } from "./chunk-meta.mjs";
2
+ import { RoutineOperationHandlerSet } from "./operations.mjs";
3
+ import { Plugin } from "@dxos/app-framework";
4
+ //#region src/plugin.ts
5
+ var RoutinePlugin = Plugin.lazy(meta, () => import("#plugin"));
6
+ //#endregion
7
+ export { RoutineOperationHandlerSet, RoutinePlugin };
8
+
9
+ //# sourceMappingURL=plugin.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"plugin.mjs","names":[],"sources":["../../src/plugin.ts"],"sourcesContent":["//\n// Copyright 2025 DXOS.org\n//\n\nimport { Plugin } from '@dxos/app-framework';\n\nimport { meta } from './meta';\n\nexport const RoutinePlugin = Plugin.lazy(meta, () => import('#plugin'));\n\nexport { RoutineOperationHandlerSet } from './operations';\n"],"mappings":";;;;AAQA,IAAa,gBAAgB,OAAO,KAAK,YAAY,OAAO,UAAU"}
@@ -0,0 +1,2 @@
1
+ import { t as RoutinePlugin } from "./chunk-RoutinePlugin.mjs";
2
+ export { RoutinePlugin };
@@ -0,0 +1,110 @@
1
+ import { Routine } from "@dxos/compute";
2
+ import { meta } from "#meta";
3
+ import { Type } from "@dxos/echo";
4
+ import { translations as translations$1 } from "@dxos/react-ui-components/translations";
5
+ import { translations as translations$2 } from "@dxos/react-ui-form/translations";
6
+ //#region src/translations.ts
7
+ var translations = [
8
+ ...translations$1,
9
+ ...translations$2,
10
+ { "en-US": {
11
+ [Type.getTypename(Routine.Routine)]: {
12
+ "typename.label": "Routine",
13
+ "typename.label_zero": "Routines",
14
+ "typename.label_one": "Routine",
15
+ "typename.label_other": "Routines",
16
+ "object-name.placeholder": "New routine",
17
+ "add-object.label": "Add routine",
18
+ "rename-object.label": "Rename routine",
19
+ "delete-object.label": "Delete routine"
20
+ },
21
+ [meta.profile.key]: {
22
+ "plugin.name": "Routine",
23
+ "automation-panel.label": "Routines",
24
+ "create-panel.template.placeholder": "Search templates...",
25
+ "schedule.kind.once.label": "Once",
26
+ "schedule.kind.hourly.label": "Hourly",
27
+ "schedule.kind.daily.label": "Daily",
28
+ "schedule.kind.weekly.label": "Weekly",
29
+ "schedule.kind.monthly.label": "Monthly",
30
+ "schedule.kind.custom.label": "Custom",
31
+ "schedule.at.label": "At",
32
+ "schedule.on.label": "On",
33
+ "schedule.minute.label": "At minute",
34
+ "schedule.day.label": "Day of month",
35
+ "schedule.cron.label": "Cron",
36
+ "schedule.close.label": "Close",
37
+ "schedule.note.message": "Runs are staggered by a few minutes to spread server load.",
38
+ "command.placeholder": "Enter slash command...",
39
+ "template.placeholder": "Enter template...",
40
+ "run-prompt.label": "Run prompt",
41
+ "routine-running.label": "Running…",
42
+ "run.label": "Run",
43
+ "run-error.message": "Failed to run routine.",
44
+ "automation-name.label": "Name",
45
+ "general.title": "General",
46
+ "general.description": "Name and description.",
47
+ "actions.title": "Actions",
48
+ "actions.description": "What this routine runs.",
49
+ "action.placeholder": "Select an operation or instructions",
50
+ "action-input.label": "Input",
51
+ "action-kind.operation.label": "Operation",
52
+ "action-kind.instructions.label": "Instructions",
53
+ "triggers.title": "Triggers",
54
+ "triggers.description": "When this routine runs.",
55
+ "trigger-kind.placeholder": "Select trigger type",
56
+ "trigger-kind.timer.label": "Schedule",
57
+ "trigger-kind.timer.description": "Run on a recurring schedule or once at a future time.",
58
+ "trigger-kind.subscription.label": "Query",
59
+ "trigger-kind.subscription.description": "Run when objects matching a query change.",
60
+ "trigger-kind.webhook.label": "Webhook",
61
+ "trigger-kind.webhook.description": "Trigger from a POST request.",
62
+ "trigger-kind.feed.label": "Feed",
63
+ "trigger-kind.feed.description": "Run when a new item arrives in a feed.",
64
+ "trigger-kind.email.label": "Email",
65
+ "trigger-kind.email.description": "Run when an email is received.",
66
+ "trigger-kind.direct.label": "Direct",
67
+ "trigger-kind.direct.description": "Run only when invoked directly.",
68
+ "trigger-kind.clear.label": "Clear",
69
+ "trigger-kind.query-stub.message": "Query editing is not yet available.",
70
+ "trigger-kind.email-note.message": "Runs whenever a new email is received.",
71
+ "method.label": "Method",
72
+ "port.label": "Port",
73
+ "cron.placeholder": "0 0 * * *",
74
+ "feed.placeholder": "Select a feed",
75
+ "enabled.label": "Enabled",
76
+ "enabled.description": "Turn this routine on or off.",
77
+ "add-trigger.label": "Add trigger",
78
+ "add-trigger-first.message": "Add a trigger to enable.",
79
+ "remove-trigger.label": "Remove",
80
+ "select-action-first.message": "Select an action first.",
81
+ "automation-companion.label": "Routine",
82
+ "routine-runs.label": "Runs",
83
+ "history.empty.message": "No runs yet.",
84
+ "history.status.success.label": "Success",
85
+ "history.status.failure.label": "Failed",
86
+ "history.status.pending.label": "Running",
87
+ "no-routines.message": "No routines for this object.",
88
+ "routine-not-associated.message": "Not yet associated with this object.",
89
+ "routine-detached.message": "No longer associated with this object.",
90
+ "add-routine.label": "Add routine",
91
+ "routine-actions.label": "Routine actions",
92
+ "disabled.label": "Disabled",
93
+ "delete.label": "Delete",
94
+ "save.label": "Save",
95
+ "cancel.label": "Cancel",
96
+ "testing.title": "Testing",
97
+ "force-run.label": "Force run",
98
+ "reset-cursor.label": "Reset feed cursor",
99
+ "reset-cursor-confirm.label": "Confirm reset feed cursor",
100
+ "routine-verbose.label": "Manage routines",
101
+ "routine.description": "Manage where routines in this space run.",
102
+ "runtime.label": "Enable triggers",
103
+ "runtime.description": "Run this space's triggers. Individual triggers can be routed to the edge."
104
+ }
105
+ } }
106
+ ];
107
+ //#endregion
108
+ export { translations };
109
+
110
+ //# sourceMappingURL=translations.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"translations.mjs","names":[],"sources":["../../src/translations.ts"],"sourcesContent":["//\n// Copyright 2023 DXOS.org\n//\n\nimport { Routine } from '@dxos/compute';\nimport { Type } from '@dxos/echo';\nimport { type Resource } from '@dxos/react-ui';\nimport { translations as componentsTranslations } from '@dxos/react-ui-components/translations';\nimport { translations as formTranslations } from '@dxos/react-ui-form/translations';\n\nimport { meta } from '#meta';\n\nexport const translations: Resource[] = [\n ...componentsTranslations,\n ...formTranslations,\n {\n 'en-US': {\n [Type.getTypename(Routine.Routine)]: {\n 'typename.label': 'Routine',\n 'typename.label_zero': 'Routines',\n 'typename.label_one': 'Routine',\n 'typename.label_other': 'Routines',\n 'object-name.placeholder': 'New routine',\n 'add-object.label': 'Add routine',\n 'rename-object.label': 'Rename routine',\n 'delete-object.label': 'Delete routine',\n },\n [meta.profile.key]: {\n 'plugin.name': 'Routine',\n 'automation-panel.label': 'Routines',\n 'create-panel.template.placeholder': 'Search templates...',\n\n 'schedule.kind.once.label': 'Once',\n 'schedule.kind.hourly.label': 'Hourly',\n 'schedule.kind.daily.label': 'Daily',\n 'schedule.kind.weekly.label': 'Weekly',\n 'schedule.kind.monthly.label': 'Monthly',\n 'schedule.kind.custom.label': 'Custom',\n 'schedule.at.label': 'At',\n 'schedule.on.label': 'On',\n 'schedule.minute.label': 'At minute',\n 'schedule.day.label': 'Day of month',\n 'schedule.cron.label': 'Cron',\n 'schedule.close.label': 'Close',\n 'schedule.note.message': 'Runs are staggered by a few minutes to spread server load.',\n\n 'command.placeholder': 'Enter slash command...',\n 'template.placeholder': 'Enter template...',\n 'run-prompt.label': 'Run prompt',\n 'routine-running.label': 'Running…',\n 'run.label': 'Run',\n 'run-error.message': 'Failed to run routine.',\n\n 'automation-name.label': 'Name',\n 'general.title': 'General',\n 'general.description': 'Name and description.',\n\n 'actions.title': 'Actions',\n 'actions.description': 'What this routine runs.',\n 'action.placeholder': 'Select an operation or instructions',\n 'action-input.label': 'Input',\n 'action-kind.operation.label': 'Operation',\n 'action-kind.instructions.label': 'Instructions',\n\n 'triggers.title': 'Triggers',\n 'triggers.description': 'When this routine runs.',\n 'trigger-kind.placeholder': 'Select trigger type',\n 'trigger-kind.timer.label': 'Schedule',\n 'trigger-kind.timer.description': 'Run on a recurring schedule or once at a future time.',\n 'trigger-kind.subscription.label': 'Query',\n 'trigger-kind.subscription.description': 'Run when objects matching a query change.',\n 'trigger-kind.webhook.label': 'Webhook',\n 'trigger-kind.webhook.description': 'Trigger from a POST request.',\n 'trigger-kind.feed.label': 'Feed',\n 'trigger-kind.feed.description': 'Run when a new item arrives in a feed.',\n 'trigger-kind.email.label': 'Email',\n 'trigger-kind.email.description': 'Run when an email is received.',\n 'trigger-kind.direct.label': 'Direct',\n 'trigger-kind.direct.description': 'Run only when invoked directly.',\n 'trigger-kind.clear.label': 'Clear',\n 'trigger-kind.query-stub.message': 'Query editing is not yet available.',\n 'trigger-kind.email-note.message': 'Runs whenever a new email is received.',\n\n 'method.label': 'Method',\n 'port.label': 'Port',\n 'cron.placeholder': '0 0 * * *',\n 'feed.placeholder': 'Select a feed',\n 'enabled.label': 'Enabled',\n 'enabled.description': 'Turn this routine on or off.',\n 'add-trigger.label': 'Add trigger',\n 'add-trigger-first.message': 'Add a trigger to enable.',\n 'remove-trigger.label': 'Remove',\n 'select-action-first.message': 'Select an action first.',\n 'automation-companion.label': 'Routine',\n 'routine-runs.label': 'Runs',\n\n 'history.empty.message': 'No runs yet.',\n 'history.status.success.label': 'Success',\n 'history.status.failure.label': 'Failed',\n 'history.status.pending.label': 'Running',\n 'no-routines.message': 'No routines for this object.',\n 'routine-not-associated.message': 'Not yet associated with this object.',\n 'routine-detached.message': 'No longer associated with this object.',\n 'add-routine.label': 'Add routine',\n 'routine-actions.label': 'Routine actions',\n 'disabled.label': 'Disabled',\n 'delete.label': 'Delete',\n 'save.label': 'Save',\n 'cancel.label': 'Cancel',\n\n 'testing.title': 'Testing',\n 'force-run.label': 'Force run',\n 'reset-cursor.label': 'Reset feed cursor',\n 'reset-cursor-confirm.label': 'Confirm reset feed cursor',\n\n 'routine-verbose.label': 'Manage routines',\n 'routine.description': 'Manage where routines in this space run.',\n\n 'runtime.label': 'Enable triggers',\n 'runtime.description': \"Run this space's triggers. Individual triggers can be routed to the edge.\",\n },\n },\n },\n] as const satisfies Resource[];\n"],"mappings":";;;;;;AAYA,IAAa,eAA2B;CACtC,GAAG;CACH,GAAG;CACH,EACE,SAAS;GACN,KAAK,YAAY,QAAQ,OAAO,IAAI;GACnC,kBAAkB;GAClB,uBAAuB;GACvB,sBAAsB;GACtB,wBAAwB;GACxB,2BAA2B;GAC3B,oBAAoB;GACpB,uBAAuB;GACvB,uBAAuB;EACzB;GACC,KAAK,QAAQ,MAAM;GAClB,eAAe;GACf,0BAA0B;GAC1B,qCAAqC;GAErC,4BAA4B;GAC5B,8BAA8B;GAC9B,6BAA6B;GAC7B,8BAA8B;GAC9B,+BAA+B;GAC/B,8BAA8B;GAC9B,qBAAqB;GACrB,qBAAqB;GACrB,yBAAyB;GACzB,sBAAsB;GACtB,uBAAuB;GACvB,wBAAwB;GACxB,yBAAyB;GAEzB,uBAAuB;GACvB,wBAAwB;GACxB,oBAAoB;GACpB,yBAAyB;GACzB,aAAa;GACb,qBAAqB;GAErB,yBAAyB;GACzB,iBAAiB;GACjB,uBAAuB;GAEvB,iBAAiB;GACjB,uBAAuB;GACvB,sBAAsB;GACtB,sBAAsB;GACtB,+BAA+B;GAC/B,kCAAkC;GAElC,kBAAkB;GAClB,wBAAwB;GACxB,4BAA4B;GAC5B,4BAA4B;GAC5B,kCAAkC;GAClC,mCAAmC;GACnC,yCAAyC;GACzC,8BAA8B;GAC9B,oCAAoC;GACpC,2BAA2B;GAC3B,iCAAiC;GACjC,4BAA4B;GAC5B,kCAAkC;GAClC,6BAA6B;GAC7B,mCAAmC;GACnC,4BAA4B;GAC5B,mCAAmC;GACnC,mCAAmC;GAEnC,gBAAgB;GAChB,cAAc;GACd,oBAAoB;GACpB,oBAAoB;GACpB,iBAAiB;GACjB,uBAAuB;GACvB,qBAAqB;GACrB,6BAA6B;GAC7B,wBAAwB;GACxB,+BAA+B;GAC/B,8BAA8B;GAC9B,sBAAsB;GAEtB,yBAAyB;GACzB,gCAAgC;GAChC,gCAAgC;GAChC,gCAAgC;GAChC,uBAAuB;GACvB,kCAAkC;GAClC,4BAA4B;GAC5B,qBAAqB;GACrB,yBAAyB;GACzB,kBAAkB;GAClB,gBAAgB;GAChB,cAAc;GACd,gBAAgB;GAEhB,iBAAiB;GACjB,mBAAmB;GACnB,sBAAsB;GACtB,8BAA8B;GAE9B,yBAAyB;GACzB,uBAAuB;GAEvB,iBAAiB;GACjB,uBAAuB;EACzB;CACF,EACF;AACF"}
@@ -0,0 +1,2 @@
1
+ import { a as RoutineCapabilities_exports, c as TriggerTemplate, r as RoutineOperation_exports, s as AutomationAction } from "./chunk-types.mjs";
2
+ export { AutomationAction, RoutineCapabilities_exports as RoutineCapabilities, RoutineOperation_exports as RoutineOperation, TriggerTemplate };
@@ -1 +1 @@
1
- {"version":3,"file":"RoutinePlugin.d.ts","sourceRoot":"","sources":["../../../src/RoutinePlugin.tsx"],"names":[],"mappings":"AAIA,OAAO,EAAqC,MAAM,EAAE,MAAM,qBAAqB,CAAC;AAuBhF,eAAO,MAAM,aAAa,4BA4BzB,CAAC;eAEa,aAAa"}
1
+ {"version":3,"file":"RoutinePlugin.d.ts","sourceRoot":"","sources":["../../../src/RoutinePlugin.tsx"],"names":[],"mappings":"AAIA,OAAO,EAAqC,MAAM,EAAE,MAAM,qBAAqB,CAAC;AAqBhF,eAAO,MAAM,aAAa,4BA4BzB,CAAC;eAEa,aAAa"}
@@ -1 +1 @@
1
- {"version":3,"file":"RoutinePlugin.node.d.ts","sourceRoot":"","sources":["../../../src/RoutinePlugin.node.ts"],"names":[],"mappings":"AAIA,OAAO,EAAqC,MAAM,EAAE,MAAM,qBAAqB,CAAC;AAkBhF,eAAO,MAAM,aAAa,4BAuBzB,CAAC;eAEa,aAAa"}
1
+ {"version":3,"file":"RoutinePlugin.node.d.ts","sourceRoot":"","sources":["../../../src/RoutinePlugin.node.ts"],"names":[],"mappings":"AAIA,OAAO,EAAqC,MAAM,EAAE,MAAM,qBAAqB,CAAC;AAiBhF,eAAO,MAAM,aAAa,4BAuBzB,CAAC;eAEa,aAAa"}
@@ -1 +1 @@
1
- {"version":3,"file":"RoutinePlugin.workerd.d.ts","sourceRoot":"","sources":["../../../src/RoutinePlugin.workerd.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,MAAM,EAAE,MAAM,qBAAqB,CAAC;AAQ7C,eAAO,MAAM,aAAa,4BASzB,CAAC;eAEa,aAAa"}
1
+ {"version":3,"file":"RoutinePlugin.workerd.d.ts","sourceRoot":"","sources":["../../../src/RoutinePlugin.workerd.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,MAAM,EAAE,MAAM,qBAAqB,CAAC;AAO7C,eAAO,MAAM,aAAa,4BASzB,CAAC;eAEa,aAAa"}
@@ -1,5 +1,5 @@
1
1
  import * as Effect from 'effect/Effect';
2
2
  import { Capability } from '@dxos/app-framework';
3
- declare const _default: (props: void) => Effect.Effect<Capability.Any, never, never>;
3
+ declare const _default: (props: void) => Effect.Effect<Capability.Any, never, import("effect/Scope").Scope>;
4
4
  export default _default;
5
5
  //# sourceMappingURL=app-graph-builder.d.ts.map
@@ -1,5 +1,5 @@
1
1
  import * as Effect from 'effect/Effect';
2
2
  import { Capability } from '@dxos/app-framework';
3
- declare const _default: (props: void) => Effect.Effect<Capability.Any, never, never>;
3
+ declare const _default: (props: void) => Effect.Effect<Capability.Any, never, import("effect/Scope").Scope>;
4
4
  export default _default;
5
5
  //# sourceMappingURL=create-object.d.ts.map
@@ -1,7 +1,6 @@
1
1
  import { Capability } from '@dxos/app-framework';
2
2
  import { OperationHandlerSet } from '@dxos/compute';
3
3
  export declare const AppGraphBuilder: Capability.LazyCapability<void, Capability.ModuleReturn, Error>;
4
- export declare const NavigationResolver: Capability.LazyCapability<void, Capability.ModuleReturn, Error>;
5
4
  export declare const CreateObject: Capability.LazyCapability<void, Capability.ModuleReturn, Error>;
6
5
  export declare const LayerSpecs: Capability.LazyCapability<void, Capability.ModuleReturn, Error>;
7
6
  export declare const OperationHandler: Capability.LazyCapability<OperationHandlerSet.OperationHandlerSet, Capability.ModuleReturn, Error>;
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/capabilities/index.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,UAAU,EAAE,MAAM,qBAAqB,CAAC;AACjD,OAAO,EAAE,mBAAmB,EAAE,MAAM,eAAe,CAAC;AAEpD,eAAO,MAAM,eAAe,iEAA0E,CAAC;AACvG,eAAO,MAAM,kBAAkB,iEAA+E,CAAC;AAC/G,eAAO,MAAM,YAAY,iEAAmE,CAAC;AAC7F,eAAO,MAAM,UAAU,iEAAuF,CAAC;AAC/G,eAAO,MAAM,gBAAgB,oGAG5B,CAAC;AACF,eAAO,MAAM,YAAY,iEAAmE,CAAC;AAC7F,eAAO,MAAM,YAAY,iEAAmE,CAAC;AAC7F,eAAO,MAAM,SAAS,iEAA4D,CAAC;AACnF,eAAO,MAAM,wBAAwB,iEAGpC,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/capabilities/index.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,UAAU,EAAE,MAAM,qBAAqB,CAAC;AACjD,OAAO,EAAE,mBAAmB,EAAE,MAAM,eAAe,CAAC;AAEpD,eAAO,MAAM,eAAe,iEAA0E,CAAC;AACvG,eAAO,MAAM,YAAY,iEAAmE,CAAC;AAC7F,eAAO,MAAM,UAAU,iEAAuF,CAAC;AAC/G,eAAO,MAAM,gBAAgB,oGAG5B,CAAC;AACF,eAAO,MAAM,YAAY,iEAAmE,CAAC;AAC7F,eAAO,MAAM,YAAY,iEAAmE,CAAC;AAC7F,eAAO,MAAM,SAAS,iEAA4D,CAAC;AACnF,eAAO,MAAM,wBAAwB,iEAGpC,CAAC"}