@skaile/workspaces 0.21.0 → 0.22.0-beta.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (212) hide show
  1. package/CHANGELOG.md +40 -0
  2. package/dist/{asset-feeds-CI76R7FI.js → asset-feeds-PJDJ3QYI.js} +11 -11
  3. package/dist/{asset-feeds-CI76R7FI.js.map → asset-feeds-PJDJ3QYI.js.map} +1 -1
  4. package/dist/asset-manager/index.js +9 -9
  5. package/dist/asset-manager/installer.js +8 -8
  6. package/dist/base-assets/connectors/deploy.js +10 -9
  7. package/dist/base-assets/connectors/devserver.js +10 -9
  8. package/dist/base-assets/connectors/flow/adapter.js +10 -9
  9. package/dist/base-assets/connectors/flow/run-flow.js +11 -10
  10. package/dist/base-assets/connectors/flow.js +10 -9
  11. package/dist/base-assets/connectors/git.js +10 -9
  12. package/dist/base-assets/connectors/gmail.js +10 -9
  13. package/dist/base-assets/connectors/googledrive.js +10 -9
  14. package/dist/base-assets/connectors/local.js +10 -9
  15. package/dist/base-assets/connectors/mattermost.js +10 -9
  16. package/dist/base-assets/connectors/memory.js +10 -9
  17. package/dist/base-assets/connectors/minio.js +10 -9
  18. package/dist/base-assets/connectors/postgres.js +10 -9
  19. package/dist/base-assets/connectors/s3.js +10 -9
  20. package/dist/base-assets/connectors/sharepoint.js +10 -9
  21. package/dist/base-assets/connectors/sqlite.js +10 -9
  22. package/dist/base-assets/connectors/static-server.js +10 -9
  23. package/dist/base-assets/connectors/tunnel.js +10 -9
  24. package/dist/base-assets/connectors/webdav.js +10 -9
  25. package/dist/base-assets/connectors/xstate-store.js +10 -9
  26. package/dist/base-assets/connectors/xstate.js +10 -9
  27. package/dist/bridge/drivers/claude-sdk.js +13 -3
  28. package/dist/bridge/drivers/claude-sdk.js.map +1 -1
  29. package/dist/bridge/drivers/codex.js +13 -3
  30. package/dist/bridge/drivers/codex.js.map +1 -1
  31. package/dist/bridge/drivers/echo.js +13 -4
  32. package/dist/bridge/drivers/echo.js.map +1 -1
  33. package/dist/bridge/drivers/omp.js +13 -3
  34. package/dist/bridge/drivers/omp.js.map +1 -1
  35. package/dist/bridge/index.js +3 -2
  36. package/dist/bridge/src/drivers/claude-sdk.d.ts +7 -0
  37. package/dist/bridge/src/drivers/claude-sdk.d.ts.map +1 -1
  38. package/dist/bridge/src/drivers/codex.d.ts +7 -0
  39. package/dist/bridge/src/drivers/codex.d.ts.map +1 -1
  40. package/dist/bridge/src/drivers/echo.d.ts +6 -0
  41. package/dist/bridge/src/drivers/echo.d.ts.map +1 -1
  42. package/dist/bridge/src/drivers/omp.d.ts +6 -0
  43. package/dist/bridge/src/drivers/omp.d.ts.map +1 -1
  44. package/dist/bridge/src/registry.d.ts +32 -34
  45. package/dist/bridge/src/registry.d.ts.map +1 -1
  46. package/dist/{chunk-DEQ3OOTU.js → chunk-2DNSSQ22.js} +7 -7
  47. package/dist/{chunk-DEQ3OOTU.js.map → chunk-2DNSSQ22.js.map} +1 -1
  48. package/dist/{chunk-ZWIG55ZX.js → chunk-2XY6732A.js} +3 -3
  49. package/dist/{chunk-ZWIG55ZX.js.map → chunk-2XY6732A.js.map} +1 -1
  50. package/dist/{chunk-2WVQMRIE.js → chunk-CSDQBWE6.js} +5 -5
  51. package/dist/{chunk-2WVQMRIE.js.map → chunk-CSDQBWE6.js.map} +1 -1
  52. package/dist/{chunk-KFDTS7RX.js → chunk-F3MGZ5E6.js} +3 -3
  53. package/dist/{chunk-KFDTS7RX.js.map → chunk-F3MGZ5E6.js.map} +1 -1
  54. package/dist/{chunk-XAVM2BAJ.js → chunk-G6GKWGOW.js} +114 -619
  55. package/dist/chunk-G6GKWGOW.js.map +1 -0
  56. package/dist/{chunk-H45ANMIU.js → chunk-GKM6MDUC.js} +3 -3
  57. package/dist/{chunk-H45ANMIU.js.map → chunk-GKM6MDUC.js.map} +1 -1
  58. package/dist/{chunk-4ACWI5YT.js → chunk-IGQEXBBG.js} +44 -36
  59. package/dist/chunk-IGQEXBBG.js.map +1 -0
  60. package/dist/{chunk-RDH4SSMH.js → chunk-J2FCO6TM.js} +2 -2
  61. package/dist/{chunk-RDH4SSMH.js.map → chunk-J2FCO6TM.js.map} +1 -1
  62. package/dist/{chunk-BSY56QS7.js → chunk-KA46DUM4.js} +3 -3
  63. package/dist/{chunk-BSY56QS7.js.map → chunk-KA46DUM4.js.map} +1 -1
  64. package/dist/{chunk-XGWGLIHZ.js → chunk-MO4JPTRD.js} +4 -4
  65. package/dist/{chunk-XGWGLIHZ.js.map → chunk-MO4JPTRD.js.map} +1 -1
  66. package/dist/{chunk-G4BR355S.js → chunk-NGC7ZQI4.js} +10 -10
  67. package/dist/{chunk-G4BR355S.js.map → chunk-NGC7ZQI4.js.map} +1 -1
  68. package/dist/{chunk-W5DFC35Z.js → chunk-RENHNO4J.js} +81 -4
  69. package/dist/chunk-RENHNO4J.js.map +1 -0
  70. package/dist/{chunk-4S4TZDCD.js → chunk-SL6JVGRD.js} +3 -3
  71. package/dist/{chunk-4S4TZDCD.js.map → chunk-SL6JVGRD.js.map} +1 -1
  72. package/dist/{chunk-5QNQLSBW.js → chunk-TKOLD2O7.js} +22 -5
  73. package/dist/chunk-TKOLD2O7.js.map +1 -0
  74. package/dist/{chunk-DFUXWNTS.js → chunk-TTY56FQQ.js} +4 -4
  75. package/dist/{chunk-DFUXWNTS.js.map → chunk-TTY56FQQ.js.map} +1 -1
  76. package/dist/chunk-UZRY5UI2.js +96 -0
  77. package/dist/chunk-UZRY5UI2.js.map +1 -0
  78. package/dist/{chunk-NCUTHLRV.js → chunk-UZVHJ7LX.js} +4 -4
  79. package/dist/{chunk-NCUTHLRV.js.map → chunk-UZVHJ7LX.js.map} +1 -1
  80. package/dist/{chunk-FRPKLIEZ.js → chunk-WIR34WMU.js} +3 -3
  81. package/dist/{chunk-FRPKLIEZ.js.map → chunk-WIR34WMU.js.map} +1 -1
  82. package/dist/{chunk-37JKX6D7.js → chunk-X5Y4EGZB.js} +2 -2
  83. package/dist/{chunk-37JKX6D7.js.map → chunk-X5Y4EGZB.js.map} +1 -1
  84. package/dist/{chunk-S2OVTCAL.js → chunk-XHFMUGDD.js} +3 -3
  85. package/dist/{chunk-S2OVTCAL.js.map → chunk-XHFMUGDD.js.map} +1 -1
  86. package/dist/cli/index.js +701 -413
  87. package/dist/cli/index.js.map +1 -1
  88. package/dist/cli/src/commands/deploy.d.ts +24 -0
  89. package/dist/cli/src/commands/deploy.d.ts.map +1 -0
  90. package/dist/cli/src/commands/integration.d.ts +19 -0
  91. package/dist/cli/src/commands/integration.d.ts.map +1 -0
  92. package/dist/cli/src/commands/plugin-registry-cmd.d.ts +22 -0
  93. package/dist/cli/src/commands/plugin-registry-cmd.d.ts.map +1 -0
  94. package/dist/cli/src/commands/serve.d.ts.map +1 -1
  95. package/dist/cli/src/plugin-store/index.d.ts +37 -0
  96. package/dist/cli/src/plugin-store/index.d.ts.map +1 -0
  97. package/dist/cli/src/plugin-store/load.d.ts +35 -0
  98. package/dist/cli/src/plugin-store/load.d.ts.map +1 -0
  99. package/dist/cli/src/plugin-store/paths.d.ts +23 -0
  100. package/dist/cli/src/plugin-store/paths.d.ts.map +1 -0
  101. package/dist/cli/src/plugin-store/reconcile.d.ts +50 -0
  102. package/dist/cli/src/plugin-store/reconcile.d.ts.map +1 -0
  103. package/dist/cli/src/plugin-store/spec.d.ts +25 -0
  104. package/dist/cli/src/plugin-store/spec.d.ts.map +1 -0
  105. package/dist/connectors/config.js +8 -8
  106. package/dist/connectors/index.js +10 -9
  107. package/dist/connectors/src/connector-manager.d.ts.map +1 -1
  108. package/dist/connectors/src/connector-registry.d.ts +42 -22
  109. package/dist/connectors/src/connector-registry.d.ts.map +1 -1
  110. package/dist/connectors/src/index.d.ts +2 -3
  111. package/dist/connectors/src/index.d.ts.map +1 -1
  112. package/dist/connectors-shared/index.js +8 -0
  113. package/dist/connectors-shared/index.js.map +1 -0
  114. package/dist/connectors-shared/src/index.d.ts +11 -0
  115. package/dist/connectors-shared/src/index.d.ts.map +1 -0
  116. package/dist/connectors-shared/src/schemas.d.ts +10 -0
  117. package/dist/connectors-shared/src/schemas.d.ts.map +1 -0
  118. package/dist/connectors-shared/src/types.d.ts +11 -0
  119. package/dist/connectors-shared/src/types.d.ts.map +1 -0
  120. package/dist/core/index.js +7 -7
  121. package/dist/core/manifest.js +2 -2
  122. package/dist/core/models.js +1 -1
  123. package/dist/core/runtime-assets.js +4 -4
  124. package/dist/core/src/index.d.ts +2 -2
  125. package/dist/core/src/index.d.ts.map +1 -1
  126. package/dist/core/src/lock.d.ts +20 -1
  127. package/dist/core/src/lock.d.ts.map +1 -1
  128. package/dist/core/src/models.d.ts +13 -0
  129. package/dist/core/src/models.d.ts.map +1 -1
  130. package/dist/core/src/workspace-config.d.ts +14 -0
  131. package/dist/core/src/workspace-config.d.ts.map +1 -1
  132. package/dist/core/src/workspace-yaml-editor.d.ts +20 -0
  133. package/dist/core/src/workspace-yaml-editor.d.ts.map +1 -1
  134. package/dist/core/workspace-config.js +3 -3
  135. package/dist/deploy/index.js +454 -0
  136. package/dist/deploy/index.js.map +1 -0
  137. package/dist/deploy/src/handle-store.d.ts +22 -0
  138. package/dist/deploy/src/handle-store.d.ts.map +1 -0
  139. package/dist/deploy/src/index.d.ts +21 -0
  140. package/dist/deploy/src/index.d.ts.map +1 -0
  141. package/dist/deploy/src/targets/container-runtime.d.ts +38 -0
  142. package/dist/deploy/src/targets/container-runtime.d.ts.map +1 -0
  143. package/dist/deploy/src/targets/docker.d.ts +18 -0
  144. package/dist/deploy/src/targets/docker.d.ts.map +1 -0
  145. package/dist/deploy/src/targets/local.d.ts +30 -0
  146. package/dist/deploy/src/targets/local.d.ts.map +1 -0
  147. package/dist/deploy/src/targets/podman.d.ts +18 -0
  148. package/dist/deploy/src/targets/podman.d.ts.map +1 -0
  149. package/dist/deploy/src/targets/port.d.ts +10 -0
  150. package/dist/deploy/src/targets/port.d.ts.map +1 -0
  151. package/dist/deploy/src/targets/stream-lines.d.ts +44 -0
  152. package/dist/deploy/src/targets/stream-lines.d.ts.map +1 -0
  153. package/dist/discovery/index.js +3 -3
  154. package/dist/{ensure-sources-IDVQ77NJ.js → ensure-sources-COGVKY44.js} +11 -11
  155. package/dist/{ensure-sources-IDVQ77NJ.js.map → ensure-sources-COGVKY44.js.map} +1 -1
  156. package/dist/{flows-6BNO4GKK.js → flows-DYFTPCPM.js} +4 -4
  157. package/dist/{flows-6BNO4GKK.js.map → flows-DYFTPCPM.js.map} +1 -1
  158. package/dist/library/index.js +4 -4
  159. package/dist/open-library-DWAQFUSQ.js +13 -0
  160. package/dist/{open-library-IOYWFK7M.js.map → open-library-DWAQFUSQ.js.map} +1 -1
  161. package/dist/plugin-registry/index.js +4 -0
  162. package/dist/plugin-registry/index.js.map +1 -0
  163. package/dist/plugin-registry/src/context.d.ts +29 -0
  164. package/dist/plugin-registry/src/context.d.ts.map +1 -0
  165. package/dist/plugin-registry/src/deploy-handle.d.ts +60 -0
  166. package/dist/plugin-registry/src/deploy-handle.d.ts.map +1 -0
  167. package/dist/plugin-registry/src/errors.d.ts +23 -0
  168. package/dist/plugin-registry/src/errors.d.ts.map +1 -0
  169. package/dist/plugin-registry/src/index.d.ts +16 -0
  170. package/dist/plugin-registry/src/index.d.ts.map +1 -0
  171. package/dist/plugin-registry/src/internal.d.ts +13 -0
  172. package/dist/plugin-registry/src/internal.d.ts.map +1 -0
  173. package/dist/plugin-registry/src/registry.d.ts +25 -0
  174. package/dist/plugin-registry/src/registry.d.ts.map +1 -0
  175. package/dist/plugin-registry/src/targets.d.ts +42 -0
  176. package/dist/plugin-registry/src/targets.d.ts.map +1 -0
  177. package/dist/plugin-store-6OENKNFW.js +144 -0
  178. package/dist/plugin-store-6OENKNFW.js.map +1 -0
  179. package/dist/runner/index.js +14 -13
  180. package/dist/sdk/asset-manager.js +9 -9
  181. package/dist/sdk/bridge.js +3 -2
  182. package/dist/sdk/core.js +7 -7
  183. package/dist/sdk/index.js +15 -14
  184. package/dist/sdk/index.js.map +1 -1
  185. package/dist/sdk/runner.js +14 -13
  186. package/dist/{setup-AIOLUTKV.js → setup-ACMP3QZC.js} +12 -11
  187. package/dist/setup-ACMP3QZC.js.map +1 -0
  188. package/dist/store-client-ZSLNOOQG.js +14 -0
  189. package/dist/{store-client-CYEH2GKC.js.map → store-client-ZSLNOOQG.js.map} +1 -1
  190. package/dist/tui/index.js +14 -13
  191. package/dist/tui/index.js.map +1 -1
  192. package/dist/workspace-plugin/adapters/mcp.js +2 -2
  193. package/dist/workspace-plugin/adapters/omp.js +3 -3
  194. package/dist/workspace-plugin/index.js +1 -1
  195. package/package.json +20 -23
  196. package/dist/base-assets/connectors/redis/adapter.d.ts +0 -39
  197. package/dist/base-assets/connectors/redis/adapter.d.ts.map +0 -1
  198. package/dist/base-assets/connectors/redis.js +0 -20
  199. package/dist/base-assets/connectors/redis.js.map +0 -1
  200. package/dist/base-assets/connectors/yjs/adapter.d.ts +0 -50
  201. package/dist/base-assets/connectors/yjs/adapter.d.ts.map +0 -1
  202. package/dist/base-assets/connectors/yjs.js +0 -20
  203. package/dist/base-assets/connectors/yjs.js.map +0 -1
  204. package/dist/chunk-4ACWI5YT.js.map +0 -1
  205. package/dist/chunk-5QNQLSBW.js.map +0 -1
  206. package/dist/chunk-W5DFC35Z.js.map +0 -1
  207. package/dist/chunk-XAVM2BAJ.js.map +0 -1
  208. package/dist/cli/src/commands/plugin.d.ts +0 -14
  209. package/dist/cli/src/commands/plugin.d.ts.map +0 -1
  210. package/dist/open-library-IOYWFK7M.js +0 -13
  211. package/dist/setup-AIOLUTKV.js.map +0 -1
  212. package/dist/store-client-CYEH2GKC.js +0 -14
package/dist/cli/index.js CHANGED
@@ -1,18 +1,18 @@
1
1
  #!/usr/bin/env node
2
- import { openCatalogSource, openLibrary, createFullRegistry, openLibraryManager } from '../chunk-NCUTHLRV.js';
3
- import { logErr, S, logOk, colorRef, logInfo, logWarn, kindColorPad, kindColor, formatRelativeTime } from '../chunk-4NDWKA64.js';
4
- import { getStoreConfig, storeFetch, saveStoreTokens, clearStoreTokens, isStoreAuthenticated } from '../chunk-KFDTS7RX.js';
5
2
  import { AI_RESOURCES } from '../chunk-2M3XTMOL.js';
3
+ import { openCatalogSource, openLibrary, createFullRegistry, openLibraryManager } from '../chunk-UZVHJ7LX.js';
4
+ import { logErr, S, logOk, colorRef, logInfo, logWarn, kindColorPad, kindColor, formatRelativeTime } from '../chunk-4NDWKA64.js';
5
+ import { getStoreConfig, storeFetch, saveStoreTokens, clearStoreTokens, isStoreAuthenticated } from '../chunk-F3MGZ5E6.js';
6
6
  import { LocalSecretsProvider } from '../chunk-JDX54X4Y.js';
7
- import { resolveLibraryDir, LocalCatalogSource, skaileHomeDir } from '../chunk-BSY56QS7.js';
7
+ import { resolveLibraryDir, LocalCatalogSource, skaileHomeDir } from '../chunk-KA46DUM4.js';
8
8
  import '../chunk-R7FOF242.js';
9
- import '../chunk-4S4TZDCD.js';
9
+ import '../chunk-SL6JVGRD.js';
10
10
  import '../chunk-OKRUTSG7.js';
11
- import { runFlow, resumeFlow } from '../chunk-2WVQMRIE.js';
11
+ import { runFlow, resumeFlow } from '../chunk-CSDQBWE6.js';
12
12
  import '../chunk-GCJXPUHG.js';
13
13
  import { validateFlowVersions, parseSkillFrontmatter } from '../chunk-IPUYL6TD.js';
14
- import { runAgentChat, loadSessionById, loadSession, listSessions, setCurrentSession, deleteSession, clearSession, loadAgentManifest, compileComposition, MarkdownStreamer, resolveMixin } from '../chunk-G4BR355S.js';
15
- import { buildClaudePluginFiles } from '../chunk-RDH4SSMH.js';
14
+ import { runAgentChat, loadSessionById, loadSession, listSessions, setCurrentSession, deleteSession, clearSession, loadAgentManifest, compileComposition, MarkdownStreamer, resolveMixin } from '../chunk-NGC7ZQI4.js';
15
+ import { buildClaudePluginFiles } from '../chunk-J2FCO6TM.js';
16
16
  import '../chunk-X5YPJV4N.js';
17
17
  import '../chunk-O7SG5PC2.js';
18
18
  import '../chunk-W2O5LWYU.js';
@@ -20,29 +20,30 @@ import '../chunk-7PTP3SQJ.js';
20
20
  import '../chunk-PBWMV5GM.js';
21
21
  import '../chunk-W3UDISS2.js';
22
22
  import '../chunk-TDSRLMDB.js';
23
- import '../chunk-S2OVTCAL.js';
23
+ import '../chunk-XHFMUGDD.js';
24
24
  import '../chunk-DQWREFRQ.js';
25
25
  import '../chunk-KOVLSBXK.js';
26
26
  import '../chunk-RRVQAE5D.js';
27
- import '../chunk-4ACWI5YT.js';
28
- import '../chunk-XAVM2BAJ.js';
29
- import '../chunk-H45ANMIU.js';
27
+ import '../chunk-IGQEXBBG.js';
28
+ import '../chunk-G6GKWGOW.js';
29
+ import '../chunk-GKM6MDUC.js';
30
30
  import '../chunk-6MB7CRME.js';
31
31
  import '../chunk-QAVZOJCV.js';
32
+ import '../chunk-UZRY5UI2.js';
32
33
  import { loadAllFlows } from '../chunk-ICS76R4T.js';
33
34
  import '../chunk-GZWJGNNN.js';
34
35
  import '../chunk-FVTV7M76.js';
35
- import { AssetManager } from '../chunk-DEQ3OOTU.js';
36
- import '../chunk-XGWGLIHZ.js';
37
- import { readLock, resolveSettings, globalSettingsPath, projectSettingsPath, loadSettings, saveSettings, portableSpawn, portableSpawnSync, WorkspaceYamlEditor } from '../chunk-W5DFC35Z.js';
38
- import '../chunk-JKNWJ64A.js';
39
- import { SUPPORTED_DRIVER_TARGETS } from '../chunk-O4JH3KUE.js';
36
+ import { AssetManager } from '../chunk-2DNSSQ22.js';
37
+ import '../chunk-MO4JPTRD.js';
38
+ import { readLock, resolveSettings, globalSettingsPath, projectSettingsPath, loadSettings, saveSettings, portableSpawn, portableSpawnSync, WorkspaceYamlEditor } from '../chunk-RENHNO4J.js';
40
39
  import { DRIVER_DEFAULTS } from '../chunk-K5GBV4SA.js';
41
40
  import '../chunk-KLNL7QHN.js';
42
- import '../chunk-DFUXWNTS.js';
43
- import { resolveSkWorkspaceConfig, resolveAgentDir, findWorkspaceRoot, workspaceConfigFilename } from '../chunk-5QNQLSBW.js';
44
- import '../chunk-FRPKLIEZ.js';
45
- import { ASSET_KINDS } from '../chunk-37JKX6D7.js';
41
+ import '../chunk-TTY56FQQ.js';
42
+ import { resolveSkWorkspaceConfig, resolveAgentDir, findWorkspaceRoot, workspaceConfigFilename } from '../chunk-TKOLD2O7.js';
43
+ import '../chunk-WIR34WMU.js';
44
+ import { ASSET_KINDS } from '../chunk-X5Y4EGZB.js';
45
+ import '../chunk-JKNWJ64A.js';
46
+ import { SUPPORTED_DRIVER_TARGETS } from '../chunk-O4JH3KUE.js';
46
47
  import { openSqlite } from '../chunk-24UIWON4.js';
47
48
  import '../chunk-KTBKW2FI.js';
48
49
  import '../chunk-UQ6LFBPZ.js';
@@ -53,8 +54,8 @@ import '../chunk-LV2HPH3C.js';
53
54
  import '../chunk-NSBPE2FW.js';
54
55
  import * as fs10 from 'fs';
55
56
  import fs10__default, { readFileSync, existsSync, writeFileSync, rmSync, statSync } from 'fs';
56
- import * as path15 from 'path';
57
- import path15__default, { resolve, join } from 'path';
57
+ import * as path14 from 'path';
58
+ import path14__default, { resolve, join } from 'path';
58
59
  import { fileURLToPath } from 'url';
59
60
  import { Help, Command, Option } from 'commander';
60
61
  import * as p5 from '@clack/prompts';
@@ -103,10 +104,10 @@ function makeAssetCommand() {
103
104
  );
104
105
  process.exit(1);
105
106
  }
106
- const basename2 = path15.basename(srcPath);
107
- const destDir = target.structure === "domain" && opts.domain ? path15.join(target.path, opts.domain) : target.path;
107
+ const basename2 = path14.basename(srcPath);
108
+ const destDir = target.structure === "domain" && opts.domain ? path14.join(target.path, opts.domain) : target.path;
108
109
  fs10.mkdirSync(destDir, { recursive: true });
109
- const destPath = path15.join(destDir, basename2);
110
+ const destPath = path14.join(destDir, basename2);
110
111
  if (fs10.existsSync(destPath)) {
111
112
  logErr(`Destination already exists: ${destPath}`);
112
113
  process.exit(1);
@@ -119,7 +120,7 @@ function makeAssetCommand() {
119
120
  fs10.renameSync(srcPath, destPath);
120
121
  break;
121
122
  case "link":
122
- fs10.symlinkSync(path15.resolve(srcPath), destPath);
123
+ fs10.symlinkSync(path14.resolve(srcPath), destPath);
123
124
  break;
124
125
  }
125
126
  if (target.backend === "git" && opts.commit) {
@@ -167,17 +168,17 @@ function makeAssetCommand() {
167
168
  }
168
169
  const manifestPath = def.manifest.path;
169
170
  const candidateSubpath = typeof manifestPath === "string" && manifestPath.length > 0 ? manifestPath : def.name;
170
- const srcPath = path15.join(lib.path, candidateSubpath);
171
+ const srcPath = path14.join(lib.path, candidateSubpath);
171
172
  if (!fs10.existsSync(srcPath)) {
172
173
  logErr(`Asset path not found: ${srcPath}`);
173
174
  process.exit(1);
174
175
  }
175
- const destPath = path15.join(target, candidateSubpath);
176
- fs10.mkdirSync(path15.dirname(destPath), { recursive: true });
176
+ const destPath = path14.join(target, candidateSubpath);
177
+ fs10.mkdirSync(path14.dirname(destPath), { recursive: true });
177
178
  if (opts.mode === "copy") {
178
179
  fs10.cpSync(srcPath, destPath, { recursive: true });
179
180
  } else {
180
- fs10.symlinkSync(path15.resolve(srcPath), destPath);
181
+ fs10.symlinkSync(path14.resolve(srcPath), destPath);
181
182
  }
182
183
  logOk(`Installed ${ref} \u2192 ${destPath} (${opts.mode})`);
183
184
  } finally {
@@ -271,7 +272,7 @@ function makeSearchCommand() {
271
272
  const showLocal = !opts.store;
272
273
  const showStore = !opts.local;
273
274
  if (showLocal) {
274
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
275
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
275
276
  const entries = am2.search(query, kind);
276
277
  if (entries.length === 0) {
277
278
  if (!showStore) {
@@ -308,7 +309,7 @@ function makeSearchCommand() {
308
309
  }
309
310
  if (showStore) {
310
311
  try {
311
- const { getStoreConfig: getStoreConfig2, storeFetch: storeFetch2 } = await import('../store-client-CYEH2GKC.js');
312
+ const { getStoreConfig: getStoreConfig2, storeFetch: storeFetch2 } = await import('../store-client-ZSLNOOQG.js');
312
313
  const config = getStoreConfig2();
313
314
  const params = {};
314
315
  if (query) params.q = query;
@@ -337,7 +338,7 @@ function makeSearchCommand() {
337
338
  function makeAddCommand() {
338
339
  return new Command("add").description("Add to skaile.yaml + deploy").argument("<ref>", "Asset reference (kind:name[@repo])").option("--project-dir <path>", "Project directory", process.cwd()).option("--global", "Deploy to global dir (~/.claude)").option("--target <agent>", "Driver target", "claude-code").action((ref, opts) => {
339
340
  const am2 = new AssetManager({
340
- projectDir: path15__default.resolve(opts.projectDir),
341
+ projectDir: path14__default.resolve(opts.projectDir),
341
342
  global: opts.global,
342
343
  driverTarget: opts.target
343
344
  });
@@ -358,7 +359,7 @@ function makeAddCommand() {
358
359
  function makeRemoveCommand() {
359
360
  return new Command("remove").description("Remove from skaile.yaml + undeploy").argument("<ref>", "Asset reference (kind:name)").option("--project-dir <path>", "Project directory", process.cwd()).option("--global", "Remove from global dir").option("--target <agent>", "Driver target", "claude-code").action((ref, opts) => {
360
361
  const am2 = new AssetManager({
361
- projectDir: path15__default.resolve(opts.projectDir),
362
+ projectDir: path14__default.resolve(opts.projectDir),
362
363
  global: opts.global,
363
364
  driverTarget: opts.target
364
365
  });
@@ -372,7 +373,7 @@ function makeListCommand() {
372
373
  new Option("--target <agent>", "Driver target").default("claude-code").choices(SUPPORTED_DRIVER_TARGETS)
373
374
  ).action((kind, opts) => {
374
375
  const am2 = new AssetManager({
375
- projectDir: path15__default.resolve(opts.projectDir),
376
+ projectDir: path14__default.resolve(opts.projectDir),
376
377
  global: opts.global,
377
378
  driverTarget: opts.target
378
379
  });
@@ -396,7 +397,7 @@ function makeListCommand() {
396
397
  }
397
398
  function makeInfoCommand() {
398
399
  return new Command("info").description("Show asset metadata, deps, deploy status").argument("<ref>", "Asset reference (kind:name)").option("--project-dir <path>", "Project directory", process.cwd()).action((ref, opts) => {
399
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
400
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
400
401
  const entry = am2.info(ref);
401
402
  if (!entry) {
402
403
  logErr(
@@ -429,7 +430,7 @@ function makeCreateCommand() {
429
430
  new Option("-k, --kind <kind>", "Asset kind").default("skill").choices([...ASSET_KINDS])
430
431
  ).option("-d, --dir <dir>", "Target directory (default: cwd)").action((name, opts) => {
431
432
  const am2 = new AssetManager({ projectDir: process.cwd() });
432
- const destDir = opts.dir ? path15__default.resolve(opts.dir) : process.cwd();
433
+ const destDir = opts.dir ? path14__default.resolve(opts.dir) : process.cwd();
433
434
  const result = am2.create(name, opts.kind, destDir);
434
435
  if (result.ok) logOk(`Created ${kindColor(opts.kind)}: ${pc5.dim(result.path)}`);
435
436
  else {
@@ -440,7 +441,7 @@ function makeCreateCommand() {
440
441
  }
441
442
  function makeDoctorCommand() {
442
443
  return new Command("doctor").description("Scan for missing dependency chains").argument("[name]", "Check a specific asset (kind:name)").option("--project-dir <path>", "Project directory", process.cwd()).action((name, opts) => {
443
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
444
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
444
445
  const issues = am2.doctor();
445
446
  if (issues.length === 0) {
446
447
  logOk("No missing dependencies.");
@@ -466,11 +467,11 @@ function makeCatalogCommand() {
466
467
  const catalog = new Command("catalog").description("Catalog source health and configuration");
467
468
  catalog.command("test").description("Probe the configured catalog source and report status").option("--project-dir <path>", "Project directory (for project-level config overlay)").option("--url <url>", "Override the catalog URL for this probe").option("--force", "Probe the network even in air-gapped mode (cache_ttl: 0)").action(async (opts) => {
468
469
  const { resolveConfig, isLocalCatalogUrl, trpcGetUrl } = await import('../library/index.js');
469
- const projectDir = opts.projectDir ? path15__default.resolve(opts.projectDir) : void 0;
470
+ const projectDir = opts.projectDir ? path14__default.resolve(opts.projectDir) : void 0;
470
471
  const cfg = resolveConfig({ projectDir });
471
472
  const baseUrl = opts.url ?? cfg.catalog.url;
472
473
  if (isLocalCatalogUrl(baseUrl)) {
473
- const { resolveCatalogSource } = await import('../open-library-IOYWFK7M.js');
474
+ const { resolveCatalogSource } = await import('../open-library-DWAQFUSQ.js');
474
475
  let resolved;
475
476
  try {
476
477
  resolved = await resolveCatalogSource({ projectDir: opts.projectDir });
@@ -559,7 +560,7 @@ function makeCatalogCommand() {
559
560
  });
560
561
  catalog.command("info").description("Print the resolved catalog configuration (url, framing, cacheTtlMs)").option("--project-dir <path>", "Project directory (for project-level config overlay)").action(async (opts) => {
561
562
  const { resolveConfig } = await import('../library/index.js');
562
- const projectDir = opts.projectDir ? path15__default.resolve(opts.projectDir) : void 0;
563
+ const projectDir = opts.projectDir ? path14__default.resolve(opts.projectDir) : void 0;
563
564
  const cfg = resolveConfig({ projectDir });
564
565
  console.log(`url: ${cfg.catalog.url}`);
565
566
  console.log(`framing: ${cfg.catalog.framing}`);
@@ -616,7 +617,7 @@ function findSkills(domain) {
616
617
  if (!fs10__default.existsSync(AI_RESOURCES)) return skills;
617
618
  const domains = fs10__default.readdirSync(AI_RESOURCES, { withFileTypes: true }).filter((d) => d.isDirectory()).filter((d) => true);
618
619
  for (const d of domains) {
619
- const skillsDir = path15__default.join(AI_RESOURCES, d.name, "skills");
620
+ const skillsDir = path14__default.join(AI_RESOURCES, d.name, "skills");
620
621
  if (!fs10__default.existsSync(skillsDir)) continue;
621
622
  walkSkills(skillsDir, d.name, skills);
622
623
  }
@@ -624,9 +625,9 @@ function findSkills(domain) {
624
625
  }
625
626
  function walkSkills(dir, domain, out) {
626
627
  for (const entry of fs10__default.readdirSync(dir, { withFileTypes: true })) {
627
- const full = path15__default.join(dir, entry.name);
628
+ const full = path14__default.join(dir, entry.name);
628
629
  if (entry.isDirectory()) {
629
- const skillMd = path15__default.join(full, "SKILL.md");
630
+ const skillMd = path14__default.join(full, "SKILL.md");
630
631
  if (fs10__default.existsSync(skillMd)) {
631
632
  out.push({ name: entry.name, path: full, skillPath: skillMd, domain });
632
633
  } else {
@@ -652,7 +653,7 @@ function resolveFlowIds() {
652
653
  }
653
654
  }
654
655
  function resolveSessionIds(projectDir) {
655
- const sessionsDir = path15__default.join(projectDir, ".skaile", "sessions");
656
+ const sessionsDir = path14__default.join(projectDir, ".skaile", "sessions");
656
657
  if (!fs10__default.existsSync(sessionsDir)) return [];
657
658
  try {
658
659
  return fs10__default.readdirSync(sessionsDir).filter((f) => f.endsWith(".json")).map((f) => f.slice(0, -".json".length));
@@ -713,7 +714,7 @@ var API_KEY_PREFIX = "apiKey.";
713
714
  function makeConfigCommand() {
714
715
  const cmd = new Command("config").description("Manage personal config (.skaile/settings.json)");
715
716
  cmd.command("show").description("Show effective config with sources").option("--project-dir <path>", "Project directory").action(async (opts) => {
716
- const projectDir = opts.projectDir ? path15__default.resolve(opts.projectDir) : process.cwd();
717
+ const projectDir = opts.projectDir ? path14__default.resolve(opts.projectDir) : process.cwd();
717
718
  const config = await resolveSettings(projectDir);
718
719
  const wsDefaults = {};
719
720
  try {
@@ -770,13 +771,13 @@ function makeConfigCommand() {
770
771
  console.log();
771
772
  });
772
773
  cmd.command("get <key>").description("Get an effective config value").option("--project-dir <path>", "Project directory").action(async (key, opts) => {
773
- const projectDir = opts.projectDir ? path15__default.resolve(opts.projectDir) : process.cwd();
774
+ const projectDir = opts.projectDir ? path14__default.resolve(opts.projectDir) : process.cwd();
774
775
  const config = await resolveSettings(projectDir);
775
776
  const value = config[key];
776
777
  console.log(value ?? S.dim("(not set)"));
777
778
  });
778
779
  cmd.command("set <key> <value>").description("Set a personal config value (driver, model, provider, apiKey.<provider>)").option("--project-dir <path>", "Project directory").option("--global", "Write to ~/.skaile/settings.json instead of project-local").action(async (key, value, opts) => {
779
- const projectDir = opts.projectDir ? path15__default.resolve(opts.projectDir) : process.cwd();
780
+ const projectDir = opts.projectDir ? path14__default.resolve(opts.projectDir) : process.cwd();
780
781
  const isApiKey = key.startsWith(API_KEY_PREFIX);
781
782
  if (!PERSONAL_KEYS.has(key) && !isApiKey) {
782
783
  logErr(
@@ -1083,8 +1084,8 @@ function makeConnectorCommand() {
1083
1084
  async (driver, opts) => {
1084
1085
  const { installNpmPackages } = await import('../connectors/index.js');
1085
1086
  const { scanDirectory, resolveBaseAssetsRoot, WorkspaceYamlEditor: WorkspaceYamlEditor2 } = await import('../core/index.js');
1086
- const projectDir = path15__default.resolve(opts.projectDir);
1087
- const yamlPath = path15__default.join(projectDir, "skaile.yaml");
1087
+ const projectDir = path14__default.resolve(opts.projectDir);
1088
+ const yamlPath = path14__default.join(projectDir, "skaile.yaml");
1088
1089
  if (!existsSync(yamlPath)) {
1089
1090
  logErr("No skaile.yaml found in current directory. Run 'skaile init' first.");
1090
1091
  process.exit(1);
@@ -1147,8 +1148,8 @@ ${installResult.output}`);
1147
1148
  );
1148
1149
  cmd.command("remove <id>").option("--project-dir <path>", "Workspace directory", process.cwd()).description("Remove a connector from skaile.yaml by its instance ID").action(async (id, opts) => {
1149
1150
  const { WorkspaceYamlEditor: WorkspaceYamlEditor2 } = await import('../core/index.js');
1150
- const projectDir = path15__default.resolve(opts.projectDir);
1151
- const yamlPath = path15__default.join(projectDir, "skaile.yaml");
1151
+ const projectDir = path14__default.resolve(opts.projectDir);
1152
+ const yamlPath = path14__default.join(projectDir, "skaile.yaml");
1152
1153
  if (!existsSync(yamlPath)) {
1153
1154
  logErr("No skaile.yaml found in current directory.");
1154
1155
  process.exit(1);
@@ -1165,7 +1166,7 @@ ${installResult.output}`);
1165
1166
  cmd.command("status [id]").option("--project-dir <path>", "Workspace directory", process.cwd()).description("Connect and report health status for one or all connectors").action(async (id, opts) => {
1166
1167
  const res = await import('../connectors/index.js');
1167
1168
  res.registerBuiltinConnectors();
1168
- const projectDir = path15__default.resolve(opts.projectDir);
1169
+ const projectDir = path14__default.resolve(opts.projectDir);
1169
1170
  const declarations = res.loadConnectorDeclarations(projectDir);
1170
1171
  if (declarations.length === 0) {
1171
1172
  console.log("No connectors configured in skaile.yaml.");
@@ -1189,7 +1190,7 @@ ${installResult.output}`);
1189
1190
  await manager.disconnectAll();
1190
1191
  });
1191
1192
  cmd.command("list").description("List all configured connectors").option("--project-dir <path>", "Workspace directory", process.cwd()).action(async (opts) => {
1192
- const projectDir = path15__default.resolve(opts.projectDir);
1193
+ const projectDir = path14__default.resolve(opts.projectDir);
1193
1194
  const manager = await connectConnectors(projectDir);
1194
1195
  try {
1195
1196
  console.log(JSON.stringify(manager.listConnectors(), null, 2));
@@ -1198,7 +1199,7 @@ ${installResult.output}`);
1198
1199
  }
1199
1200
  });
1200
1201
  cmd.command("sync [id]").description("Re-sync a filesystem-face connector or all of them (git pull, S3 refresh, etc.)").option("--all", "Sync all connectors").option("--project-dir <path>", "Workspace directory", process.cwd()).action(async (id, opts) => {
1201
- const projectDir = path15__default.resolve(opts.projectDir);
1202
+ const projectDir = path14__default.resolve(opts.projectDir);
1202
1203
  const manager = await connectConnectors(projectDir);
1203
1204
  try {
1204
1205
  if (opts.all) {
@@ -1222,7 +1223,7 @@ ${installResult.output}`);
1222
1223
  }
1223
1224
  });
1224
1225
  cmd.command("ops <id>").description("List available operations for a connector").option("--project-dir <path>", "Workspace directory", process.cwd()).action(async (id, opts) => {
1225
- const projectDir = path15__default.resolve(opts.projectDir);
1226
+ const projectDir = path14__default.resolve(opts.projectDir);
1226
1227
  const manager = await connectConnectors(projectDir);
1227
1228
  try {
1228
1229
  if (!manager.has(id)) {
@@ -1237,7 +1238,7 @@ ${installResult.output}`);
1237
1238
  }
1238
1239
  });
1239
1240
  cmd.command("read <id> <resource-path>").description("Read content from a connector").option("--project-dir <path>", "Workspace directory", process.cwd()).action(async (id, resourcePath, opts) => {
1240
- const projectDir = path15__default.resolve(opts.projectDir);
1241
+ const projectDir = path14__default.resolve(opts.projectDir);
1241
1242
  const manager = await connectConnectors(projectDir);
1242
1243
  try {
1243
1244
  const content = await manager.read(id, resourcePath);
@@ -1247,7 +1248,7 @@ ${installResult.output}`);
1247
1248
  }
1248
1249
  });
1249
1250
  cmd.command("write <id> <resource-path> <content>").description("Write content to a connector at a path").option("--project-dir <path>", "Workspace directory", process.cwd()).action(async (id, resourcePath, content, opts) => {
1250
- const projectDir = path15__default.resolve(opts.projectDir);
1251
+ const projectDir = path14__default.resolve(opts.projectDir);
1251
1252
  const manager = await connectConnectors(projectDir);
1252
1253
  try {
1253
1254
  await manager.write(id, resourcePath, { data: content });
@@ -1257,7 +1258,7 @@ ${installResult.output}`);
1257
1258
  }
1258
1259
  });
1259
1260
  cmd.command("entries <id> [resource-path]").description("List entries in a connector (files, keys, rows, etc)").option("--project-dir <path>", "Workspace directory", process.cwd()).option("--recursive", "Include nested entries").option("--limit <n>", "Maximum entries to return", parseInt).action(async (id, resourcePath, opts) => {
1260
- const projectDir = path15__default.resolve(opts.projectDir);
1261
+ const projectDir = path14__default.resolve(opts.projectDir);
1261
1262
  const manager = await connectConnectors(projectDir);
1262
1263
  try {
1263
1264
  const entries = await manager.list(id, resourcePath, {
@@ -1270,7 +1271,7 @@ ${installResult.output}`);
1270
1271
  }
1271
1272
  });
1272
1273
  cmd.command("search <id> <query>").description("Search within a connector for matching content").option("--project-dir <path>", "Workspace directory", process.cwd()).action(async (id, query, opts) => {
1273
- const projectDir = path15__default.resolve(opts.projectDir);
1274
+ const projectDir = path14__default.resolve(opts.projectDir);
1274
1275
  const manager = await connectConnectors(projectDir);
1275
1276
  try {
1276
1277
  const results = await manager.search(id, query);
@@ -1280,7 +1281,7 @@ ${installResult.output}`);
1280
1281
  }
1281
1282
  });
1282
1283
  cmd.command("delete <id> <resource-path>").description("Delete an entry from a connector").option("--project-dir <path>", "Workspace directory", process.cwd()).action(async (id, resourcePath, opts) => {
1283
- const projectDir = path15__default.resolve(opts.projectDir);
1284
+ const projectDir = path14__default.resolve(opts.projectDir);
1284
1285
  const manager = await connectConnectors(projectDir);
1285
1286
  try {
1286
1287
  const ok = await manager.delete(id, resourcePath);
@@ -1290,7 +1291,7 @@ ${installResult.output}`);
1290
1291
  }
1291
1292
  });
1292
1293
  cmd.command("run <id> <op> [args...]").description("Run a custom adapter operation (e.g. git log, sqlite query)").option("--project-dir <path>", "Workspace directory", process.cwd()).allowUnknownOption().action(async (id, op, args, opts) => {
1293
- const projectDir = path15__default.resolve(opts.projectDir);
1294
+ const projectDir = path14__default.resolve(opts.projectDir);
1294
1295
  const manager = await connectConnectors(projectDir);
1295
1296
  try {
1296
1297
  if (!manager.has(id)) {
@@ -1379,9 +1380,172 @@ function makeDebugCommand() {
1379
1380
  });
1380
1381
  return cmd;
1381
1382
  }
1383
+ function action(fn) {
1384
+ return async (...args) => {
1385
+ try {
1386
+ await fn(...args);
1387
+ } catch (err) {
1388
+ logErr(err instanceof Error ? err.message : String(err));
1389
+ process.exitCode = 1;
1390
+ }
1391
+ };
1392
+ }
1393
+ function envRecord() {
1394
+ const out = {};
1395
+ for (const [k, v] of Object.entries(process.env)) {
1396
+ if (typeof v === "string") out[k] = v;
1397
+ }
1398
+ return out;
1399
+ }
1400
+ async function buildDeployContext(projectDir) {
1401
+ const { resolveSkWorkspaceConfig: resolveSkWorkspaceConfig2 } = await import('../core/index.js');
1402
+ const config = resolveSkWorkspaceConfig2(projectDir);
1403
+ const workspaceId = config.name ?? path14__default.basename(projectDir);
1404
+ let log;
1405
+ try {
1406
+ const { createLogger } = await import('../core/logging.js');
1407
+ log = createLogger({ kind: "gateway", subkind: "deploy" });
1408
+ } catch {
1409
+ const shim = {
1410
+ debug: (m) => console.error(S.dim(` \xB7 ${m}`)),
1411
+ info: (m) => console.error(S.dim(` \xB7 ${m}`)),
1412
+ warn: (m) => logWarn(m),
1413
+ error: (m, e) => logErr(`${m}${e ? `: ${e instanceof Error ? e.message : String(e)}` : ""}`),
1414
+ child: () => shim
1415
+ };
1416
+ log = shim;
1417
+ }
1418
+ const controller = new AbortController();
1419
+ const ctx = {
1420
+ workspaceId,
1421
+ env: envRecord(),
1422
+ log,
1423
+ signal: controller.signal,
1424
+ ...process.env.SKAILE_WS_AUTH_TOKEN ? { wsAuth: process.env.SKAILE_WS_AUTH_TOKEN } : {}
1425
+ };
1426
+ return { ctx, controller };
1427
+ }
1428
+ async function ensureTargetsRegistered(projectDir) {
1429
+ const { registerBuiltinDeployTargets } = await import('../deploy/index.js');
1430
+ const { pluginRegistry } = await import('../plugin-registry/index.js');
1431
+ registerBuiltinDeployTargets(pluginRegistry);
1432
+ const { resolveSkWorkspaceConfig: resolveSkWorkspaceConfig2 } = await import('../core/index.js');
1433
+ const config = resolveSkWorkspaceConfig2(projectDir);
1434
+ if (config.plugins && config.plugins.length > 0) {
1435
+ const { ensurePluginsLoaded } = await import('../plugin-store-6OENKNFW.js');
1436
+ const result = await ensurePluginsLoaded(projectDir, config.plugins, pluginRegistry);
1437
+ for (const f of result.failed) logWarn(f.error);
1438
+ }
1439
+ }
1440
+ async function runUp(opts) {
1441
+ const projectDir = path14__default.resolve(opts.projectDir);
1442
+ await ensureTargetsRegistered(projectDir);
1443
+ const { resolveSkWorkspaceConfig: resolveSkWorkspaceConfig2 } = await import('../core/index.js');
1444
+ const { resolveDeployTarget, pluginRegistry } = await import('../plugin-registry/index.js');
1445
+ const config = resolveSkWorkspaceConfig2(projectDir);
1446
+ const resolution = await resolveDeployTarget(
1447
+ { deploy: config.deploy },
1448
+ opts.target ? { target: opts.target, config: config.deploy?.config ?? {}, reason: "cli --target" } : void 0,
1449
+ pluginRegistry
1450
+ );
1451
+ const { ctx, controller } = await buildDeployContext(projectDir);
1452
+ ctx.log.debug(`deploy target resolved`, {
1453
+ target: resolution.target.id,
1454
+ source: resolution.provenance.source,
1455
+ reason: resolution.provenance.reason
1456
+ });
1457
+ logInfo(`Deploying to ${S.cmd(resolution.target.id)} (${S.dim(resolution.provenance.source)})\u2026`);
1458
+ const handle = await resolution.target.create(resolution.config, ctx);
1459
+ await handle.waitReady();
1460
+ logOk(`Ready at ${S.cmd(handle.wsUrl)}`);
1461
+ console.log(` ${S.dim("source")} ${resolution.provenance.source}`);
1462
+ if (opts.detach) {
1463
+ const { writeHandle } = await import('../deploy/index.js');
1464
+ await writeHandle(projectDir, resolution.target.id, handle.payload);
1465
+ logInfo(`Detached \u2014 handle written to ${S.cmd(".skaile/deploy/handle.json")}`);
1466
+ return;
1467
+ }
1468
+ logInfo("Holding deploy in the foreground \u2014 press Ctrl-C to stop.");
1469
+ await holdUntilSignal(handle, controller);
1470
+ }
1471
+ function holdUntilSignal(handle, controller) {
1472
+ return new Promise((resolve4) => {
1473
+ const onSig = () => {
1474
+ process.removeListener("SIGINT", onSig);
1475
+ controller.abort();
1476
+ logInfo("Stopping\u2026");
1477
+ handle.stop().then(() => logOk("Stopped.")).catch((e) => logErr(`stop failed: ${e instanceof Error ? e.message : String(e)}`)).finally(() => resolve4());
1478
+ };
1479
+ process.on("SIGINT", onSig);
1480
+ });
1481
+ }
1482
+ async function restoreFromHandle(projectDir) {
1483
+ const { readHandle } = await import('../deploy/index.js');
1484
+ const stored = await readHandle(projectDir);
1485
+ if (!stored) {
1486
+ logInfo("No active deploy \u2014 nothing to do (no .skaile/deploy/handle.json).");
1487
+ return null;
1488
+ }
1489
+ await ensureTargetsRegistered(projectDir);
1490
+ const { pluginRegistry } = await import('../plugin-registry/index.js');
1491
+ const target = pluginRegistry.get("deployTarget", stored.targetId);
1492
+ if (!target) {
1493
+ logErr(`unknown deploy target "${stored.targetId}" \u2014 is its plugin installed?`);
1494
+ return null;
1495
+ }
1496
+ const { ctx } = await buildDeployContext(projectDir);
1497
+ const handle = await target.restore(stored.payload, ctx);
1498
+ return { target, handle, ctx };
1499
+ }
1500
+ async function runDown(opts) {
1501
+ const projectDir = path14__default.resolve(opts.projectDir);
1502
+ const restored = await restoreFromHandle(projectDir);
1503
+ if (!restored) return;
1504
+ await restored.handle.stop();
1505
+ const { clearHandle } = await import('../deploy/index.js');
1506
+ await clearHandle(projectDir);
1507
+ logOk(`Stopped ${S.cmd(restored.target.id)} and cleared the handle.`);
1508
+ }
1509
+ async function runStatus(opts) {
1510
+ const projectDir = path14__default.resolve(opts.projectDir);
1511
+ const restored = await restoreFromHandle(projectDir);
1512
+ if (!restored) return;
1513
+ const health = await restored.handle.health();
1514
+ console.log();
1515
+ console.log(` ${S.label("target")} ${S.cmd(restored.target.id)}`);
1516
+ console.log(` ${S.label("state")} ${restored.handle.state}`);
1517
+ console.log(` ${S.label("wsUrl")} ${S.cmd(restored.handle.wsUrl)}`);
1518
+ console.log(
1519
+ ` ${S.label("health")} ${health.healthy ? S.ok("healthy") : S.err("unhealthy")}${health.detail ? ` ${S.dim(`(${health.detail})`)}` : ""}`
1520
+ );
1521
+ console.log();
1522
+ }
1523
+ async function runLogs(opts) {
1524
+ const projectDir = path14__default.resolve(opts.projectDir);
1525
+ const restored = await restoreFromHandle(projectDir);
1526
+ if (!restored) return;
1527
+ if (!restored.handle.logs) {
1528
+ logInfo(`logs not supported by target ${S.cmd(restored.target.id)}`);
1529
+ return;
1530
+ }
1531
+ for await (const entry of restored.handle.logs({ follow: opts.follow })) {
1532
+ console.log(entry.line);
1533
+ }
1534
+ }
1535
+ function makeDeployCommand() {
1536
+ const cmd = new Command("deploy").description(
1537
+ "Deploy a workspace to a target (up / down / status / logs)"
1538
+ );
1539
+ cmd.command("up").description("Resolve a deploy target, stand the workspace up, and wait until ready").option("--project-dir <path>", "Project directory", process.cwd()).option("--target <id>", "Override the deploy target (precedence: override > yaml > default)").option("--detach", "Persist the handle and return instead of holding in the foreground").action(action(runUp));
1540
+ cmd.command("down").description("Tear down the active deploy and clear its handle").option("--project-dir <path>", "Project directory", process.cwd()).action(action(runDown));
1541
+ cmd.command("status").description("Show the active deploy's state, ws URL, and health").option("--project-dir <path>", "Project directory", process.cwd()).action(action(runStatus));
1542
+ cmd.command("logs").description("Stream logs from the active deploy (if the target supports it)").option("--project-dir <path>", "Project directory", process.cwd()).option("--follow", "Keep streaming new log lines").action(action(runLogs));
1543
+ cmd.action(() => cmd.help());
1544
+ return cmd;
1545
+ }
1382
1546
  function makeDiffCommand() {
1383
1547
  return new Command("diff").description("Show changes between deployed and source versions").argument("<ref>", "Asset reference (kind:name)").option("--project-dir <path>", "Project directory", process.cwd()).action((ref, opts) => {
1384
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
1548
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
1385
1549
  const result = am2.diff(ref);
1386
1550
  if (result === null) {
1387
1551
  logInfo("No differences (or asset not found).");
@@ -1434,7 +1598,7 @@ function makeFlowCommand() {
1434
1598
  function makeHistoryCommand() {
1435
1599
  const cmd = new Command("history").description("Show recent add/remove/update actions");
1436
1600
  cmd.argument("[limit]", "Number of entries to show", "20").option("--project-dir <path>", "Project directory", process.cwd()).action((limitStr, opts) => {
1437
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
1601
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
1438
1602
  const limit = parseInt(limitStr, 10) || 20;
1439
1603
  const entries = am2.history(limit);
1440
1604
  if (entries.length === 0) {
@@ -1454,7 +1618,7 @@ function makeHistoryCommand() {
1454
1618
  console.log();
1455
1619
  });
1456
1620
  cmd.command("clear").description("Clear action history").option("--project-dir <path>", "Project directory", process.cwd()).action((opts) => {
1457
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
1621
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
1458
1622
  am2.clearHistory();
1459
1623
  logOk("History cleared.");
1460
1624
  });
@@ -1522,7 +1686,7 @@ function makeLibraryCommand() {
1522
1686
  cmd.command("init <name>").description("Create a new local library at ~/.skaile/libraries/<name>").option("--git <url>", "Initialize as a git library tracking <url>").option("--owner", "Mark as owner (default for local)").option("--contributor", "Mark as contributor").option("--reader", "Mark as reader").action(
1523
1687
  async (name, opts) => {
1524
1688
  const libDir = resolveLibraryDir();
1525
- const libPath = path15.join(libDir, name);
1689
+ const libPath = path14.join(libDir, name);
1526
1690
  const ownership = opts.contributor ? "contributor" : opts.reader ? "reader" : "owner";
1527
1691
  const { manager, close } = await openLibraryManager();
1528
1692
  try {
@@ -1595,7 +1759,7 @@ function makeLibraryCommand() {
1595
1759
  target = def;
1596
1760
  }
1597
1761
  const am2 = new AssetManager({ projectDir: process.cwd() });
1598
- const destDir = opts.dir ? path15.join(target.path, opts.dir) : target.path;
1762
+ const destDir = opts.dir ? path14.join(target.path, opts.dir) : target.path;
1599
1763
  const res = am2.create(name, opts.kind ?? kind, destDir);
1600
1764
  if (res.ok) {
1601
1765
  logOk(`Created ${opts.kind ?? kind}: ${pc5.dim(res.path)}`);
@@ -1621,8 +1785,8 @@ function makeLibraryCommand() {
1621
1785
  const { manager, close } = await openLibraryManager();
1622
1786
  try {
1623
1787
  const lib = await manager.requireLibrary(oldName);
1624
- const parent = path15.dirname(lib.path);
1625
- const newPath = path15.join(parent, newName);
1788
+ const parent = path14.dirname(lib.path);
1789
+ const newPath = path14.join(parent, newName);
1626
1790
  if (fs10.existsSync(newPath)) {
1627
1791
  logErr(`Target directory already exists: ${newPath}`);
1628
1792
  process.exit(1);
@@ -1813,9 +1977,9 @@ async function printOverallStatus(projectDir, asJson) {
1813
1977
  } catch {
1814
1978
  secretsStrategy = "unavailable";
1815
1979
  }
1816
- const resolvedProjectDir = path15.resolve(projectDir);
1817
- const hasWorkspaceConfig = existsSync(path15.join(resolvedProjectDir, "skaile.yaml"));
1818
- const hasLockFile = existsSync(path15.join(resolvedProjectDir, "skaile.lock.yaml"));
1980
+ const resolvedProjectDir = path14.resolve(projectDir);
1981
+ const hasWorkspaceConfig = existsSync(path14.join(resolvedProjectDir, "skaile.yaml"));
1982
+ const hasLockFile = existsSync(path14.join(resolvedProjectDir, "skaile.lock.yaml"));
1819
1983
  let subscriptions = [];
1820
1984
  if (hasWorkspaceConfig) {
1821
1985
  try {
@@ -2092,16 +2256,16 @@ function assetRefOf(r) {
2092
2256
  function findAssetRow(ref) {
2093
2257
  return state.assetRows.find((r) => isAsset(r) && assetRefOf(r) === ref);
2094
2258
  }
2095
- function setSelection(ref, action) {
2259
+ function setSelection(ref, action3) {
2096
2260
  const row = findAssetRow(ref);
2097
2261
  if (!row) return;
2098
- if (action === "clear") {
2262
+ if (action3 === "clear") {
2099
2263
  state.pendingAdds.delete(ref);
2100
2264
  state.pendingRemoves.delete(ref);
2101
2265
  return;
2102
2266
  }
2103
2267
  let resolved;
2104
- if (action === "toggle") {
2268
+ if (action3 === "toggle") {
2105
2269
  if (state.pendingAdds.has(ref) || state.pendingRemoves.has(ref)) {
2106
2270
  state.pendingAdds.delete(ref);
2107
2271
  state.pendingRemoves.delete(ref);
@@ -2109,7 +2273,7 @@ function setSelection(ref, action) {
2109
2273
  }
2110
2274
  resolved = row.installed ? "remove" : "add";
2111
2275
  } else {
2112
- resolved = action;
2276
+ resolved = action3;
2113
2277
  }
2114
2278
  if (resolved === "add") {
2115
2279
  state.pendingRemoves.delete(ref);
@@ -2121,22 +2285,22 @@ function setSelection(ref, action) {
2121
2285
  state.pendingRemoves.add(ref);
2122
2286
  }
2123
2287
  }
2124
- function bulkSelection(refs, action) {
2125
- for (const ref of refs) setSelection(ref, action);
2288
+ function bulkSelection(refs, action3) {
2289
+ for (const ref of refs) setSelection(ref, action3);
2126
2290
  }
2127
- function actOnHeader(row, action) {
2291
+ function actOnHeader(row, action3) {
2128
2292
  if (row.type === "source-header") {
2129
- bulkSelection(sourceAssetRefs(state.assetRows, row.source), action);
2293
+ bulkSelection(sourceAssetRefs(state.assetRows, row.source), action3);
2130
2294
  return true;
2131
2295
  }
2132
2296
  if (row.type === "header") {
2133
- bulkSelection(domainAssetRefs(state.assetRows, row.source, row.domain), action);
2297
+ bulkSelection(domainAssetRefs(state.assetRows, row.source, row.domain), action3);
2134
2298
  return true;
2135
2299
  }
2136
2300
  return false;
2137
2301
  }
2138
2302
  async function loadAssets() {
2139
- const { gatherAssetFeeds } = await import('../asset-feeds-CI76R7FI.js');
2303
+ const { gatherAssetFeeds } = await import('../asset-feeds-PJDJ3QYI.js');
2140
2304
  const { entries, notes } = await gatherAssetFeeds(am, am.projectDir);
2141
2305
  if (notes.length > 0) {
2142
2306
  state.message = notes.map((n) => `[${n.feed}] ${n.message}`).join(" \u2022 ");
@@ -2193,12 +2357,12 @@ async function loadAssets() {
2193
2357
  async function loadSourcesAndLibraries() {
2194
2358
  try {
2195
2359
  const [{ openLibraryManager: openLibraryManager2 }, { skaileHomeDir: skaileHomeDir2 }] = await Promise.all([
2196
- import('../open-library-IOYWFK7M.js'),
2360
+ import('../open-library-DWAQFUSQ.js'),
2197
2361
  import('../library/index.js')
2198
2362
  ]);
2199
2363
  const { manager, library, close } = await openLibraryManager2();
2200
2364
  try {
2201
- const sourcesDir2 = path15__default.join(skaileHomeDir2(), "sources");
2365
+ const sourcesDir2 = path14__default.join(skaileHomeDir2(), "sources");
2202
2366
  const isSourceRow = (l) => l.path.startsWith(sourcesDir2);
2203
2367
  const libs = await manager.listLibraries();
2204
2368
  const defs = await library.listAssetDefs();
@@ -2469,14 +2633,14 @@ async function syncAll() {
2469
2633
  "Sync is not yet driven from the manage TUI. Run `skaile source sync` (sources) or `skaile library sync <name>` (git-backed libraries) from the shell."
2470
2634
  );
2471
2635
  }
2472
- function sourceShellHint(action) {
2636
+ function sourceShellHint(action3) {
2473
2637
  state.message = pc5.yellow(
2474
- `${action} is a shell command. Run \`skaile source \u2026\` from the shell.`
2638
+ `${action3} is a shell command. Run \`skaile source \u2026\` from the shell.`
2475
2639
  );
2476
2640
  }
2477
- function libraryShellHint(action) {
2641
+ function libraryShellHint(action3) {
2478
2642
  state.message = pc5.yellow(
2479
- `${action} is a shell command. Run \`skaile library \u2026\` from the shell.`
2643
+ `${action3} is a shell command. Run \`skaile library \u2026\` from the shell.`
2480
2644
  );
2481
2645
  }
2482
2646
  async function showInfo() {
@@ -2700,13 +2864,13 @@ async function run(projectDir) {
2700
2864
  }
2701
2865
  function makeManageCommand() {
2702
2866
  return new Command("manage").description("Interactive TUI for managing assets, sources, and libraries").option("--project-dir <path>", "Project directory", process.cwd()).action(async (opts) => {
2703
- await run(path15__default.resolve(opts.projectDir));
2867
+ await run(path14__default.resolve(opts.projectDir));
2704
2868
  });
2705
2869
  }
2706
2870
  function makeMcpServerCommand() {
2707
2871
  return new Command("mcp-server").description("Start skaile workspace MCP server (stdio transport)").option("--project-dir <path>", "Project directory (default: cwd)", process.cwd()).action(async (opts) => {
2708
- const path32 = await import('path');
2709
- const projectDir = path32.default.resolve(opts.projectDir);
2872
+ const path34 = await import('path');
2873
+ const projectDir = path34.default.resolve(opts.projectDir);
2710
2874
  const { LogStore, StdoutSink, registerLogStore } = await import('../core/logging.js');
2711
2875
  registerLogStore(
2712
2876
  new LogStore({
@@ -2741,7 +2905,7 @@ function makeNpxCommand() {
2741
2905
  const npx = new Command("npx").description("Compatibility shim for npx skills syntax");
2742
2906
  const skills = npx.command("skills").description("Skill installation from external repos");
2743
2907
  skills.command("add <url>").description("Register a repo as a Library Source and install a skill from it").requiredOption("--skill <name>", "Skill name to install from the repo").option("--project-dir <path>", "Project directory", process.cwd()).option("--target <agent>", "Agent framework", "claude-code").option("--global", "Deploy globally").action(async (url, opts) => {
2744
- const projectDir = path15__default.resolve(opts.projectDir);
2908
+ const projectDir = path14__default.resolve(opts.projectDir);
2745
2909
  const spinner5 = p5.spinner();
2746
2910
  let sourcePath;
2747
2911
  const isUrl = /^(https?:|git@|git:)/.test(url);
@@ -2752,14 +2916,14 @@ function makeNpxCommand() {
2752
2916
  if (!existsSync(sourcePath)) {
2753
2917
  execSync(`git clone ${url} ${sourcePath}`, { stdio: "ignore" });
2754
2918
  }
2755
- spinner5.stop(`Cloned to ${path15__default.basename(sourcePath)}`);
2919
+ spinner5.stop(`Cloned to ${path14__default.basename(sourcePath)}`);
2756
2920
  } catch (err) {
2757
2921
  spinner5.stop("Clone failed");
2758
2922
  logErr(err instanceof Error ? err.message : String(err));
2759
2923
  process.exit(1);
2760
2924
  }
2761
2925
  } else {
2762
- sourcePath = path15__default.resolve(url);
2926
+ sourcePath = path14__default.resolve(url);
2763
2927
  if (!existsSync(sourcePath)) {
2764
2928
  logErr(`Path does not exist: ${sourcePath}`);
2765
2929
  process.exit(1);
@@ -2772,7 +2936,7 @@ function makeNpxCommand() {
2772
2936
  if (!source) {
2773
2937
  source = await library.addSource({
2774
2938
  backend: "local",
2775
- name: path15__default.basename(sourcePath),
2939
+ name: path14__default.basename(sourcePath),
2776
2940
  path: sourcePath,
2777
2941
  ownership: "owner"
2778
2942
  });
@@ -2813,7 +2977,7 @@ function makeNpxCommand() {
2813
2977
  }
2814
2978
  function cloneDestination(url) {
2815
2979
  const cleaned = url.replace(/\.git$/, "");
2816
- const root = path15__default.join(homedir(), ".skaile", "clones");
2980
+ const root = path14__default.join(homedir(), ".skaile", "clones");
2817
2981
  let host = "unknown";
2818
2982
  let pathPart = cleaned;
2819
2983
  const httpMatch = cleaned.match(/^https?:\/\/([^/]+)\/(.+)$/);
@@ -2829,83 +2993,7 @@ function cloneDestination(url) {
2829
2993
  host = gitProtoMatch[1];
2830
2994
  pathPart = gitProtoMatch[2];
2831
2995
  }
2832
- return path15__default.join(root, host, pathPart);
2833
- }
2834
- function makeOutdatedCommand() {
2835
- return new Command("outdated").description("Check for assets behind their repo").argument("[name]", "Check a specific asset (kind:name)").option("--project-dir <path>", "Project directory", process.cwd()).addOption(
2836
- new Option("--target <agent>", "Driver target").default("claude-code").choices(SUPPORTED_DRIVER_TARGETS)
2837
- ).action((name, opts) => {
2838
- const am2 = new AssetManager({
2839
- projectDir: path15__default.resolve(opts.projectDir),
2840
- driverTarget: opts.target
2841
- });
2842
- const entries = am2.outdated();
2843
- if (entries.length === 0) {
2844
- logInfo("All assets are up to date.");
2845
- return;
2846
- }
2847
- const filtered = name ? entries.filter((e) => `${e.kind}:${e.name}` === name || e.name === name) : entries;
2848
- if (filtered.length === 0) {
2849
- logInfo(`${name} is up to date.`);
2850
- return;
2851
- }
2852
- const nameW = Math.max(4, ...filtered.map((e) => e.name.length));
2853
- console.log();
2854
- console.log(S.heading(" Outdated Assets"));
2855
- console.log(` ${S.rule(nameW + 40)}`);
2856
- for (const e of filtered) {
2857
- console.log(
2858
- ` ${kindColorPad(e.kind)} ${e.name.padEnd(nameW)} ${S.dim(e.repository)} ${pc5.yellow(`${e.behind} commit(s) behind`)}`
2859
- );
2860
- }
2861
- console.log();
2862
- logWarn(`Run ${S.cmd("skaile update")} to re-deploy.`);
2863
- });
2864
- }
2865
- function makePatchCommand() {
2866
- const cmd = new Command("patch").description("Patch workflow for skill improvement");
2867
- cmd.command("extract <ref>").alias("start").description("Extract asset for local editing").option("--project-dir <path>", "Project directory", process.cwd()).action((ref, opts) => {
2868
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
2869
- try {
2870
- const dest = am2.patch(ref);
2871
- logOk(`Extracted to ${S.dim(dest)}`);
2872
- console.log(` Edit the files, then run ${S.cmd(`skaile patch commit ${ref}`)}`);
2873
- } catch (err) {
2874
- logErr(String(err));
2875
- process.exit(1);
2876
- }
2877
- });
2878
- cmd.command("commit <ref>").description("Generate .patch file from edits").option("--project-dir <path>", "Project directory", process.cwd()).action((ref, opts) => {
2879
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
2880
- try {
2881
- const patchFile = am2.patchCommit(ref);
2882
- logOk(`Patch saved to ${S.dim(patchFile)}`);
2883
- console.log(` Add to skaile.yaml patches section, then run ${S.cmd("skaile install")}`);
2884
- } catch (err) {
2885
- logErr(String(err));
2886
- process.exit(1);
2887
- }
2888
- });
2889
- cmd.command("submit <ref>").description("Apply patch to repo clone and prepare for PR").option("--project-dir <path>", "Project directory", process.cwd()).action((ref, opts) => {
2890
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
2891
- try {
2892
- am2.patchSubmit(ref);
2893
- logOk("Patch applied to repo clone and committed.");
2894
- console.log(
2895
- ` Push upstream from the source repo directly \u2014 the legacy ${S.cmd("skaile repo contrib push")} command was removed on 2026-05-12.`
2896
- );
2897
- } catch (err) {
2898
- logErr(String(err));
2899
- process.exit(1);
2900
- }
2901
- });
2902
- cmd.command("remove <ref>").description("Remove local patch after upstream merge").option("--project-dir <path>", "Project directory", process.cwd()).action((ref, opts) => {
2903
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
2904
- am2.patchRemove(ref);
2905
- logOk(`Patch removed for ${ref}`);
2906
- });
2907
- cmd.action(() => cmd.help());
2908
- return cmd;
2996
+ return path14__default.join(root, host, pathPart);
2909
2997
  }
2910
2998
  var SKAILE_MCP_NAME = "skaile-workspace";
2911
2999
  var MCP_SERVER_ENTRY = {
@@ -2914,7 +3002,7 @@ var MCP_SERVER_ENTRY = {
2914
3002
  env: {}
2915
3003
  };
2916
3004
  function pluginDir(projectDir) {
2917
- return path15__default.join(projectDir, ".claude", "plugins", "skaile");
3005
+ return path14__default.join(projectDir, ".claude", "plugins", "skaile");
2918
3006
  }
2919
3007
  async function readJsonStrict(p7) {
2920
3008
  let raw;
@@ -2932,7 +3020,7 @@ async function readJsonStrict(p7) {
2932
3020
  }
2933
3021
  }
2934
3022
  async function writeJson(p7, value) {
2935
- await fs5.mkdir(path15__default.dirname(p7), { recursive: true });
3023
+ await fs5.mkdir(path14__default.dirname(p7), { recursive: true });
2936
3024
  await fs5.writeFile(p7, `${JSON.stringify(value, null, 2)}
2937
3025
  `);
2938
3026
  }
@@ -2940,8 +3028,8 @@ async function copyDir(src, dest) {
2940
3028
  await fs5.mkdir(dest, { recursive: true });
2941
3029
  const entries = await fs5.readdir(src, { withFileTypes: true });
2942
3030
  for (const entry of entries) {
2943
- const srcPath = path15__default.join(src, entry.name);
2944
- const destPath = path15__default.join(dest, entry.name);
3031
+ const srcPath = path14__default.join(src, entry.name);
3032
+ const destPath = path14__default.join(dest, entry.name);
2945
3033
  if (entry.isDirectory()) await copyDir(srcPath, destPath);
2946
3034
  else await fs5.copyFile(srcPath, destPath);
2947
3035
  }
@@ -2950,14 +3038,14 @@ async function install(projectDir, opts) {
2950
3038
  return opts?.full ? installFullPlugin(projectDir) : installMcp(projectDir);
2951
3039
  }
2952
3040
  async function installMcp(projectDir) {
2953
- const mcpPath = path15__default.join(projectDir, ".claude", "mcp.json");
3041
+ const mcpPath = path14__default.join(projectDir, ".claude", "mcp.json");
2954
3042
  const existing = await readJsonStrict(mcpPath) ?? {};
2955
3043
  const mcpServers = { ...existing.mcpServers ?? {} };
2956
3044
  const previous = mcpServers[SKAILE_MCP_NAME];
2957
3045
  const matches = previous && JSON.stringify(previous) === JSON.stringify(MCP_SERVER_ENTRY);
2958
3046
  let warning;
2959
3047
  if (previous && !matches) {
2960
- warning = `overwrote existing ${SKAILE_MCP_NAME} entry in ${path15__default.relative(projectDir, mcpPath)}`;
3048
+ warning = `overwrote existing ${SKAILE_MCP_NAME} entry in ${path14__default.relative(projectDir, mcpPath)}`;
2961
3049
  }
2962
3050
  mcpServers[SKAILE_MCP_NAME] = MCP_SERVER_ENTRY;
2963
3051
  await writeJson(mcpPath, { ...existing, mcpServers });
@@ -2966,15 +3054,15 @@ async function installMcp(projectDir) {
2966
3054
  async function installFullPlugin(projectDir) {
2967
3055
  const dir = pluginDir(projectDir);
2968
3056
  for (const [rel, content] of Object.entries(buildClaudePluginFiles())) {
2969
- const dest = path15__default.join(dir, rel);
2970
- await fs5.mkdir(path15__default.dirname(dest), { recursive: true });
3057
+ const dest = path14__default.join(dir, rel);
3058
+ await fs5.mkdir(path14__default.dirname(dest), { recursive: true });
2971
3059
  await fs5.writeFile(dest, content);
2972
3060
  }
2973
- const projectSkillsDir = path15__default.join(projectDir, ".skaile", "skills");
3061
+ const projectSkillsDir = path14__default.join(projectDir, ".skaile", "skills");
2974
3062
  if (existsSync(projectSkillsDir)) {
2975
- await copyDir(projectSkillsDir, path15__default.join(dir, "skills"));
3063
+ await copyDir(projectSkillsDir, path14__default.join(dir, "skills"));
2976
3064
  }
2977
- const settingsPath = path15__default.join(projectDir, ".claude", "settings.json");
3065
+ const settingsPath = path14__default.join(projectDir, ".claude", "settings.json");
2978
3066
  const settings = await readJsonStrict(settingsPath) ?? {};
2979
3067
  const plugins = settings.plugins ?? [];
2980
3068
  if (!plugins.includes(dir)) plugins.push(dir);
@@ -2982,8 +3070,8 @@ async function installFullPlugin(projectDir) {
2982
3070
  return { changed: true, method: "plugin" };
2983
3071
  }
2984
3072
  async function uninstall(projectDir) {
2985
- const settingsPath = path15__default.join(projectDir, ".claude", "settings.json");
2986
- const mcpPath = path15__default.join(projectDir, ".claude", "mcp.json");
3073
+ const settingsPath = path14__default.join(projectDir, ".claude", "settings.json");
3074
+ const mcpPath = path14__default.join(projectDir, ".claude", "mcp.json");
2987
3075
  const dir = pluginDir(projectDir);
2988
3076
  let changed = false;
2989
3077
  const settings = await readJsonStrict(settingsPath);
@@ -3017,12 +3105,12 @@ async function uninstall(projectDir) {
3017
3105
  async function detectInstall(projectDir) {
3018
3106
  const dir = pluginDir(projectDir);
3019
3107
  const settings = await readJsonStrict(
3020
- path15__default.join(projectDir, ".claude", "settings.json")
3108
+ path14__default.join(projectDir, ".claude", "settings.json")
3021
3109
  );
3022
- if (existsSync(path15__default.join(dir, ".claude-plugin", "plugin.json")) && settings?.plugins?.includes(dir)) {
3110
+ if (existsSync(path14__default.join(dir, ".claude-plugin", "plugin.json")) && settings?.plugins?.includes(dir)) {
3023
3111
  return { method: "plugin", pluginPath: dir };
3024
3112
  }
3025
- const mcp = await readJsonStrict(path15__default.join(projectDir, ".claude", "mcp.json"));
3113
+ const mcp = await readJsonStrict(path14__default.join(projectDir, ".claude", "mcp.json"));
3026
3114
  if (mcp?.mcpServers && SKAILE_MCP_NAME in mcp.mcpServers) {
3027
3115
  return { method: "mcp" };
3028
3116
  }
@@ -3031,7 +3119,7 @@ async function detectInstall(projectDir) {
3031
3119
  async function enable(projectDir) {
3032
3120
  const detected = await detectInstall(projectDir);
3033
3121
  if (!detected) throw new Error("plugin not installed for claude-code");
3034
- const settingsPath = path15__default.join(projectDir, ".claude", "settings.json");
3122
+ const settingsPath = path14__default.join(projectDir, ".claude", "settings.json");
3035
3123
  const settings = await readJsonStrict(settingsPath) ?? {};
3036
3124
  if (detected.method === "plugin") {
3037
3125
  const disabled2 = settings.disabledPlugins ?? [];
@@ -3053,7 +3141,7 @@ async function enable(projectDir) {
3053
3141
  async function disable(projectDir) {
3054
3142
  const detected = await detectInstall(projectDir);
3055
3143
  if (!detected) throw new Error("plugin not installed for claude-code");
3056
- const settingsPath = path15__default.join(projectDir, ".claude", "settings.json");
3144
+ const settingsPath = path14__default.join(projectDir, ".claude", "settings.json");
3057
3145
  const settings = await readJsonStrict(settingsPath) ?? {};
3058
3146
  if (detected.method === "plugin") {
3059
3147
  const list2 = settings.disabledPlugins ?? [];
@@ -3073,12 +3161,12 @@ async function disable(projectDir) {
3073
3161
  return { changed: true };
3074
3162
  }
3075
3163
  async function status(projectDir) {
3076
- const settingsPath = path15__default.join(projectDir, ".claude", "settings.json");
3077
- const mcpPath = path15__default.join(projectDir, ".claude", "mcp.json");
3164
+ const settingsPath = path14__default.join(projectDir, ".claude", "settings.json");
3165
+ const mcpPath = path14__default.join(projectDir, ".claude", "mcp.json");
3078
3166
  const dir = pluginDir(projectDir);
3079
3167
  const settings = await readJsonStrict(settingsPath);
3080
3168
  const mcp = await readJsonStrict(mcpPath);
3081
- const pluginInstalled = !!(existsSync(path15__default.join(dir, ".claude-plugin", "plugin.json")) && settings?.plugins?.includes(dir));
3169
+ const pluginInstalled = !!(existsSync(path14__default.join(dir, ".claude-plugin", "plugin.json")) && settings?.plugins?.includes(dir));
3082
3170
  const mcpInstalled = !!(mcp?.mcpServers && SKAILE_MCP_NAME in mcp.mcpServers);
3083
3171
  if (!pluginInstalled && !mcpInstalled) {
3084
3172
  return {
@@ -3096,7 +3184,7 @@ async function status(projectDir) {
3096
3184
  installed: "yes",
3097
3185
  enabled: disabled2 ? "no" : "yes",
3098
3186
  method: "plugin",
3099
- location: path15__default.relative(projectDir, dir)
3187
+ location: path14__default.relative(projectDir, dir)
3100
3188
  };
3101
3189
  }
3102
3190
  const disabled = settings?.disabledMcpjsonServers?.includes(SKAILE_MCP_NAME) ?? false;
@@ -3105,7 +3193,7 @@ async function status(projectDir) {
3105
3193
  installed: "yes",
3106
3194
  enabled: disabled ? "no" : "yes",
3107
3195
  method: "mcp",
3108
- location: path15__default.relative(projectDir, mcpPath)
3196
+ location: path14__default.relative(projectDir, mcpPath)
3109
3197
  };
3110
3198
  }
3111
3199
  var SKAILE_MCP_NAME2 = "skaile-workspace";
@@ -3132,7 +3220,7 @@ async function readConfig(p7) {
3132
3220
  }
3133
3221
  }
3134
3222
  async function writeConfig(p7, value) {
3135
- await fs5.mkdir(path15__default.dirname(p7), { recursive: true });
3223
+ await fs5.mkdir(path14__default.dirname(p7), { recursive: true });
3136
3224
  const cleaned = {};
3137
3225
  for (const [k, v] of Object.entries(value)) {
3138
3226
  if (v === void 0) continue;
@@ -3141,7 +3229,7 @@ async function writeConfig(p7, value) {
3141
3229
  await fs5.writeFile(p7, stringify(cleaned));
3142
3230
  }
3143
3231
  function configPath(projectDir) {
3144
- return path15__default.join(projectDir, ".codex", "config.toml");
3232
+ return path14__default.join(projectDir, ".codex", "config.toml");
3145
3233
  }
3146
3234
  async function install2(projectDir) {
3147
3235
  const p7 = configPath(projectDir);
@@ -3152,7 +3240,7 @@ async function install2(projectDir) {
3152
3240
  const matches = previous && JSON.stringify(previous) === JSON.stringify(next);
3153
3241
  let warning;
3154
3242
  if (previous && !matches) {
3155
- warning = `overwrote existing ${SKAILE_MCP_NAME2} entry in ${path15__default.relative(projectDir, p7)}`;
3243
+ warning = `overwrote existing ${SKAILE_MCP_NAME2} entry in ${path14__default.relative(projectDir, p7)}`;
3156
3244
  }
3157
3245
  if (matches) return { changed: false, method: "toml" };
3158
3246
  servers[SKAILE_MCP_NAME2] = next;
@@ -3193,12 +3281,12 @@ async function status2(projectDir) {
3193
3281
  installed: "yes",
3194
3282
  enabled: "n/a",
3195
3283
  method: "mcp",
3196
- location: path15__default.relative(projectDir, p7)
3284
+ location: path14__default.relative(projectDir, p7)
3197
3285
  };
3198
3286
  }
3199
3287
  async function install3(projectDir) {
3200
- const extDir = path15__default.join(projectDir, ".omp", "extensions");
3201
- const extPath = path15__default.join(extDir, "skaile.ts");
3288
+ const extDir = path14__default.join(projectDir, ".omp", "extensions");
3289
+ const extPath = path14__default.join(extDir, "skaile.ts");
3202
3290
  await fs5.mkdir(extDir, { recursive: true });
3203
3291
  const { WorkspacePlugin } = await import('../workspace-plugin/index.js');
3204
3292
  const plugin = new WorkspacePlugin({ projectDir });
@@ -3213,7 +3301,7 @@ async function install3(projectDir) {
3213
3301
  return { changed: true, method: "generated" };
3214
3302
  }
3215
3303
  async function uninstall3(projectDir) {
3216
- const extPath = path15__default.join(projectDir, ".omp", "extensions", "skaile.ts");
3304
+ const extPath = path14__default.join(projectDir, ".omp", "extensions", "skaile.ts");
3217
3305
  try {
3218
3306
  await fs5.unlink(extPath);
3219
3307
  return { changed: true };
@@ -3222,14 +3310,14 @@ async function uninstall3(projectDir) {
3222
3310
  }
3223
3311
  }
3224
3312
  async function status3(projectDir) {
3225
- const extPath = path15__default.join(projectDir, ".omp", "extensions", "skaile.ts");
3313
+ const extPath = path14__default.join(projectDir, ".omp", "extensions", "skaile.ts");
3226
3314
  if (existsSync(extPath)) {
3227
3315
  return {
3228
3316
  backend: "omp",
3229
3317
  installed: "yes",
3230
3318
  enabled: "n/a",
3231
3319
  method: "extension",
3232
- location: path15__default.relative(projectDir, extPath)
3320
+ location: path14__default.relative(projectDir, extPath)
3233
3321
  };
3234
3322
  }
3235
3323
  return {
@@ -3241,7 +3329,7 @@ async function status3(projectDir) {
3241
3329
  };
3242
3330
  }
3243
3331
 
3244
- // cli/src/commands/plugin.ts
3332
+ // cli/src/commands/integration.ts
3245
3333
  var ALL_BACKENDS = ["claude-code", "omp", "codex"];
3246
3334
  var TOGGLE_SUPPORTED = ["claude-code"];
3247
3335
  function resolveDriver(driver) {
@@ -3250,7 +3338,7 @@ function resolveDriver(driver) {
3250
3338
  throw new Error(`unknown driver: ${driver} (expected: claude-code | omp | codex | all)`);
3251
3339
  }
3252
3340
  async function runInstall(opts) {
3253
- const projectDir = path15__default.resolve(opts.projectDir);
3341
+ const projectDir = path14__default.resolve(opts.projectDir);
3254
3342
  const targets = resolveDriver(opts.driver);
3255
3343
  let exitCode = 0;
3256
3344
  if (targets.includes("claude-code")) {
@@ -3305,7 +3393,7 @@ async function runInstall(opts) {
3305
3393
  return exitCode;
3306
3394
  }
3307
3395
  async function runUninstall(opts) {
3308
- const projectDir = path15__default.resolve(opts.projectDir);
3396
+ const projectDir = path14__default.resolve(opts.projectDir);
3309
3397
  const targets = resolveDriver(opts.driver);
3310
3398
  let exitCode = 0;
3311
3399
  if (targets.includes("claude-code")) {
@@ -3341,15 +3429,15 @@ async function runUninstall(opts) {
3341
3429
  if (exitCode === 0) logOk("Plugin uninstalled.");
3342
3430
  return exitCode;
3343
3431
  }
3344
- async function runToggle(opts, action) {
3345
- const projectDir = path15__default.resolve(opts.projectDir);
3432
+ async function runToggle(opts, action3) {
3433
+ const projectDir = path14__default.resolve(opts.projectDir);
3346
3434
  const requestedAll = opts.driver === "all";
3347
3435
  const targets = resolveDriver(opts.driver);
3348
3436
  if (!requestedAll) {
3349
3437
  const unsupported = targets.filter((t) => !TOGGLE_SUPPORTED.includes(t));
3350
3438
  if (unsupported.length > 0) {
3351
3439
  logErr(
3352
- `${action} is only supported for claude-code; for ${unsupported.join(", ")} use uninstall/install`
3440
+ `${action3} is only supported for claude-code; for ${unsupported.join(", ")} use uninstall/install`
3353
3441
  );
3354
3442
  return 2;
3355
3443
  }
@@ -3357,27 +3445,27 @@ async function runToggle(opts, action) {
3357
3445
  let exitCode = 0;
3358
3446
  for (const t of targets) {
3359
3447
  if (!TOGGLE_SUPPORTED.includes(t)) {
3360
- logInfo(`${t}: ${action} not supported; skipping`);
3448
+ logInfo(`${t}: ${action3} not supported; skipping`);
3361
3449
  continue;
3362
3450
  }
3363
3451
  if (t === "claude-code") {
3364
3452
  try {
3365
- const r = action === "enable" ? await enable(projectDir) : await disable(projectDir);
3453
+ const r = action3 === "enable" ? await enable(projectDir) : await disable(projectDir);
3366
3454
  if (r.changed) {
3367
- logOk(`claude-code: ${action}d`);
3455
+ logOk(`claude-code: ${action3}d`);
3368
3456
  } else {
3369
- logInfo(`claude-code: already ${action}d`);
3457
+ logInfo(`claude-code: already ${action3}d`);
3370
3458
  }
3371
3459
  } catch (e) {
3372
- logErr(`claude-code ${action}: ${e instanceof Error ? e.message : String(e)}`);
3460
+ logErr(`claude-code ${action3}: ${e instanceof Error ? e.message : String(e)}`);
3373
3461
  exitCode = 1;
3374
3462
  }
3375
3463
  }
3376
3464
  }
3377
3465
  return exitCode;
3378
3466
  }
3379
- async function runStatus(opts) {
3380
- const projectDir = path15__default.resolve(opts.projectDir);
3467
+ async function runStatus2(opts) {
3468
+ const projectDir = path14__default.resolve(opts.projectDir);
3381
3469
  const targets = resolveDriver(opts.driver);
3382
3470
  const rows = [];
3383
3471
  let exitCode = 0;
@@ -3448,7 +3536,7 @@ async function runHook(event) {
3448
3536
  await plugin.shutdown();
3449
3537
  return;
3450
3538
  }
3451
- const store = new PluginStore(path15__default.join(projectDir, ".skaile", "plugin-state.json"));
3539
+ const store = new PluginStore(path14__default.join(projectDir, ".skaile", "plugin-state.json"));
3452
3540
  await store.load();
3453
3541
  const status4 = store.get("connector:status");
3454
3542
  if (status4 && typeof status4 === "object" && Object.keys(status4).length > 0) {
@@ -3463,9 +3551,9 @@ async function runHook(event) {
3463
3551
  );
3464
3552
  }
3465
3553
  }
3466
- function makePluginCommand() {
3467
- const cmd = new Command("plugin").description(
3468
- "Manage skaile workspace plugin (Claude Code / OMP / Codex)"
3554
+ function makeIntegrationCommand() {
3555
+ const cmd = new Command("integration").description(
3556
+ "Manage skaile agent integration / workspace-plugin adapter (Claude Code / OMP / Codex)"
3469
3557
  );
3470
3558
  cmd.command("install").description("Install skaile workspace plugin").option("--driver <name>", "Target: claude-code | omp | codex | all", "all").option("--project-dir <path>", "Project directory", process.cwd()).option(
3471
3559
  "--full",
@@ -3483,7 +3571,7 @@ function makePluginCommand() {
3483
3571
  process.exitCode = await runToggle(opts, "disable");
3484
3572
  });
3485
3573
  cmd.command("status").description("Show install / enable status across backends").option("--driver <name>", "Target: claude-code | omp | codex | all", "all").option("--project-dir <path>", "Project directory", process.cwd()).action(async (opts) => {
3486
- process.exitCode = await runStatus(opts);
3574
+ process.exitCode = await runStatus2(opts);
3487
3575
  });
3488
3576
  cmd.command("hook <event>").description(
3489
3577
  "Run a Claude Code lifecycle hook (session-start | session-end | user-prompt-submit)"
@@ -3508,12 +3596,189 @@ function makePluginCommand() {
3508
3596
  cmd.action(() => cmd.help());
3509
3597
  return cmd;
3510
3598
  }
3599
+ function makeOutdatedCommand() {
3600
+ return new Command("outdated").description("Check for assets behind their repo").argument("[name]", "Check a specific asset (kind:name)").option("--project-dir <path>", "Project directory", process.cwd()).addOption(
3601
+ new Option("--target <agent>", "Driver target").default("claude-code").choices(SUPPORTED_DRIVER_TARGETS)
3602
+ ).action((name, opts) => {
3603
+ const am2 = new AssetManager({
3604
+ projectDir: path14__default.resolve(opts.projectDir),
3605
+ driverTarget: opts.target
3606
+ });
3607
+ const entries = am2.outdated();
3608
+ if (entries.length === 0) {
3609
+ logInfo("All assets are up to date.");
3610
+ return;
3611
+ }
3612
+ const filtered = name ? entries.filter((e) => `${e.kind}:${e.name}` === name || e.name === name) : entries;
3613
+ if (filtered.length === 0) {
3614
+ logInfo(`${name} is up to date.`);
3615
+ return;
3616
+ }
3617
+ const nameW = Math.max(4, ...filtered.map((e) => e.name.length));
3618
+ console.log();
3619
+ console.log(S.heading(" Outdated Assets"));
3620
+ console.log(` ${S.rule(nameW + 40)}`);
3621
+ for (const e of filtered) {
3622
+ console.log(
3623
+ ` ${kindColorPad(e.kind)} ${e.name.padEnd(nameW)} ${S.dim(e.repository)} ${pc5.yellow(`${e.behind} commit(s) behind`)}`
3624
+ );
3625
+ }
3626
+ console.log();
3627
+ logWarn(`Run ${S.cmd("skaile update")} to re-deploy.`);
3628
+ });
3629
+ }
3630
+ function makePatchCommand() {
3631
+ const cmd = new Command("patch").description("Patch workflow for skill improvement");
3632
+ cmd.command("extract <ref>").alias("start").description("Extract asset for local editing").option("--project-dir <path>", "Project directory", process.cwd()).action((ref, opts) => {
3633
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
3634
+ try {
3635
+ const dest = am2.patch(ref);
3636
+ logOk(`Extracted to ${S.dim(dest)}`);
3637
+ console.log(` Edit the files, then run ${S.cmd(`skaile patch commit ${ref}`)}`);
3638
+ } catch (err) {
3639
+ logErr(String(err));
3640
+ process.exit(1);
3641
+ }
3642
+ });
3643
+ cmd.command("commit <ref>").description("Generate .patch file from edits").option("--project-dir <path>", "Project directory", process.cwd()).action((ref, opts) => {
3644
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
3645
+ try {
3646
+ const patchFile = am2.patchCommit(ref);
3647
+ logOk(`Patch saved to ${S.dim(patchFile)}`);
3648
+ console.log(` Add to skaile.yaml patches section, then run ${S.cmd("skaile install")}`);
3649
+ } catch (err) {
3650
+ logErr(String(err));
3651
+ process.exit(1);
3652
+ }
3653
+ });
3654
+ cmd.command("submit <ref>").description("Apply patch to repo clone and prepare for PR").option("--project-dir <path>", "Project directory", process.cwd()).action((ref, opts) => {
3655
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
3656
+ try {
3657
+ am2.patchSubmit(ref);
3658
+ logOk("Patch applied to repo clone and committed.");
3659
+ console.log(
3660
+ ` Push upstream from the source repo directly \u2014 the legacy ${S.cmd("skaile repo contrib push")} command was removed on 2026-05-12.`
3661
+ );
3662
+ } catch (err) {
3663
+ logErr(String(err));
3664
+ process.exit(1);
3665
+ }
3666
+ });
3667
+ cmd.command("remove <ref>").description("Remove local patch after upstream merge").option("--project-dir <path>", "Project directory", process.cwd()).action((ref, opts) => {
3668
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
3669
+ am2.patchRemove(ref);
3670
+ logOk(`Patch removed for ${ref}`);
3671
+ });
3672
+ cmd.action(() => cmd.help());
3673
+ return cmd;
3674
+ }
3675
+ function action2(fn) {
3676
+ return async (...args) => {
3677
+ try {
3678
+ await fn(...args);
3679
+ } catch (err) {
3680
+ logErr(err instanceof Error ? err.message : String(err));
3681
+ process.exitCode = 1;
3682
+ }
3683
+ };
3684
+ }
3685
+ async function reconcileAndReport(projectDir, plugins) {
3686
+ const { reconcilePlugins } = await import('../plugin-store-6OENKNFW.js');
3687
+ if (plugins.length === 0) {
3688
+ logInfo("No plugins declared \u2014 nothing to reconcile.");
3689
+ return;
3690
+ }
3691
+ try {
3692
+ const result = await reconcilePlugins(projectDir, plugins);
3693
+ if (result.changed) logOk(`Reconciled plugin store (${result.reason}).`);
3694
+ else logInfo(`Plugin store ${result.reason}.`);
3695
+ } catch (err) {
3696
+ logWarn(`reconcile skipped: ${err instanceof Error ? err.message : String(err)}`);
3697
+ }
3698
+ }
3699
+ async function runInstall2(spec, opts) {
3700
+ const projectDir = path14__default.resolve(opts.projectDir);
3701
+ const { WorkspaceYamlEditor: WorkspaceYamlEditor2 } = await import('../core/index.js');
3702
+ const { specName } = await import('../plugin-store-6OENKNFW.js');
3703
+ const yamlPath = path14__default.join(projectDir, "skaile.yaml");
3704
+ const editor = WorkspaceYamlEditor2.load(yamlPath);
3705
+ const replaced = editor.addPlugin(spec, specName);
3706
+ editor.save();
3707
+ if (replaced) logOk(`Updated ${S.cmd(specName(spec))} \u2192 ${S.cmd(spec)} in skaile.yaml`);
3708
+ else logOk(`Added ${S.cmd(spec)} to skaile.yaml plugins`);
3709
+ await reconcileAndReport(projectDir, editor.getPlugins());
3710
+ }
3711
+ async function runRemove(name, opts) {
3712
+ const projectDir = path14__default.resolve(opts.projectDir);
3713
+ const { WorkspaceYamlEditor: WorkspaceYamlEditor2 } = await import('../core/index.js');
3714
+ const { specName } = await import('../plugin-store-6OENKNFW.js');
3715
+ const yamlPath = path14__default.join(projectDir, "skaile.yaml");
3716
+ const editor = WorkspaceYamlEditor2.load(yamlPath);
3717
+ const removed = editor.removePlugin(name, specName);
3718
+ if (!removed) {
3719
+ logInfo(`No plugin matching ${S.cmd(name)} in skaile.yaml plugins.`);
3720
+ return;
3721
+ }
3722
+ editor.save();
3723
+ logOk(`Removed ${S.cmd(name)} from skaile.yaml plugins`);
3724
+ await reconcileAndReport(projectDir, editor.getPlugins());
3725
+ }
3726
+ async function runList(opts) {
3727
+ const projectDir = path14__default.resolve(opts.projectDir);
3728
+ const { resolveSkWorkspaceConfig: resolveSkWorkspaceConfig2 } = await import('../core/index.js');
3729
+ const config = resolveSkWorkspaceConfig2(projectDir);
3730
+ const declared = config.plugins ?? [];
3731
+ console.log();
3732
+ console.log(S.heading(" Declared plugins (skaile.yaml):"));
3733
+ if (declared.length === 0) {
3734
+ console.log(` ${S.dim("(none)")}`);
3735
+ } else {
3736
+ for (const spec of declared) console.log(` ${S.dim("\xB7")} ${S.cmd(spec)}`);
3737
+ }
3738
+ const { createPluginRegistry } = await import('../plugin-registry/index.js');
3739
+ const registry = createPluginRegistry();
3740
+ if (declared.length > 0) {
3741
+ try {
3742
+ const { loadPlugins } = await import('../plugin-store-6OENKNFW.js');
3743
+ const result = await loadPlugins(projectDir, declared, registry);
3744
+ for (const f of result.failed) logWarn(f.error);
3745
+ } catch (err) {
3746
+ logWarn(`could not load plugins: ${err instanceof Error ? err.message : String(err)}`);
3747
+ }
3748
+ }
3749
+ const kinds = [
3750
+ { kind: "driver", label: "drivers" },
3751
+ { kind: "connector", label: "connectors" },
3752
+ { kind: "deployTarget", label: "deploy targets" }
3753
+ ];
3754
+ console.log();
3755
+ console.log(S.heading(" Contributed targets:"));
3756
+ let any = false;
3757
+ for (const { kind, label } of kinds) {
3758
+ const metas = registry.list(kind);
3759
+ if (metas.length === 0) continue;
3760
+ any = true;
3761
+ console.log(` ${S.label(label)}: ${metas.map((m) => S.cmd(m.id)).join(", ")}`);
3762
+ }
3763
+ if (!any) console.log(` ${S.dim("(none \u2014 plugins not installed, or contribute nothing)")}`);
3764
+ console.log();
3765
+ }
3766
+ function makePluginCommand() {
3767
+ const cmd = new Command("plugin").description(
3768
+ "Manage registry plugins (drivers / connectors / deploy targets) declared in skaile.yaml"
3769
+ );
3770
+ cmd.command("install <spec>").description("Add a plugin spec to skaile.yaml plugins and reconcile the store").option("--project-dir <path>", "Project directory", process.cwd()).action(action2(runInstall2));
3771
+ cmd.command("remove <name>").description("Remove a plugin (by package name) from skaile.yaml plugins and reconcile").option("--project-dir <path>", "Project directory", process.cwd()).action(action2(runRemove));
3772
+ cmd.command("list").description("List declared plugins and the targets they contribute").option("--project-dir <path>", "Project directory", process.cwd()).action(action2(runList));
3773
+ cmd.action(() => cmd.help());
3774
+ return cmd;
3775
+ }
3511
3776
  function makePresetCommand() {
3512
3777
  const cmd = new Command("preset").description("Scaffold and validate preset YAML files");
3513
3778
  cmd.command("init [name]").description("Scaffold a new .preset.yaml file").option("--dir <path>", "Output directory", process.cwd()).action(async (name, opts) => {
3514
3779
  const presetName = name ?? "my-preset";
3515
3780
  const filename = `${presetName}.preset.yaml`;
3516
- const outPath = path15__default.join(path15__default.resolve(opts.dir), filename);
3781
+ const outPath = path14__default.join(path14__default.resolve(opts.dir), filename);
3517
3782
  if (existsSync(outPath)) {
3518
3783
  logErr(`File already exists: ${outPath}`);
3519
3784
  logInfo("Choose a different name or remove the existing file.");
@@ -3527,7 +3792,7 @@ function makePresetCommand() {
3527
3792
  logInfo(` skaile preset validate ${filename}`);
3528
3793
  });
3529
3794
  cmd.command("validate <path>").description("Validate a preset YAML file (schema + cycles + nesting depth)").action(async (filePath) => {
3530
- const resolved = path15__default.resolve(filePath);
3795
+ const resolved = path14__default.resolve(filePath);
3531
3796
  if (!existsSync(resolved)) {
3532
3797
  logErr(`File not found: ${resolved}`);
3533
3798
  process.exit(1);
@@ -3553,7 +3818,7 @@ function makePresetCommand() {
3553
3818
  logInfo(`Nested preset refs: ${nestedRefs.length} (depth validated at apply-time)`);
3554
3819
  }
3555
3820
  const { detectCycles } = await import('../discovery/index.js');
3556
- const presetRef = path15__default.basename(resolved, ".preset.yaml");
3821
+ const presetRef = path14__default.basename(resolved, ".preset.yaml");
3557
3822
  const edges = [];
3558
3823
  for (const item of preset.items) {
3559
3824
  if (item.ref) {
@@ -3677,8 +3942,8 @@ function makeInstallCommand() {
3677
3942
  const spinner6 = p5.spinner();
3678
3943
  spinner6.start(`Installing ${ref}`);
3679
3944
  try {
3680
- const { openCatalogSource: openCatalogSource2, openLibrary: openLibrary2 } = await import('../open-library-IOYWFK7M.js');
3681
- const catalog = await openCatalogSource2({ projectDir: path15__default.resolve(opts.projectDir) });
3945
+ const { openCatalogSource: openCatalogSource2, openLibrary: openLibrary2 } = await import('../open-library-DWAQFUSQ.js');
3946
+ const catalog = await openCatalogSource2({ projectDir: path14__default.resolve(opts.projectDir) });
3682
3947
  if (!supportsInstallManifest(catalog)) {
3683
3948
  throw new Error(
3684
3949
  "pointer-only install (skaile install <ref>) requires a tRPC-framed Catalog. The configured catalog uses REST framing, which does not serve install manifests. Set catalog.url to https://skaile.store, or catalog.framing: trpc, in ~/.skaile/config.yaml."
@@ -3707,9 +3972,9 @@ function makeInstallCommand() {
3707
3972
  }
3708
3973
  return;
3709
3974
  }
3710
- const projectDir = path15__default.resolve(opts.projectDir);
3975
+ const projectDir = path14__default.resolve(opts.projectDir);
3711
3976
  try {
3712
- const { ensureSourcesCloned } = await import('../ensure-sources-IDVQ77NJ.js');
3977
+ const { ensureSourcesCloned } = await import('../ensure-sources-COGVKY44.js');
3713
3978
  const hydrate = ensureSourcesCloned(projectDir, { quiet: true });
3714
3979
  if (hydrate.cloned.length > 0) {
3715
3980
  logOk(`Cloned source(s): ${hydrate.cloned.join(", ")}`);
@@ -3762,7 +4027,7 @@ function makeInstallCommand() {
3762
4027
  }
3763
4028
  function makeCheckCommand() {
3764
4029
  return new Command("check").description("Check for unmet requirements").option("--project-dir <path>", "Project directory", process.cwd()).action((opts) => {
3765
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
4030
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
3766
4031
  const issues = am2.doctor();
3767
4032
  if (issues.length === 0) {
3768
4033
  logOk("All dependencies satisfied.");
@@ -3779,10 +4044,10 @@ function makeCheckCommand() {
3779
4044
  function makeCleanCommand() {
3780
4045
  return new Command("clean").description("Remove all skaile-managed assets from the workspace").option("--all", "Full reset: also remove history, patches, repos, and lock file").option("--dry-run", "Show what would be removed without doing it").option("-y, --yes", "Skip confirmation prompt").option("--project-dir <path>", "Project directory", process.cwd()).option("--target <agent>", "Agent framework", "claude-code").action(async (opts) => {
3781
4046
  const am2 = new AssetManager({
3782
- projectDir: path15__default.resolve(opts.projectDir),
4047
+ projectDir: path14__default.resolve(opts.projectDir),
3783
4048
  driverTarget: opts.target
3784
4049
  });
3785
- const lock = readLock(path15__default.resolve(opts.projectDir, "skaile.lock.yaml"));
4050
+ const lock = readLock(path14__default.resolve(opts.projectDir, "skaile.lock.yaml"));
3786
4051
  if (!lock || Object.keys(lock.assets).length === 0) {
3787
4052
  logInfo("Nothing to clean (no skaile-managed assets found).");
3788
4053
  return;
@@ -3835,14 +4100,14 @@ function makeCleanCommand() {
3835
4100
  }
3836
4101
  function makeRebuildCommand() {
3837
4102
  return new Command("rebuild").description("Re-snapshot inline-snapshot composition items and bump prompt version").argument("[agent]", "Agent name or path (defaults to current project agent)").option("--project-dir <dir>", "Project directory", process.cwd()).action(async (agentArg, opts) => {
3838
- const projectDir = path15__default.resolve(opts.projectDir);
4103
+ const projectDir = path14__default.resolve(opts.projectDir);
3839
4104
  let agentDir;
3840
4105
  if (agentArg) {
3841
4106
  if (agentArg.includes("/") || agentArg.includes("\\")) {
3842
- agentDir = path15__default.resolve(projectDir, agentArg);
4107
+ agentDir = path14__default.resolve(projectDir, agentArg);
3843
4108
  } else {
3844
4109
  const resolved = resolveAgentDir(projectDir);
3845
- agentDir = resolved ?? path15__default.resolve(projectDir, agentArg);
4110
+ agentDir = resolved ?? path14__default.resolve(projectDir, agentArg);
3846
4111
  }
3847
4112
  } else {
3848
4113
  const resolved = resolveAgentDir(projectDir);
@@ -3920,7 +4185,7 @@ function makeFlowEventHandler() {
3920
4185
  }
3921
4186
  function makeRunCommand() {
3922
4187
  const cmd = new Command("run").description("Start a flow or run a single-shot text prompt").argument("[flow-id-or-text...]", "Flow ID or text prompt").option("--project-dir <path>", "Project directory", process.cwd()).option("--driver <name>", "Driver backend (claude-sdk, codex, omp)").option("--provider <name>", "LLM provider").option("--model <name>", "Model override").option("--label <label>", "Human-readable session label").option("--dry-run", "Print plan without executing").option("--skill <name>", "Skill name (for single-shot mode)").action(async (positional, opts) => {
3923
- const projectDir = path15__default.resolve(opts.projectDir);
4188
+ const projectDir = path14__default.resolve(opts.projectDir);
3924
4189
  const cliDriver = opts.driver;
3925
4190
  const dryRun = opts.dryRun ?? false;
3926
4191
  let flowId = positional[0];
@@ -3974,15 +4239,15 @@ function makeRunCommand() {
3974
4239
  let flowPath;
3975
4240
  let dir = projectDir;
3976
4241
  for (let i = 0; i < 6; i++) {
3977
- const candidate = path15__default.join(dir, "ai-assets");
4242
+ const candidate = path14__default.join(dir, "ai-assets");
3978
4243
  if (fs10__default.existsSync(candidate)) {
3979
4244
  for (const domain of fs10__default.readdirSync(candidate)) {
3980
- const p_ = path15__default.join(candidate, domain, "flows", `${flowId}.flow.yaml`);
4245
+ const p_ = path14__default.join(candidate, domain, "flows", `${flowId}.flow.yaml`);
3981
4246
  if (fs10__default.existsSync(p_)) {
3982
4247
  flowPath = p_;
3983
4248
  break;
3984
4249
  }
3985
- const legacy = path15__default.join(candidate, domain, "flows", `${flowId}.json`);
4250
+ const legacy = path14__default.join(candidate, domain, "flows", `${flowId}.json`);
3986
4251
  if (fs10__default.existsSync(legacy)) {
3987
4252
  flowPath = legacy;
3988
4253
  break;
@@ -3990,16 +4255,16 @@ function makeRunCommand() {
3990
4255
  }
3991
4256
  break;
3992
4257
  }
3993
- dir = path15__default.dirname(dir);
4258
+ dir = path14__default.dirname(dir);
3994
4259
  }
3995
4260
  if (!flowPath) {
3996
4261
  for (const domain of fs10__default.readdirSync(AI_RESOURCES)) {
3997
- const p_ = path15__default.join(AI_RESOURCES, domain, "flows", `${flowId}.flow.yaml`);
4262
+ const p_ = path14__default.join(AI_RESOURCES, domain, "flows", `${flowId}.flow.yaml`);
3998
4263
  if (fs10__default.existsSync(p_)) {
3999
4264
  flowPath = p_;
4000
4265
  break;
4001
4266
  }
4002
- const legacy = path15__default.join(AI_RESOURCES, domain, "flows", `${flowId}.json`);
4267
+ const legacy = path14__default.join(AI_RESOURCES, domain, "flows", `${flowId}.json`);
4003
4268
  if (fs10__default.existsSync(legacy)) {
4004
4269
  flowPath = legacy;
4005
4270
  break;
@@ -4033,7 +4298,7 @@ function makeRunCommand() {
4033
4298
  }
4034
4299
  function makeResumeCommand() {
4035
4300
  const cmd = new Command("resume").description("Resume current session").option("--project-dir <path>", "Project directory", process.cwd()).option("--session <run-id>", "Target session by runId").option("--dry-run", "Print plan without executing").action(async (opts) => {
4036
- const projectDir = path15__default.resolve(opts.projectDir);
4301
+ const projectDir = path14__default.resolve(opts.projectDir);
4037
4302
  const sessionId = opts.session;
4038
4303
  const dryRun = opts.dryRun ?? false;
4039
4304
  const session = sessionId ? await loadSessionById(projectDir, sessionId) : await loadSession(projectDir);
@@ -4060,7 +4325,7 @@ function makeResumeCommand() {
4060
4325
  }
4061
4326
  function makeStatusCommand() {
4062
4327
  return new Command("status").description("Show current session state").option("--project-dir <path>", "Project directory", process.cwd()).action(async (opts) => {
4063
- const projectDir = path15__default.resolve(opts.projectDir);
4328
+ const projectDir = path14__default.resolve(opts.projectDir);
4064
4329
  const session = await loadSession(projectDir);
4065
4330
  if (!session) {
4066
4331
  logInfo("No active session.");
@@ -4085,7 +4350,7 @@ function makeStatusCommand() {
4085
4350
  }
4086
4351
  function makeClearCommand() {
4087
4352
  return new Command("clear").description("Unset current session pointer").option("--project-dir <path>", "Project directory", process.cwd()).action(async (opts) => {
4088
- const projectDir = path15__default.resolve(opts.projectDir);
4353
+ const projectDir = path14__default.resolve(opts.projectDir);
4089
4354
  await clearSession(projectDir);
4090
4355
  logOk("Session cleared.");
4091
4356
  });
@@ -4095,7 +4360,7 @@ function makeReplCommand() {
4095
4360
  const { findWorkspaceRoot: findWorkspaceRoot2 } = await import('../core/index.js');
4096
4361
  const { startRepl } = await import('../tui/index.js');
4097
4362
  const os = await import('os');
4098
- const userCwd = path15__default.resolve(opts.projectDir ?? process.cwd());
4363
+ const userCwd = path14__default.resolve(opts.projectDir ?? process.cwd());
4099
4364
  const workspaceRoot = findWorkspaceRoot2(userCwd);
4100
4365
  let projectDir;
4101
4366
  let agentCwd;
@@ -4117,12 +4382,12 @@ function makeReplCommand() {
4117
4382
  p5.cancel("Cancelled.");
4118
4383
  process.exit(0);
4119
4384
  }
4120
- const tmpDir = fs10__default.mkdtempSync(path15__default.join(os.tmpdir(), "skaile-repl-"));
4385
+ const tmpDir = fs10__default.mkdtempSync(path14__default.join(os.tmpdir(), "skaile-repl-"));
4121
4386
  projectDir = tmpDir;
4122
4387
  agentCwd = userCwd;
4123
4388
  logOk(`Temporary workspace: ${S.cmd(tmpDir)}`);
4124
4389
  if (!driverOverride) {
4125
- const claudeDir = path15__default.join(os.homedir(), ".claude");
4390
+ const claudeDir = path14__default.join(os.homedir(), ".claude");
4126
4391
  if (fs10__default.existsSync(claudeDir)) {
4127
4392
  driverOverride = "claude-sdk";
4128
4393
  logInfo(`Detected ${S.cmd("~/.claude")} \u2192 using ${S.cmd("claude-sdk")} backend`);
@@ -4154,6 +4419,7 @@ function makeServeCommand() {
4154
4419
  await runCompileTest({ ...opts, withCodex: opts.withCodex ?? false });
4155
4420
  return;
4156
4421
  }
4422
+ await ensurePluginsLoadedForServe(opts.projectDir);
4157
4423
  const { startAgentServer } = await import('../runner/index.js');
4158
4424
  await startAgentServer({
4159
4425
  port: parseInt(opts.port, 10),
@@ -4167,6 +4433,25 @@ function makeServeCommand() {
4167
4433
  }
4168
4434
  );
4169
4435
  }
4436
+ async function ensurePluginsLoadedForServe(projectDir) {
4437
+ const { logInfo: logInfo2, logWarn: logWarn2 } = await import('../helpers-I3SREIC3.js');
4438
+ try {
4439
+ const { resolveSkWorkspaceConfig: resolveSkWorkspaceConfig2 } = await import('../core/index.js');
4440
+ const config = resolveSkWorkspaceConfig2(projectDir);
4441
+ if (!config.plugins || config.plugins.length === 0) return;
4442
+ const { ensurePluginsLoaded } = await import('../plugin-store-6OENKNFW.js');
4443
+ const { pluginRegistry } = await import('../plugin-registry/index.js');
4444
+ const result = await ensurePluginsLoaded(projectDir, config.plugins, pluginRegistry);
4445
+ if (result.loaded.length > 0) {
4446
+ logInfo2(`Loaded ${result.loaded.length} plugin(s): ${result.loaded.join(", ")}`);
4447
+ }
4448
+ for (const f of result.failed) {
4449
+ logWarn2(f.error);
4450
+ }
4451
+ } catch (err) {
4452
+ logWarn2(`plugin store skipped: ${err instanceof Error ? err.message : String(err)}`);
4453
+ }
4454
+ }
4170
4455
  async function runCompileTest(opts) {
4171
4456
  const { logOk: logOk2, logErr: logErr2, logInfo: logInfo2, S: S2 } = await import('../helpers-I3SREIC3.js');
4172
4457
  const { tmpdir } = await import('os');
@@ -4645,7 +4930,7 @@ function resolveMode(opts) {
4645
4930
  if (opts.forceLocal && opts.forceRemote) {
4646
4931
  throw new Error("Cannot use both --local and --remote");
4647
4932
  }
4648
- const startDir = path15__default.resolve(opts.projectDir ?? process.cwd());
4933
+ const startDir = path14__default.resolve(opts.projectDir ?? process.cwd());
4649
4934
  const localDb = findLogsDb(startDir);
4650
4935
  if (opts.forceLocal) {
4651
4936
  if (!localDb) {
@@ -4678,14 +4963,14 @@ function resolveMode(opts) {
4678
4963
  function findLogsDb(startDir) {
4679
4964
  let dir = startDir;
4680
4965
  for (let i = 0; i < MAX_WALK_LEVELS; i++) {
4681
- const candidate = path15__default.join(dir, ".skaile", "logs.db");
4966
+ const candidate = path14__default.join(dir, ".skaile", "logs.db");
4682
4967
  if (existsSync(candidate)) {
4683
4968
  try {
4684
4969
  if (statSync(candidate).isFile()) return candidate;
4685
4970
  } catch {
4686
4971
  }
4687
4972
  }
4688
- const parent = path15__default.dirname(dir);
4973
+ const parent = path14__default.dirname(dir);
4689
4974
  if (parent === dir) return void 0;
4690
4975
  dir = parent;
4691
4976
  }
@@ -4711,7 +4996,7 @@ function readApiToken() {
4711
4996
  }
4712
4997
  function readGlobalSettings() {
4713
4998
  try {
4714
- const settingsPath = path15__default.join(homedir(), ".skaile", "settings.json");
4999
+ const settingsPath = path14__default.join(homedir(), ".skaile", "settings.json");
4715
5000
  if (!existsSync(settingsPath)) return {};
4716
5001
  return JSON.parse(readFileSync(settingsPath, "utf8"));
4717
5002
  } catch {
@@ -4859,7 +5144,7 @@ function parsePositiveInt(value, flag) {
4859
5144
  function makeSessionCommand() {
4860
5145
  const cmd = new Command("session").description("Manage sessions");
4861
5146
  cmd.command("list").description("List all sessions for a project").option("--project-dir <path>", "Project directory", process.cwd()).action(async (opts) => {
4862
- const projectDir = path15__default.resolve(opts.projectDir);
5147
+ const projectDir = path14__default.resolve(opts.projectDir);
4863
5148
  const sessions = await listSessions(projectDir);
4864
5149
  const current = await loadSession(projectDir);
4865
5150
  if (sessions.length === 0) {
@@ -4887,7 +5172,7 @@ function makeSessionCommand() {
4887
5172
  console.log();
4888
5173
  });
4889
5174
  cmd.command("show <run-id>").description("Show a specific session").option("--project-dir <path>", "Project directory", process.cwd()).action(async (runId, opts) => {
4890
- const projectDir = path15__default.resolve(opts.projectDir);
5175
+ const projectDir = path14__default.resolve(opts.projectDir);
4891
5176
  const session = await loadSessionById(projectDir, runId);
4892
5177
  if (!session) {
4893
5178
  logErr(`Session not found: ${runId}`);
@@ -4896,12 +5181,12 @@ function makeSessionCommand() {
4896
5181
  console.log(JSON.stringify(session, null, 2));
4897
5182
  });
4898
5183
  cmd.command("switch <run-id>").description("Switch the current session").option("--project-dir <path>", "Project directory", process.cwd()).action(async (runId, opts) => {
4899
- const projectDir = path15__default.resolve(opts.projectDir);
5184
+ const projectDir = path14__default.resolve(opts.projectDir);
4900
5185
  await setCurrentSession(projectDir, runId);
4901
5186
  logOk(`Switched to session: ${S.dim(runId.slice(0, 8))}`);
4902
5187
  });
4903
5188
  cmd.command("delete <run-id>").description("Delete a session").option("--project-dir <path>", "Project directory", process.cwd()).action(async (runId, opts) => {
4904
- const projectDir = path15__default.resolve(opts.projectDir);
5189
+ const projectDir = path14__default.resolve(opts.projectDir);
4905
5190
  await deleteSession(projectDir, runId);
4906
5191
  logOk(`Deleted session: ${S.dim(runId.slice(0, 8))}`);
4907
5192
  });
@@ -4964,7 +5249,7 @@ function showAsset(am2, kind, name) {
4964
5249
  function makeShowCommand() {
4965
5250
  return new Command("show").description("Show deployed assets overview, or print asset content").argument("[kind]", "Asset kind (skill, agent, prompt, flow, bundle, contract)").argument("[name]", "Asset name").option("--project-dir <path>", "Project directory", process.cwd()).option("--target <agent>", "Agent framework", "claude-code").action((kind, name, opts) => {
4966
5251
  const am2 = new AssetManager({
4967
- projectDir: path15__default.resolve(opts.projectDir),
5252
+ projectDir: path14__default.resolve(opts.projectDir),
4968
5253
  driverTarget: opts.target
4969
5254
  });
4970
5255
  if (!kind) {
@@ -5002,10 +5287,10 @@ function addSourceManifestCommands(src) {
5002
5287
 
5003
5288
  // cli/src/commands/source.ts
5004
5289
  function sourcesDir() {
5005
- return path15.join(skaileHomeDir(), "sources");
5290
+ return path14.join(skaileHomeDir(), "sources");
5006
5291
  }
5007
5292
  function sourceClonePath(name) {
5008
- return path15.join(sourcesDir(), name);
5293
+ return path14.join(sourcesDir(), name);
5009
5294
  }
5010
5295
  function deriveSlug(url) {
5011
5296
  return url.replace(/\.git$/, "").split(/[/:]/).pop() ?? "source";
@@ -5018,7 +5303,7 @@ function requireProjectYamlPath() {
5018
5303
  );
5019
5304
  process.exit(1);
5020
5305
  }
5021
- return path15.join(root, workspaceConfigFilename());
5306
+ return path14.join(root, workspaceConfigFilename());
5022
5307
  }
5023
5308
  function readProjectSources(yamlPath) {
5024
5309
  if (!existsSync(yamlPath)) return [];
@@ -5112,7 +5397,7 @@ function makeSourceCommand() {
5112
5397
  const result = await refreshManifestCache(entry, opts.dev);
5113
5398
  logOk(`Indexed ${result.assetsUpdated} of ${result.assetsFound} asset(s) from "${slug}".`);
5114
5399
  for (const err of result.errors) logWarn(err);
5115
- logOk(`Source "${slug}" registered in ${path15.relative(process.cwd(), yamlPath)}.`);
5400
+ logOk(`Source "${slug}" registered in ${path14.relative(process.cwd(), yamlPath)}.`);
5116
5401
  }
5117
5402
  );
5118
5403
  cmd.command("list").description("List sources registered in this project's skaile.yaml").option("--json", "Output as JSON").action(async (opts) => {
@@ -5371,7 +5656,7 @@ function printTree(node, prefix = "", isLast = true) {
5371
5656
  }
5372
5657
  function makeTreeCommand() {
5373
5658
  return new Command("tree").description("Show full dependency tree").option("--project-dir <path>", "Project directory", process.cwd()).action((opts) => {
5374
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
5659
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
5375
5660
  const root = am2.tree();
5376
5661
  if (root.children.length === 0) {
5377
5662
  logInfo("No dependencies in lock file. Run `skaile install` first.");
@@ -5389,7 +5674,7 @@ function makeUpdateCommand() {
5389
5674
  try {
5390
5675
  const catalogSpinner = p5.spinner();
5391
5676
  catalogSpinner.start("Refreshing catalog cache");
5392
- const remote = await openCatalogSource({ projectDir: path15__default.resolve(opts.projectDir) });
5677
+ const remote = await openCatalogSource({ projectDir: path14__default.resolve(opts.projectDir) });
5393
5678
  const result2 = await remote.refresh();
5394
5679
  catalogSpinner.stop(
5395
5680
  `Catalog refreshed: ${S.heading(String(result2.assetsCached))} assets cached`
@@ -5401,7 +5686,7 @@ function makeUpdateCommand() {
5401
5686
  }
5402
5687
  }
5403
5688
  if (opts.catalogOnly) return;
5404
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
5689
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
5405
5690
  const spinner5 = p5.spinner();
5406
5691
  spinner5.start("Re-deploying assets");
5407
5692
  const result = await am2.install();
@@ -5447,7 +5732,7 @@ function findManifestCandidates(rootPath) {
5447
5732
  return;
5448
5733
  }
5449
5734
  for (const entry of entries) {
5450
- const fullPath = path15__default.join(dir, entry.name);
5735
+ const fullPath = path14__default.join(dir, entry.name);
5451
5736
  if (entry.isDirectory()) {
5452
5737
  if (!SKIP_DIRS.has(entry.name)) walk(fullPath);
5453
5738
  } else if (entry.isFile()) {
@@ -5469,7 +5754,7 @@ function parseMdFrontmatter(content) {
5469
5754
  return parse(fmMatch[1]);
5470
5755
  }
5471
5756
  function validateManifests(rootPath) {
5472
- const absRoot = path15__default.resolve(rootPath);
5757
+ const absRoot = path14__default.resolve(rootPath);
5473
5758
  if (!fs10__default.existsSync(absRoot)) {
5474
5759
  logErr(`Path does not exist: ${absRoot}`);
5475
5760
  return { total: 0, errors: 1, warnings: 0 };
@@ -5490,14 +5775,14 @@ function validateManifests(rootPath) {
5490
5775
  try {
5491
5776
  parsed = c.filePath.endsWith(".json") ? JSON.parse(content) : parse(content);
5492
5777
  } catch (e) {
5493
- const relPath2 = path15__default.relative(absRoot, c.filePath);
5778
+ const relPath2 = path14__default.relative(absRoot, c.filePath);
5494
5779
  logErr(`${relPath2} \u2014 parse error: ${e instanceof Error ? e.message : String(e)}`);
5495
5780
  errors++;
5496
5781
  continue;
5497
5782
  }
5498
5783
  }
5499
5784
  const provider = registry.getProvider(c.kind);
5500
- const relPath = path15__default.relative(absRoot, c.filePath);
5785
+ const relPath = path14__default.relative(absRoot, c.filePath);
5501
5786
  if (!provider) {
5502
5787
  logWarn(`${relPath} [${c.kind}] \u2014 kind "${c.kind}" is not registered, skipping validation`);
5503
5788
  warnings++;
@@ -5519,20 +5804,20 @@ function collectAssetVersions() {
5519
5804
  if (!fs10__default.existsSync(AI_RESOURCES)) return assets;
5520
5805
  const domains = fs10__default.readdirSync(AI_RESOURCES, { withFileTypes: true }).filter((d) => d.isDirectory() && !EXCLUDED_DOMAINS.has(d.name));
5521
5806
  for (const d of domains) {
5522
- const domainDir = path15__default.join(AI_RESOURCES, d.name);
5523
- const skillsDir = path15__default.join(domainDir, "skills");
5807
+ const domainDir = path14__default.join(AI_RESOURCES, d.name);
5808
+ const skillsDir = path14__default.join(domainDir, "skills");
5524
5809
  if (fs10__default.existsSync(skillsDir)) {
5525
5810
  collectSkillVersions(skillsDir, d.name, assets);
5526
5811
  }
5527
- const agentsDir = path15__default.join(domainDir, "agents");
5812
+ const agentsDir = path14__default.join(domainDir, "agents");
5528
5813
  if (fs10__default.existsSync(agentsDir)) {
5529
5814
  collectAgentVersions(agentsDir, d.name, assets);
5530
5815
  }
5531
- const flowsDir = path15__default.join(domainDir, "flows");
5816
+ const flowsDir = path14__default.join(domainDir, "flows");
5532
5817
  if (fs10__default.existsSync(flowsDir)) {
5533
5818
  for (const f of fs10__default.readdirSync(flowsDir)) {
5534
5819
  if (!f.endsWith(".flow.yaml")) continue;
5535
- const fp = path15__default.join(flowsDir, f);
5820
+ const fp = path14__default.join(flowsDir, f);
5536
5821
  const content = fs10__default.readFileSync(fp, "utf-8");
5537
5822
  const parsed = parse(content);
5538
5823
  assets.push({
@@ -5544,11 +5829,11 @@ function collectAssetVersions() {
5544
5829
  });
5545
5830
  }
5546
5831
  }
5547
- const promptsDir = path15__default.join(domainDir, "prompts");
5832
+ const promptsDir = path14__default.join(domainDir, "prompts");
5548
5833
  if (fs10__default.existsSync(promptsDir)) {
5549
5834
  for (const f of fs10__default.readdirSync(promptsDir)) {
5550
5835
  if (!f.endsWith(".prompt.md")) continue;
5551
- const fp = path15__default.join(promptsDir, f);
5836
+ const fp = path14__default.join(promptsDir, f);
5552
5837
  const content = fs10__default.readFileSync(fp, "utf-8");
5553
5838
  const fm = parseSkillFrontmatter(content);
5554
5839
  assets.push({
@@ -5566,8 +5851,8 @@ function collectAssetVersions() {
5566
5851
  function collectSkillVersions(dir, domain, out) {
5567
5852
  for (const entry of fs10__default.readdirSync(dir, { withFileTypes: true })) {
5568
5853
  if (!entry.isDirectory()) continue;
5569
- const full = path15__default.join(dir, entry.name);
5570
- const skillMd = path15__default.join(full, "SKILL.md");
5854
+ const full = path14__default.join(dir, entry.name);
5855
+ const skillMd = path14__default.join(full, "SKILL.md");
5571
5856
  if (fs10__default.existsSync(skillMd)) {
5572
5857
  const content = fs10__default.readFileSync(skillMd, "utf-8");
5573
5858
  const fm = parseSkillFrontmatter(content);
@@ -5586,7 +5871,7 @@ function collectSkillVersions(dir, domain, out) {
5586
5871
  function collectAgentVersions(dir, domain, out) {
5587
5872
  for (const entry of fs10__default.readdirSync(dir, { withFileTypes: true })) {
5588
5873
  if (!entry.isDirectory()) continue;
5589
- const agentYaml = path15__default.join(dir, entry.name, "agent.yaml");
5874
+ const agentYaml = path14__default.join(dir, entry.name, "agent.yaml");
5590
5875
  if (!fs10__default.existsSync(agentYaml)) continue;
5591
5876
  const content = fs10__default.readFileSync(agentYaml, "utf-8");
5592
5877
  const parsed = parse(content);
@@ -5617,7 +5902,7 @@ function makeValidateCommand() {
5617
5902
  "Validate asset manifests, versions, and changelogs"
5618
5903
  );
5619
5904
  cmd.argument("[path]", "Path to asset repo or directory to validate", ".").action((targetPath) => {
5620
- const absPath = path15__default.resolve(targetPath);
5905
+ const absPath = path14__default.resolve(targetPath);
5621
5906
  logInfo(`Validating manifests in ${absPath}`);
5622
5907
  const { total, errors } = validateManifests(absPath);
5623
5908
  console.log();
@@ -5638,7 +5923,7 @@ function makeValidateCommand() {
5638
5923
  encoding: "utf-8"
5639
5924
  });
5640
5925
  const changedFiles = new Set(
5641
- diffOutput.trim().split("\n").filter(Boolean).map((f) => path15__default.resolve(AI_RESOURCES, f))
5926
+ diffOutput.trim().split("\n").filter(Boolean).map((f) => path14__default.resolve(AI_RESOURCES, f))
5642
5927
  );
5643
5928
  assets = assets.filter((a) => changedFiles.has(a.filePath));
5644
5929
  } catch {
@@ -5660,7 +5945,7 @@ function makeValidateCommand() {
5660
5945
  if (opts.changedOnly) {
5661
5946
  for (const a of assets) {
5662
5947
  if (!a.version) continue;
5663
- const relPath = path15__default.relative(AI_RESOURCES, a.filePath);
5948
+ const relPath = path14__default.relative(AI_RESOURCES, a.filePath);
5664
5949
  try {
5665
5950
  const headContent = execSync(`git show HEAD:${relPath}`, {
5666
5951
  cwd: AI_RESOURCES,
@@ -5740,7 +6025,7 @@ function makeValidateCommand() {
5740
6025
  let errors = 0;
5741
6026
  for (const domain of modifiedDomains) {
5742
6027
  const changelogModified = modifiedFiles.some(
5743
- (f) => f === `${domain}/CHANGELOG.md` || f === path15__default.join(domain, "CHANGELOG.md")
6028
+ (f) => f === `${domain}/CHANGELOG.md` || f === path14__default.join(domain, "CHANGELOG.md")
5744
6029
  );
5745
6030
  if (changelogModified) {
5746
6031
  logOk(`${domain}/CHANGELOG.md updated`);
@@ -5822,7 +6107,7 @@ function makeVerifyCommand() {
5822
6107
  }
5823
6108
  function makeWhyCommand() {
5824
6109
  return new Command("why").description("Show why an asset is installed (dependency chain)").argument("<ref>", "Asset reference (kind:name)").option("--project-dir <path>", "Project directory", process.cwd()).action((ref, opts) => {
5825
- const am2 = new AssetManager({ projectDir: path15__default.resolve(opts.projectDir) });
6110
+ const am2 = new AssetManager({ projectDir: path14__default.resolve(opts.projectDir) });
5826
6111
  const chain = am2.why(ref);
5827
6112
  if (chain.length === 0) {
5828
6113
  logErr(`${ref} not found in lock file. Run \`skaile install\` first.`);
@@ -5843,7 +6128,7 @@ function makeWhyCommand() {
5843
6128
  var _defaultFormatHelp = Help.prototype.formatHelp;
5844
6129
  var pkg = JSON.parse(
5845
6130
  readFileSync(
5846
- path15__default.resolve(path15__default.dirname(fileURLToPath(import.meta.url)), "../../package.json"),
6131
+ path14__default.resolve(path14__default.dirname(fileURLToPath(import.meta.url)), "../../package.json"),
5847
6132
  "utf-8"
5848
6133
  )
5849
6134
  );
@@ -5891,11 +6176,18 @@ Execution:
5891
6176
  resume Resume last session
5892
6177
  serve [--compile-test] Start WebSocket agent server
5893
6178
  mcp-server Start workspace MCP server (for .claude/mcp.json)
5894
- plugin install [--driver all] Install workspace plugin (claude-code | omp | codex)
5895
- plugin uninstall [--driver all] Uninstall workspace plugin
5896
- plugin enable Enable plugin (claude-code only)
5897
- plugin disable Disable plugin (claude-code only)
5898
- plugin status Show install / enable state across backends
6179
+ integration install [--driver all] Install agent integration (claude-code | omp | codex)
6180
+ integration uninstall [--driver all] Uninstall agent integration
6181
+ integration enable Enable integration (claude-code only)
6182
+ integration disable Disable integration (claude-code only)
6183
+ integration status Show install / enable state across backends
6184
+ plugin install <spec> Add a registry plugin to skaile.yaml + reconcile
6185
+ plugin remove <name> Remove a registry plugin from skaile.yaml
6186
+ plugin list List declared plugins + the targets they contribute
6187
+ deploy up [--target] [--detach] Stand the workspace up on a deploy target
6188
+ deploy down Tear down the active deploy
6189
+ deploy status Show the active deploy's state + ws URL
6190
+ deploy logs [--follow] Stream logs from the active deploy
5899
6191
  debug tools|connectors|mcp|config|state Inspect running container state
5900
6192
  connect <url> Interactive WebSocket REPL
5901
6193
  logs [--follow] [--filter] Tail skaile container logs
@@ -5947,136 +6239,130 @@ Advanced:
5947
6239
  `;
5948
6240
  }
5949
6241
  });
5950
- program.command("init [project-dir]").description("Initialize a project directory (defaults to current directory)").option(
5951
- "--backend <name>",
5952
- "Coding-agent backend (claude-code | omp | codex)",
5953
- "claude-code"
5954
- ).option("--no-git", "Skip git init and .gitignore").action(
5955
- async (projectDir, opts) => {
5956
- const { execSync: execSync3 } = await import('child_process');
5957
- const { existsSync: existsSync12, mkdirSync: mkdirSync3, readFileSync: readFileSync5, writeFileSync: writeFileSync2 } = await import('fs');
5958
- const { stringify } = await import('yaml');
5959
- const { DRIVER_TARGETS, SUPPORTED_DRIVER_TARGETS: SUPPORTED_DRIVER_TARGETS2 } = await import('../core/index.js');
5960
- const backend = opts.backend;
5961
- if (!SUPPORTED_DRIVER_TARGETS2.includes(backend)) {
5962
- logErr(
5963
- `Unknown backend "${opts.backend}". Supported: ${SUPPORTED_DRIVER_TARGETS2.join(", ")}`
5964
- );
5965
- process.exitCode = 1;
5966
- return;
5967
- }
5968
- const resolved = path15__default.resolve(projectDir ?? ".");
5969
- const projectName = path15__default.basename(resolved);
5970
- const created = [];
5971
- if (!existsSync12(resolved)) {
5972
- mkdirSync3(resolved, { recursive: true });
5973
- created.push(".");
5974
- }
5975
- const skaileDir = path15__default.join(resolved, ".skaile");
5976
- if (!existsSync12(skaileDir)) {
5977
- mkdirSync3(path15__default.join(skaileDir, "sessions"), { recursive: true });
5978
- created.push(".skaile/");
5979
- }
5980
- const settingsPath = path15__default.join(skaileDir, "settings.json");
5981
- if (!existsSync12(settingsPath)) {
5982
- writeFileSync2(settingsPath, "{}\n");
5983
- created.push(".skaile/settings.json");
5984
- }
5985
- const wsConfigPath = path15__default.join(resolved, "skaile.yaml");
5986
- if (!existsSync12(wsConfigPath)) {
5987
- writeFileSync2(
5988
- wsConfigPath,
5989
- stringify({
5990
- name: projectName,
5991
- description: `${projectName} AI skill dependencies`,
5992
- "agent-config": {
5993
- default: {
5994
- agent: backend,
5995
- provider: "anthropic",
5996
- model: "claude-sonnet-4-6",
5997
- driver: "claude-sdk",
5998
- max_turns: 200
5999
- }
6000
- },
6001
- ai_resources: []
6002
- })
6003
- );
6004
- created.push("skaile.yaml");
6005
- }
6006
- for (const dir of new Set(Object.values(DRIVER_TARGETS[backend].local))) {
6007
- const full = path15__default.join(resolved, dir);
6008
- if (!existsSync12(full)) {
6009
- mkdirSync3(full, { recursive: true });
6010
- created.push(`${dir}/`);
6011
- }
6012
- }
6013
- if (opts.git) {
6014
- const gitignorePath = path15__default.join(resolved, ".gitignore");
6015
- const entries = ["node_modules/", ".skaile/sessions/", "*.log", ".env", ".env.local"];
6016
- const existing = existsSync12(gitignorePath) ? readFileSync5(gitignorePath, "utf-8") : "";
6017
- const have = new Set(existing.split("\n").map((l) => l.trim()));
6018
- const append = entries.filter((e) => !have.has(e));
6019
- if (append.length > 0) {
6020
- const prefix = existing && !existing.endsWith("\n") ? "\n" : "";
6021
- writeFileSync2(gitignorePath, existing + prefix + `${append.join("\n")}
6242
+ program.command("init [project-dir]").description("Initialize a project directory (defaults to current directory)").option("--backend <name>", "Coding-agent backend (claude-code | omp | codex)", "claude-code").option("--no-git", "Skip git init and .gitignore").action(async (projectDir, opts) => {
6243
+ const { execSync: execSync3 } = await import('child_process');
6244
+ const { existsSync: existsSync12, mkdirSync: mkdirSync3, readFileSync: readFileSync5, writeFileSync: writeFileSync2 } = await import('fs');
6245
+ const { stringify } = await import('yaml');
6246
+ const { DRIVER_TARGETS, SUPPORTED_DRIVER_TARGETS: SUPPORTED_DRIVER_TARGETS2 } = await import('../core/index.js');
6247
+ const backend = opts.backend;
6248
+ if (!SUPPORTED_DRIVER_TARGETS2.includes(backend)) {
6249
+ logErr(
6250
+ `Unknown backend "${opts.backend}". Supported: ${SUPPORTED_DRIVER_TARGETS2.join(", ")}`
6251
+ );
6252
+ process.exitCode = 1;
6253
+ return;
6254
+ }
6255
+ const resolved = path14__default.resolve(projectDir ?? ".");
6256
+ const projectName = path14__default.basename(resolved);
6257
+ const created = [];
6258
+ if (!existsSync12(resolved)) {
6259
+ mkdirSync3(resolved, { recursive: true });
6260
+ created.push(".");
6261
+ }
6262
+ const skaileDir = path14__default.join(resolved, ".skaile");
6263
+ if (!existsSync12(skaileDir)) {
6264
+ mkdirSync3(path14__default.join(skaileDir, "sessions"), { recursive: true });
6265
+ created.push(".skaile/");
6266
+ }
6267
+ const settingsPath = path14__default.join(skaileDir, "settings.json");
6268
+ if (!existsSync12(settingsPath)) {
6269
+ writeFileSync2(settingsPath, "{}\n");
6270
+ created.push(".skaile/settings.json");
6271
+ }
6272
+ const wsConfigPath = path14__default.join(resolved, "skaile.yaml");
6273
+ if (!existsSync12(wsConfigPath)) {
6274
+ writeFileSync2(
6275
+ wsConfigPath,
6276
+ stringify({
6277
+ name: projectName,
6278
+ description: `${projectName} AI skill dependencies`,
6279
+ "agent-config": {
6280
+ default: {
6281
+ agent: backend,
6282
+ provider: "anthropic",
6283
+ model: "claude-sonnet-4-6",
6284
+ driver: "claude-sdk",
6285
+ max_turns: 200
6286
+ }
6287
+ },
6288
+ ai_resources: []
6289
+ })
6290
+ );
6291
+ created.push("skaile.yaml");
6292
+ }
6293
+ for (const dir of new Set(Object.values(DRIVER_TARGETS[backend].local))) {
6294
+ const full = path14__default.join(resolved, dir);
6295
+ if (!existsSync12(full)) {
6296
+ mkdirSync3(full, { recursive: true });
6297
+ created.push(`${dir}/`);
6298
+ }
6299
+ }
6300
+ if (opts.git) {
6301
+ const gitignorePath = path14__default.join(resolved, ".gitignore");
6302
+ const entries = ["node_modules/", ".skaile/sessions/", "*.log", ".env", ".env.local"];
6303
+ const existing = existsSync12(gitignorePath) ? readFileSync5(gitignorePath, "utf-8") : "";
6304
+ const have = new Set(existing.split("\n").map((l) => l.trim()));
6305
+ const append = entries.filter((e) => !have.has(e));
6306
+ if (append.length > 0) {
6307
+ const prefix = existing && !existing.endsWith("\n") ? "\n" : "";
6308
+ writeFileSync2(gitignorePath, existing + prefix + `${append.join("\n")}
6022
6309
  `);
6023
- if (!existing) created.push(".gitignore");
6024
- }
6025
- if (!existsSync12(path15__default.join(resolved, ".git"))) {
6026
- try {
6027
- execSync3("git init", { cwd: resolved, stdio: "pipe" });
6028
- created.push(".git/");
6029
- } catch (err) {
6030
- const msg = err instanceof Error ? err.message : String(err);
6031
- console.log(` ${S.dim(`\u26A0 git init failed: ${msg}`)}`);
6032
- }
6033
- }
6310
+ if (!existing) created.push(".gitignore");
6034
6311
  }
6035
- try {
6036
- const fs11 = await import('fs');
6037
- const { userConfigPath, saveConfig, getConfigDefaults } = await import('../library/index.js');
6038
- const userCfgPath = userConfigPath();
6039
- if (!fs11.existsSync(userCfgPath)) {
6040
- const defaults = getConfigDefaults();
6041
- saveConfig(userCfgPath, {
6042
- catalog: { url: defaults.catalog.url, cache_ttl: defaults.catalog.cache_ttl }
6043
- });
6044
- console.log(` ${S.dim(`\u2713 wrote default user config at ${userCfgPath}`)}`);
6312
+ if (!existsSync12(path14__default.join(resolved, ".git"))) {
6313
+ try {
6314
+ execSync3("git init", { cwd: resolved, stdio: "pipe" });
6315
+ created.push(".git/");
6316
+ } catch (err) {
6317
+ const msg = err instanceof Error ? err.message : String(err);
6318
+ console.log(` ${S.dim(`\u26A0 git init failed: ${msg}`)}`);
6045
6319
  }
6046
- } catch (err) {
6047
- console.log(
6048
- ` ${S.dim(`\u26A0 could not bootstrap user config: ${err instanceof Error ? err.message : String(err)}`)}`
6049
- );
6050
6320
  }
6051
- try {
6052
- const { ensureSourcesCloned } = await import('../ensure-sources-IDVQ77NJ.js');
6053
- const hydrate = ensureSourcesCloned(resolved, { quiet: true });
6054
- for (const n of hydrate.cloned) created.push(`~/.skaile/sources/${n}/`);
6055
- if (hydrate.failed.length > 0) {
6056
- logErr(`Failed to clone source(s): ${hydrate.failed.join(", ")}`);
6057
- }
6058
- } catch (err) {
6059
- const msg = err instanceof Error ? err.message : String(err);
6060
- console.log(` ${S.dim(`\u26A0 source hydration skipped: ${msg}`)}`);
6321
+ }
6322
+ try {
6323
+ const fs11 = await import('fs');
6324
+ const { userConfigPath, saveConfig, getConfigDefaults } = await import('../library/index.js');
6325
+ const userCfgPath = userConfigPath();
6326
+ if (!fs11.existsSync(userCfgPath)) {
6327
+ const defaults = getConfigDefaults();
6328
+ saveConfig(userCfgPath, {
6329
+ catalog: { url: defaults.catalog.url, cache_ttl: defaults.catalog.cache_ttl }
6330
+ });
6331
+ console.log(` ${S.dim(`\u2713 wrote default user config at ${userCfgPath}`)}`);
6061
6332
  }
6062
- for (const c of created) console.log(` ${S.dim(`+ ${c}`)}`);
6063
- logOk(`Initialized project at ${S.heading(resolved)}`);
6064
- console.log();
6065
- console.log(S.heading(" Next steps:"));
6066
- const isCurrentDir = resolved === path15__default.resolve(".");
6067
- let step = 1;
6068
- if (!isCurrentDir) {
6069
- console.log(` ${S.dim(`${step}.`)} ${S.cmd(`cd ${projectDir}`)}`);
6070
- step++;
6071
- }
6072
- console.log(` ${S.dim(`${step}.`)} Edit ${S.cmd("skaile.yaml")} to add dependencies`);
6333
+ } catch (err) {
6334
+ console.log(
6335
+ ` ${S.dim(`\u26A0 could not bootstrap user config: ${err instanceof Error ? err.message : String(err)}`)}`
6336
+ );
6337
+ }
6338
+ try {
6339
+ const { ensureSourcesCloned } = await import('../ensure-sources-COGVKY44.js');
6340
+ const hydrate = ensureSourcesCloned(resolved, { quiet: true });
6341
+ for (const n of hydrate.cloned) created.push(`~/.skaile/sources/${n}/`);
6342
+ if (hydrate.failed.length > 0) {
6343
+ logErr(`Failed to clone source(s): ${hydrate.failed.join(", ")}`);
6344
+ }
6345
+ } catch (err) {
6346
+ const msg = err instanceof Error ? err.message : String(err);
6347
+ console.log(` ${S.dim(`\u26A0 source hydration skipped: ${msg}`)}`);
6348
+ }
6349
+ for (const c of created) console.log(` ${S.dim(`+ ${c}`)}`);
6350
+ logOk(`Initialized project at ${S.heading(resolved)}`);
6351
+ console.log();
6352
+ console.log(S.heading(" Next steps:"));
6353
+ const isCurrentDir = resolved === path14__default.resolve(".");
6354
+ let step = 1;
6355
+ if (!isCurrentDir) {
6356
+ console.log(` ${S.dim(`${step}.`)} ${S.cmd(`cd ${projectDir}`)}`);
6073
6357
  step++;
6074
- console.log(` ${S.dim(`${step}.`)} ${S.cmd("skaile install")}`);
6075
- console.log();
6076
6358
  }
6077
- );
6359
+ console.log(` ${S.dim(`${step}.`)} Edit ${S.cmd("skaile.yaml")} to add dependencies`);
6360
+ step++;
6361
+ console.log(` ${S.dim(`${step}.`)} ${S.cmd("skaile install")}`);
6362
+ console.log();
6363
+ });
6078
6364
  program.command("setup").description("Interactive provider setup wizard").action(async () => {
6079
- const { cmdSetup } = await import('../setup-AIOLUTKV.js');
6365
+ const { cmdSetup } = await import('../setup-ACMP3QZC.js');
6080
6366
  await cmdSetup([], { projectDir: process.cwd() });
6081
6367
  });
6082
6368
  program.addCommand(makeInstallCommand());
@@ -6105,7 +6391,9 @@ program.addCommand(makeReplCommand());
6105
6391
  program.addCommand(makeResumeCommand());
6106
6392
  program.addCommand(makeServeCommand());
6107
6393
  program.addCommand(makeMcpServerCommand());
6394
+ program.addCommand(makeIntegrationCommand());
6108
6395
  program.addCommand(makePluginCommand());
6396
+ program.addCommand(makeDeployCommand());
6109
6397
  program.addCommand(makeDebugCommand());
6110
6398
  program.addCommand(makeConnectCommand());
6111
6399
  program.addCommand(makeLogsCommand());