@skaile/workspaces 2.9.0 → 3.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +14 -0
- package/README.md +17 -6
- package/dist/{asset-feeds-EO2QDJ4C.js → asset-feeds-XKPJZ6QT.js} +4 -4
- package/dist/{asset-feeds-EO2QDJ4C.js.map → asset-feeds-XKPJZ6QT.js.map} +1 -1
- package/dist/asset-manager/index.js +1 -1
- package/dist/bridge/drivers/claude-sdk.js +2 -2
- package/dist/bridge/drivers/codex.js +2 -2
- package/dist/bridge/drivers/continue.js +2 -2
- package/dist/bridge/drivers/echo.js +1 -1
- package/dist/bridge/drivers/gemini.js +4 -4
- package/dist/bridge/drivers/goose.js +2 -2
- package/dist/bridge/drivers/omp.js +1 -1
- package/dist/bridge/drivers/opencode.js +2 -2
- package/dist/bridge/drivers/qwen.js +4 -4
- package/dist/bridge/index.js +3 -3
- package/dist/bridge/src/models.d.ts +59 -0
- package/dist/bridge/src/models.d.ts.map +1 -1
- package/dist/{chunk-INHE5U74.js → chunk-5QGMEPUX.js} +8 -12
- package/dist/chunk-5QGMEPUX.js.map +1 -0
- package/dist/{chunk-TU7JDHKS.js → chunk-7HXS7WZF.js} +2 -2
- package/dist/{chunk-TU7JDHKS.js.map → chunk-7HXS7WZF.js.map} +1 -1
- package/dist/{chunk-OHLKWUO3.js → chunk-7KFN2EPR.js} +12 -4
- package/dist/chunk-7KFN2EPR.js.map +1 -0
- package/dist/{chunk-L3TS7ZO4.js → chunk-BJDACPWZ.js} +3 -3
- package/dist/{chunk-L3TS7ZO4.js.map → chunk-BJDACPWZ.js.map} +1 -1
- package/dist/{chunk-AFUOORJE.js → chunk-EH7BCJF4.js} +6 -6
- package/dist/{chunk-AFUOORJE.js.map → chunk-EH7BCJF4.js.map} +1 -1
- package/dist/{chunk-AGFAOSCZ.js → chunk-F5VREBV2.js} +8 -5
- package/dist/chunk-F5VREBV2.js.map +1 -0
- package/dist/{chunk-5LA4XI4Y.js → chunk-JQMULHO6.js} +24 -12
- package/dist/chunk-JQMULHO6.js.map +1 -0
- package/dist/{chunk-ZR2X4SIG.js → chunk-KXWUCKP5.js} +5 -5
- package/dist/{chunk-ZR2X4SIG.js.map → chunk-KXWUCKP5.js.map} +1 -1
- package/dist/{chunk-ZXJKWA44.js → chunk-N4GFUWWC.js} +3 -3
- package/dist/{chunk-ZXJKWA44.js.map → chunk-N4GFUWWC.js.map} +1 -1
- package/dist/{chunk-UTHMTZEH.js → chunk-NMKTM55X.js} +2 -2
- package/dist/{chunk-UTHMTZEH.js.map → chunk-NMKTM55X.js.map} +1 -1
- package/dist/{chunk-QVFCDSRH.js → chunk-P2J3MLTW.js} +3 -3
- package/dist/{chunk-QVFCDSRH.js.map → chunk-P2J3MLTW.js.map} +1 -1
- package/dist/{chunk-VNIKF66R.js → chunk-P5W6JVD4.js} +4 -4
- package/dist/{chunk-VNIKF66R.js.map → chunk-P5W6JVD4.js.map} +1 -1
- package/dist/{chunk-4PSDPZUG.js → chunk-Q6O53D5Q.js} +2 -2
- package/dist/{chunk-4PSDPZUG.js.map → chunk-Q6O53D5Q.js.map} +1 -1
- package/dist/{chunk-YFAED6OB.js → chunk-QGDQHNYC.js} +4 -4
- package/dist/{chunk-YFAED6OB.js.map → chunk-QGDQHNYC.js.map} +1 -1
- package/dist/{chunk-UAIR3K6X.js → chunk-S5FV6ISY.js} +8 -5
- package/dist/chunk-S5FV6ISY.js.map +1 -0
- package/dist/{chunk-HY3MBSNC.js → chunk-SR6NBBWT.js} +2 -2
- package/dist/{chunk-HY3MBSNC.js.map → chunk-SR6NBBWT.js.map} +1 -1
- package/dist/{chunk-BIKTLLLD.js → chunk-TXTCW7V6.js} +6 -6
- package/dist/{chunk-BIKTLLLD.js.map → chunk-TXTCW7V6.js.map} +1 -1
- package/dist/{chunk-BMQKMOQY.js → chunk-V34ZEXSE.js} +61 -3
- package/dist/chunk-V34ZEXSE.js.map +1 -0
- package/dist/{chunk-XXDQHZJY.js → chunk-WECBTWWZ.js} +3 -3
- package/dist/{chunk-XXDQHZJY.js.map → chunk-WECBTWWZ.js.map} +1 -1
- package/dist/{chunk-XHSS3YHV.js → chunk-XJECOBCO.js} +16 -7
- package/dist/chunk-XJECOBCO.js.map +1 -0
- package/dist/{chunk-E5VGAW4E.js → chunk-ZO7KL7GN.js} +230 -9
- package/dist/chunk-ZO7KL7GN.js.map +1 -0
- package/dist/cli/index.js +38 -38
- package/dist/connectors/index.js +11 -5
- package/dist/{ensure-sources-6ZOD45TO.js → ensure-sources-D6R57GAP.js} +4 -4
- package/dist/{ensure-sources-6ZOD45TO.js.map → ensure-sources-D6R57GAP.js.map} +1 -1
- package/dist/factory-assets/connectors/box.js +11 -5
- package/dist/factory-assets/connectors/deploy.js +11 -5
- package/dist/factory-assets/connectors/devserver.js +11 -5
- package/dist/factory-assets/connectors/flow/CONNECTOR.md +47 -6
- package/dist/factory-assets/connectors/flow/adapter.d.ts +5 -0
- package/dist/factory-assets/connectors/flow/adapter.d.ts.map +1 -1
- package/dist/factory-assets/connectors/flow/adapter.js +11 -5
- package/dist/factory-assets/connectors/flow/contract/flow.v2.schema.json +0 -6
- package/dist/factory-assets/connectors/flow/contract/normalize.d.ts.map +1 -1
- package/dist/factory-assets/connectors/flow/contract/schema.d.ts +0 -4
- package/dist/factory-assets/connectors/flow/contract/schema.d.ts.map +1 -1
- package/dist/factory-assets/connectors/flow/contract.js +2 -2
- package/dist/factory-assets/connectors/flow/engine/bindings.d.ts.map +1 -1
- package/dist/factory-assets/connectors/flow/engine/node-shape.d.ts +7 -1
- package/dist/factory-assets/connectors/flow/engine/node-shape.d.ts.map +1 -1
- package/dist/factory-assets/connectors/flow/engine/types.d.ts +12 -12
- package/dist/factory-assets/connectors/flow/engine/types.d.ts.map +1 -1
- package/dist/factory-assets/connectors/flow/engine.js +3 -3
- package/dist/factory-assets/connectors/flow/index.d.ts +1 -0
- package/dist/factory-assets/connectors/flow/index.d.ts.map +1 -1
- package/dist/factory-assets/connectors/flow/inline-sub-flow-host.d.ts +3 -0
- package/dist/factory-assets/connectors/flow/inline-sub-flow-host.d.ts.map +1 -1
- package/dist/factory-assets/connectors/flow/prompt-fragments.d.ts +14 -0
- package/dist/factory-assets/connectors/flow/prompt-fragments.d.ts.map +1 -1
- package/dist/factory-assets/connectors/flow/prompt-fragments.js +2 -2
- package/dist/factory-assets/connectors/flow/run-flow.d.ts.map +1 -1
- package/dist/factory-assets/connectors/flow/run-flow.js +12 -6
- package/dist/factory-assets/connectors/flow/subprompt-runner.d.ts +99 -0
- package/dist/factory-assets/connectors/flow/subprompt-runner.d.ts.map +1 -0
- package/dist/factory-assets/connectors/flow.js +11 -5
- package/dist/factory-assets/connectors/git.js +11 -5
- package/dist/factory-assets/connectors/gmail.js +11 -5
- package/dist/factory-assets/connectors/googledrive.js +11 -5
- package/dist/factory-assets/connectors/local.js +11 -5
- package/dist/factory-assets/connectors/mattermost.js +11 -5
- package/dist/factory-assets/connectors/memory.js +11 -5
- package/dist/factory-assets/connectors/minio.js +11 -5
- package/dist/factory-assets/connectors/postgres.js +11 -5
- package/dist/factory-assets/connectors/s3.js +11 -5
- package/dist/factory-assets/connectors/sharepoint.js +11 -5
- package/dist/factory-assets/connectors/sqlite.js +11 -5
- package/dist/factory-assets/connectors/static-server.js +11 -5
- package/dist/factory-assets/connectors/tunnel.js +11 -5
- package/dist/factory-assets/connectors/webdav.js +11 -5
- package/dist/factory-assets/connectors/xstate-store.js +11 -5
- package/dist/factory-assets/connectors/xstate.js +11 -5
- package/dist/{flows-7N5AUUIS.js → flows-LQSVM45J.js} +3 -3
- package/dist/{flows-7N5AUUIS.js.map → flows-LQSVM45J.js.map} +1 -1
- package/dist/{helpers-HWLCANAK.js → helpers-IS4MSEOQ.js} +4 -4
- package/dist/{helpers-HWLCANAK.js.map → helpers-IS4MSEOQ.js.map} +1 -1
- package/dist/{library-publish-GSAIZCO3.js → library-publish-QJACP6FW.js} +9 -9
- package/dist/{library-publish-GSAIZCO3.js.map → library-publish-QJACP6FW.js.map} +1 -1
- package/dist/{open-library-ZB2STYC6.js → open-library-3FMLAU3F.js} +8 -8
- package/dist/{open-library-ZB2STYC6.js.map → open-library-3FMLAU3F.js.map} +1 -1
- package/dist/{project-EJFCLSHS.js → project-KEAAGHSX.js} +5 -5
- package/dist/{project-EJFCLSHS.js.map → project-KEAAGHSX.js.map} +1 -1
- package/dist/runner/index.js +15 -15
- package/dist/runner/src/serve.d.ts.map +1 -1
- package/dist/sdk/asset-manager.js +1 -1
- package/dist/sdk/bridge.js +3 -3
- package/dist/sdk/flow.js +3 -3
- package/dist/sdk/index.js +15 -15
- package/dist/sdk/runner.js +15 -15
- package/dist/{setup-RHWARBBB.js → setup-VX6EPF5P.js} +5 -5
- package/dist/{setup-RHWARBBB.js.map → setup-VX6EPF5P.js.map} +1 -1
- package/dist/{source-ILV6ZKWM.js → source-45XHQSBF.js} +9 -9
- package/dist/{source-ILV6ZKWM.js.map → source-45XHQSBF.js.map} +1 -1
- package/dist/{source-manifest-publish-QE2IFDRW.js → source-manifest-publish-M34SKD46.js} +10 -10
- package/dist/{source-manifest-publish-QE2IFDRW.js.map → source-manifest-publish-M34SKD46.js.map} +1 -1
- package/dist/tui/index.js +15 -15
- package/dist/workspace-plugin/adapters/mcp.js +1 -1
- package/dist/workspace-plugin/adapters/omp.js +3 -3
- package/dist/workspace-plugin/index.js +1 -1
- package/package.json +1 -1
- package/dist/chunk-5LA4XI4Y.js.map +0 -1
- package/dist/chunk-AGFAOSCZ.js.map +0 -1
- package/dist/chunk-BMQKMOQY.js.map +0 -1
- package/dist/chunk-E5VGAW4E.js.map +0 -1
- package/dist/chunk-INHE5U74.js.map +0 -1
- package/dist/chunk-OHLKWUO3.js.map +0 -1
- package/dist/chunk-UAIR3K6X.js.map +0 -1
- package/dist/chunk-XHSS3YHV.js.map +0 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,19 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## 3.0.0
|
|
4
|
+
|
|
5
|
+
### Major Changes
|
|
6
|
+
|
|
7
|
+
- [#515](https://github.com/skaile-ai/workspaces/pull/515) [`ff160e9`](https://github.com/skaile-ai/workspaces/commit/ff160e92dc97fce2cfdaae5c75b9add9fc8553dc) Thanks [@peteralbert](https://github.com/peteralbert)! - Remove the inert `control.subagent` and `defaults.subagentMode` fields from the Flow v2 contract.
|
|
8
|
+
|
|
9
|
+
Both were carried through v1 normalization while it was open whether a later node kind would consume them; nothing ever read either. They meant "run this skill in a fresh conversation context" — which is what a `sub-flow` already does, not the single isolated model call a `subprompt` performs — so wiring them to `subprompt` would have silently changed what authored flows do.
|
|
10
|
+
|
|
11
|
+
**Breaking:** both keys are gone from the strict v2 schema, so a v2 document carrying either is now rejected with an authored path. Only the v1 normalizer ever produced them and it no longer does; a v1 document may still carry them and both are dropped. Dropping `subagent_mode` is explicit rather than a deleted key mapping, because `defaults.parameters` is an open passthrough bag — an unmapped key would have survived as `defaults.parameters.subagent_mode`, a rename rather than a removal.
|
|
12
|
+
|
|
13
|
+
### Minor Changes
|
|
14
|
+
|
|
15
|
+
- [#515](https://github.com/skaile-ai/workspaces/pull/515) [`ff160e9`](https://github.com/skaile-ai/workspaces/commit/ff160e92dc97fce2cfdaae5c75b9add9fc8553dc) Thanks [@peteralbert](https://github.com/peteralbert)! - Activate Flow v2 `subprompt` nodes — the last of the seven Flow v2 kinds. A subprompt is `function`-shaped for everything except how the work is performed and how its output provenance is classified: instead of `NodeExecutor`, it hands its interpolated instruction to a `SubpromptRunner`, whose production implementation (`SessionSubpromptRunner`) constructs a second, isolated `AgentDriver` instance per call — same backend, provider, resolved model, and credentials as the session driver, but no Skaile system prompt, no MCP servers, no connector capabilities, no access to the session conversation, and bounded to a single turn. It does retain the backend's own native tool surface rooted at the session workspace — isolation here is a separate conversation, not a sandbox. `run.model` (`"small" | "default" | "deep"`) resolves through a new pure `resolveModelTier` in `bridge/src/models.ts`: a host-configured override first, then `PROVIDER_MODEL_TIERS`, a new built-in per-provider table of direct provider-API ids (consulted only on the direct API, since a gateway transport renames them) whose every entry is pinned by test to also exist in `STATIC_MODELS`. `default` and an absent tier inherit the session model — the one id known to work for this deployment, already carrying whatever gateway translation the host configured; `small` and `deep` instead raise the new `ModelTierResolutionError` and fail the node, so an explicit request for a cheap or a strong model is never silently served by whichever model the session happened to start with. With no declared output contract the response is prose; with one declared, the response is additionally parsed as JSON and validated through the same `validateConsumedNodeOutput` path every kind uses — there is no corrective reprompt, so a parse or validation failure consumes `control.retries` like any ordinary failure. The reply is carried verbatim as the node's `summary` in both cases, since `fields` reaches a consumer only through an expression binding and `build_handoff` renders a predecessor's summary/artifacts/concerns but never its `fields`. `control.optional`, `control.retries`, and `control.timeoutSec` behave as they do for a `function` node, except that an optional subprompt whose retry budget is exhausted becomes `skipped` rather than `failed` — matching `sub-flow`, because only `complete` and `skipped` satisfy a hard `flow` edge, so leaving it `failed` would permanently block its dependents. A subprompt inside an inline `sub-flow` child reaches the same runner as one in the parent. A subprompt's output is classified `obtainedBy: "agent"` (fixing a provenance hole: a downstream `check` consuming it now always derives `"asserted"`, never `"verified"`). `raceWithTimeout` does not cancel the underlying driver call on timeout — a known, documented cost this change does not address.
|
|
16
|
+
|
|
3
17
|
## 2.9.0
|
|
4
18
|
|
|
5
19
|
### Minor Changes
|
package/README.md
CHANGED
|
@@ -105,11 +105,22 @@ Explicit legacy `type: skill` and exact `type: sub-flow` nodes normalize to
|
|
|
105
105
|
their executable v2 kinds; every other legacy kind remains an inert
|
|
106
106
|
compatibility placeholder with its IDs, parameters, assets, and dependency
|
|
107
107
|
semantics retained.
|
|
108
|
-
The runtime activates `agent`, `
|
|
108
|
+
The runtime activates all seven kinds: `agent`, `subprompt`, `function`,
|
|
109
|
+
`check`, `gate`, `router`, and `sub-flow`.
|
|
109
110
|
Interpolated agent instructions, resolved values, and origins reach the session
|
|
110
|
-
agent through `build_handoff(nodeId)`; function nodes run shell,
|
|
111
|
-
commands in the existing session workspace without a model
|
|
112
|
-
values exported as environment variables
|
|
111
|
+
agent through `build_handoff(nodeId)`; function and check nodes run shell,
|
|
112
|
+
Node, or Python commands in the existing session workspace without a model
|
|
113
|
+
turn, with resolved values exported as environment variables — a check's exit
|
|
114
|
+
status is a pass/fail verdict rather than a plain success/failure. Subprompt
|
|
115
|
+
nodes are `function`-shaped except for how the work runs: a second, isolated
|
|
116
|
+
`AgentDriver` instance per call, with no Skaile system prompt, no MCP servers, no connector capabilities, and no access to the session conversation, bounded to a single turn. It does retain the backend's own native tool surface (a coding backend keeps its file and shell tools, rooted at the session workspace) — isolation here means a separate conversation, not a sandbox, resolving its declared `run.model` tier via a pure
|
|
117
|
+
`resolveModelTier` against per-provider built-in tiers, failing the node
|
|
118
|
+
rather than substituting a model when a tier cannot be served. A declared output contract drives a JSON-response request and
|
|
119
|
+
response parsing through the same consumed-output validation every kind uses;
|
|
120
|
+
there is no corrective reprompt, so a parse or validation failure is an
|
|
121
|
+
ordinary node failure. A subprompt's output is classified agent-obtained, so a
|
|
122
|
+
downstream check always derives "asserted" provenance over it, never
|
|
123
|
+
"verified". Gate nodes
|
|
113
124
|
park immediately through the durable approval state, complete on approval, and
|
|
114
125
|
preserve rejection feedback for revision and a later approval re-request.
|
|
115
126
|
Router nodes evaluate ordered bounded expressions only after admission. The first
|
|
@@ -130,8 +141,8 @@ durable corrective call; deterministic functions fail directly. Unconsumed schem
|
|
|
130
141
|
remain prose-only.
|
|
131
142
|
Skills, connectors, mounts, MCP servers, and knowledge stay reusable
|
|
132
143
|
`run.assets` requirements, and shared refs are deduplicated in the dependency
|
|
133
|
-
graph.
|
|
134
|
-
`sub-flow
|
|
144
|
+
graph. All seven current kinds — `agent`, `subprompt`, `function`, `check`,
|
|
145
|
+
`gate`, `router`, and `sub-flow` — are active.
|
|
135
146
|
`FlowDefinition` is the strict authored-v2 type; parser results use the wider
|
|
136
147
|
`ParsedFlowDefinition` so unknown legacy edge kinds and their metadata can be
|
|
137
148
|
retained inertly without weakening authored validation.
|
|
@@ -65,7 +65,7 @@ async function libraryAssets() {
|
|
|
65
65
|
const domains = [];
|
|
66
66
|
try {
|
|
67
67
|
const [{ openLibraryManager }, { skaileHomeDir }, { getGlobalCacheDir }] = await Promise.all([
|
|
68
|
-
import('./open-library-
|
|
68
|
+
import('./open-library-3FMLAU3F.js'),
|
|
69
69
|
import('./library/index.js'),
|
|
70
70
|
import('./core/index.js')
|
|
71
71
|
]);
|
|
@@ -98,7 +98,7 @@ async function libraryAssets() {
|
|
|
98
98
|
async function storeAssets(projectDir) {
|
|
99
99
|
const notes = [];
|
|
100
100
|
try {
|
|
101
|
-
const { resolveCatalogSource } = await import('./open-library-
|
|
101
|
+
const { resolveCatalogSource } = await import('./open-library-3FMLAU3F.js');
|
|
102
102
|
const { source, close } = await resolveCatalogSource({ projectDir });
|
|
103
103
|
try {
|
|
104
104
|
const assets = await source.listAssets();
|
|
@@ -202,5 +202,5 @@ function dedupeBySlug(domains) {
|
|
|
202
202
|
}
|
|
203
203
|
|
|
204
204
|
export { gatherAssetFeeds };
|
|
205
|
-
//# sourceMappingURL=asset-feeds-
|
|
206
|
-
//# sourceMappingURL=asset-feeds-
|
|
205
|
+
//# sourceMappingURL=asset-feeds-XKPJZ6QT.js.map
|
|
206
|
+
//# sourceMappingURL=asset-feeds-XKPJZ6QT.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../cli/src/asset-feeds.ts"],"names":[],"mappings":"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","file":"asset-feeds-EO2QDJ4C.js","sourcesContent":["/**\n * asset-feeds.ts — gather installable assets from every feed the manage TUI\n * surfaces.\n *\n * Four feeds, normalized into `CatalogEntry`:\n * - **Project sources** — `skaile.yaml` `sources:` entries (scanned via\n * `AssetManager.search()`; the new `sources:` field is merged into the\n * legacy repositories map in `AssetManager.loadConfig`).\n * - **Local libraries** — user authoring places from `LocalIndex` (filesystem\n * scan of each library's `path`).\n * - **Factory assets** — the bundled first-party `factory-assets` tree\n * (`factoryAssetRoots()`), scanned from disk. Always present; no network.\n * - **Remote store** — the configured catalog source when `catalog.url` is\n * not `local`. Failures are non-fatal — they surface as notes.\n */\n\nimport { existsSync, readFileSync } from \"node:fs\";\nimport * as path from \"node:path\";\nimport {\n type AssetKind,\n type CatalogDomain,\n type CatalogEntry,\n factoryAssetRoots,\n parseFrontmatter,\n scanRepo,\n walkDir,\n} from \"@skaile/workspaces/core\";\nimport {\n assignDomain,\n buildDomainIndex,\n DOMAIN_MD_FILENAME,\n type DomainMd,\n parseDomainMd,\n} from \"@skaile/workspaces/discovery\";\n\n/** One non-fatal note returned to the caller for surfacing in the UI. */\nexport interface FeedNote {\n feed: \"sources\" | \"libraries\" | \"store\" | \"factory\";\n message: string;\n}\n\n/**\n * Which feed an asset came from. This is the top-level grouping axis in the\n * manage TUI (\"where is this skill coming from?\") and is intentionally distinct\n * from `publisher` (asset-intrinsic identity): the same publisher can legitimately\n * appear under more than one origin (e.g. a github repo you added as a `source`\n * that is also listed in the remote `store`).\n */\nexport type AssetOrigin = \"source\" | \"library\" | \"factory\" | \"store\";\n\n/** A catalog entry tagged with the feed it was gathered from. */\nexport interface OriginEntry {\n origin: AssetOrigin;\n entry: CatalogEntry;\n /**\n * Second-level grouping label for the manage tree. Defaults (when unset) to the\n * entry's `publisher`; the source feed sets it to the source's short repo name\n * so the Sources band groups by source — \"which repo did this come from\" — not\n * by the asset-intrinsic publisher.\n */\n group?: string;\n}\n\nexport interface AssetFeedResult {\n entries: OriginEntry[];\n /**\n * Display-only domain metadata, keyed (by the consumer) on `slug`. Populated\n * from the store's `catalog.listDomains` when the connected catalog source\n * exposes it; empty otherwise. The manage TUI joins `entry.domainSlug` → a\n * domain for grouping headers, descriptions, and relation badges.\n */\n domains: CatalogDomain[];\n notes: FeedNote[];\n}\n\n// ── Domain stamping (on-disk feeds) ──────────────────────────────────────────\n//\n// `scanRepo` (the source / library / factory scan path) does not read the\n// `DOMAIN.md` sidecars, so its entries arrive with no `domainSlug` and render\n// flat under their publisher band. We re-derive the grouping here from the\n// root's `DOMAIN.md` files (the same sidecars the remote store computes\n// server-side), and fall back to the repo/source name for any entry no domain\n// claims so it still groups instead of landing in the synthetic \"no domain\" pile.\n\n/** Repo-relative POSIX path (DOMAIN.md slugs are matched whole-segment, `/`-joined). */\nfunction toPosix(p: string): string {\n return p.split(path.sep).join(\"/\");\n}\n\n/** Parse every `DOMAIN.md` sidecar under `root` into a {@link DomainMd}. */\nasync function loadDomainMds(root: string): Promise<DomainMd[]> {\n const out: DomainMd[] = [];\n for await (const { path: filePath, name } of walkDir(root)) {\n if (name !== DOMAIN_MD_FILENAME) continue;\n try {\n const { data } = parseFrontmatter(readFileSync(filePath, \"utf8\"));\n out.push(parseDomainMd(toPosix(path.relative(root, filePath)), data));\n } catch {}\n }\n return out;\n}\n\n/**\n * Stamp `domainSlug` onto every entry scanned from `root` using the root's\n * `DOMAIN.md` sidecars. Returns the `CatalogDomain` registry for the real\n * domains, plus a synthetic fallback domain when any entry used the fallback.\n * Mutates `entries` in place (sets `entry.domainSlug`).\n *\n * `synthesizeFallback` (default true): entries no domain claims fall back to\n * `fallbackSlug` (the repo/source name). Pass `false` when the caller already\n * groups these entries one level up (e.g. the source feed groups by source\n * node) — unmatched entries then get no domain (`\"\"`) and hang directly under\n * that parent, instead of nesting under a same-named fallback domain.\n */\nasync function stampDomains(\n root: string,\n fallbackSlug: string,\n entries: CatalogEntry[],\n synthesizeFallback = true,\n): Promise<CatalogDomain[]> {\n const domainMds = await loadDomainMds(root);\n const assignables = entries.map((entry) => ({\n entry,\n ref: `${entry.kind}:${entry.name}`,\n relativePath: toPosix(path.relative(root, entry.source)),\n }));\n\n let usedFallback = false;\n for (const a of assignables) {\n const slug = assignDomain(a.relativePath, domainMds);\n if (slug) a.entry.domainSlug = slug;\n else if (synthesizeFallback) {\n a.entry.domainSlug = fallbackSlug;\n usedFallback = true;\n } else a.entry.domainSlug = \"\";\n }\n\n const { index } = buildDomainIndex(assignables, domainMds);\n const catalog: CatalogDomain[] = Object.values(index).map((d) => ({\n slug: d.slug,\n title: d.title,\n ...(d.description ? { description: d.description } : {}),\n ...(d.relation ? { relation: d.relation } : {}),\n ...(d.order !== undefined ? { order: d.order } : {}),\n ...(d.recommended[0] ? { recommendedRef: d.recommended[0] } : {}),\n }));\n if (usedFallback) catalog.push({ slug: fallbackSlug, title: fallbackSlug });\n return catalog;\n}\n\n/**\n * Pull assets from local libraries (the authoring places under\n * `~/.skaile/libraries/<name>/`, not the `~/.skaile/cache/sources/` cache). Each\n * library's `path` is scanned with `scanRepo` and grouped under the bare library\n * name (`group: <name>`) so the manage TUI shows a clean `<name>` band — no\n * `library:` prefix and no redundant same-named fallback domain (mirrors the\n * source feed).\n */\nasync function libraryAssets(): Promise<{\n entries: OriginEntry[];\n domains: CatalogDomain[];\n notes: FeedNote[];\n}> {\n const notes: FeedNote[] = [];\n const domains: CatalogDomain[] = [];\n try {\n const [{ openLibraryManager }, { skaileHomeDir }, { getGlobalCacheDir }] = await Promise.all([\n import(\"./open-library.ts\"),\n import(\"@skaile/workspaces/library\"),\n import(\"@skaile/workspaces/core\"),\n ]);\n const { manager, close } = await openLibraryManager();\n try {\n // Authoring libraries are the rows that are NOT source clones. index.db\n // rows predating the cache migration still carry the legacy\n // ~/.skaile/sources path, so exclude both roots.\n const newRoot = getGlobalCacheDir();\n const legacyRoot = path.join(skaileHomeDir(), \"sources\");\n const libs = (await manager.listLibraries()).filter(\n (l) => !l.path.startsWith(newRoot) && !l.path.startsWith(legacyRoot),\n );\n const entries: OriginEntry[] = [];\n for (const lib of libs) {\n if (!existsSync(lib.path)) continue;\n // Scan + group under the bare library name. `synthesizeFallback: false`\n // (as the source feed does) keeps domainless assets directly under the\n // library band instead of a redundant same-named fallback domain.\n const libEntries = [...(await scanRepo(lib.path, lib.name))];\n domains.push(...(await stampDomains(lib.path, lib.name, libEntries, false)));\n for (const entry of libEntries) entries.push({ origin: \"library\", entry, group: lib.name });\n }\n return { entries, domains, notes };\n } finally {\n close();\n }\n } catch (err) {\n notes.push({\n feed: \"libraries\",\n message: err instanceof Error ? err.message : String(err),\n });\n return { entries: [], domains, notes };\n }\n}\n\n/**\n * Pull a (best-effort) snapshot of the connected remote store catalog.\n *\n * - Returns no entries when the resolved catalog is local-only or the host\n * is unreachable (the failure becomes a note, not an exception).\n * - Maps `CatalogAsset` → `CatalogEntry`, carrying `publisher`, `repo`, and\n * `category` straight through and using `source = \"store://<id>\"`; per-file\n * `source` paths are not available for remote assets so the canonical ref is\n * a stable placeholder.\n */\nasync function storeAssets(projectDir: string): Promise<{\n entries: CatalogEntry[];\n domains: CatalogDomain[];\n notes: FeedNote[];\n}> {\n const notes: FeedNote[] = [];\n try {\n const { resolveCatalogSource } = await import(\"./open-library.ts\");\n const { source, close } = await resolveCatalogSource({ projectDir });\n try {\n const assets = await source.listAssets();\n const entries: CatalogEntry[] = assets.map((a) => ({\n name: a.name,\n kind: (a.kind as AssetKind) ?? \"skill\",\n description: a.description ?? \"\",\n source: `store://${a.id}`,\n publisher: a.publisher,\n repo: a.repo,\n domainSlug: a.domainSlug,\n category: a.category,\n version: a.version,\n requires: [],\n dependencies: [],\n }));\n // Domains are optional on the catalog source — only the store backend\n // (post Part 4 `catalog.listDomains`) exposes them. Duck-type the call so\n // older sources and the local catalog degrade to no domains, not an error.\n const domains = await loadDomains(source);\n return { entries, domains, notes };\n } finally {\n close();\n }\n } catch (err) {\n const msg = err instanceof Error ? err.message : String(err);\n // Local-only catalog throws a recognizable message — silence it; absence\n // is the user's choice, not an error.\n if (!/local/i.test(msg)) {\n notes.push({ feed: \"store\", message: msg });\n }\n return { entries: [], domains: [], notes };\n }\n}\n\n/** Optional `listDomains` capability — returns `[]` when the source lacks it. */\nasync function loadDomains(source: unknown): Promise<CatalogDomain[]> {\n const fn = (source as { listDomains?: () => Promise<CatalogDomain[]> }).listDomains;\n if (typeof fn !== \"function\") return [];\n const domains = await fn.call(source);\n return Array.isArray(domains) ? domains : [];\n}\n\n/** The slice of `AssetManager` the source feed needs (kept narrow for tests). */\ninterface AssetManagerLike {\n search: () => Promise<CatalogEntry[]>;\n searchRepoRoots: () => { repoName: string; root: string }[];\n}\n\n/**\n * Project-source feed: leans on `AssetManager.search()`, which now merges\n * `skaile.yaml`'s `sources:` field into the repositories map, then stamps\n * `DOMAIN.md`-derived domain grouping onto the scanned entries via\n * `searchRepoRoots()`.\n */\nasync function sourceAssets(\n am: AssetManagerLike,\n): Promise<{ entries: OriginEntry[]; domains: CatalogDomain[] }> {\n // The bundled factory tree is injected into the repositories map as an implicit\n // source, so `am.search()` returns it too. It has its own `factory` origin band,\n // so drop it here — otherwise the same first-party skills list twice under Sources.\n const factoryPrefixes = factoryAssetRoots().map((r) => (r.endsWith(path.sep) ? r : r + path.sep));\n const isFactoryPath = (p: string) =>\n factoryPrefixes.some((fp) => p === fp.slice(0, -1) || p.startsWith(fp));\n\n const all = (await am.search()).filter((e) => !isFactoryPath(e.source));\n const entries: OriginEntry[] = [];\n const domains: CatalogDomain[] = [];\n // Group each source's entries under the source node (its short repo name), not\n // the publisher: under Sources the navigational question is \"which repo did\n // this come from\". Each entry's `source` (absolute manifest path) lives under\n // exactly one declared root, so group + stamp by prefix. The cache slug is\n // URL-keyed `github.com/<org>/<repo>` — take the trailing segment.\n for (const { repoName, root } of am.searchRepoRoots()) {\n if (isFactoryPath(root)) continue;\n const prefix = root.endsWith(path.sep) ? root : root + path.sep;\n const owned = all.filter((e) => e.source === root || e.source.startsWith(prefix));\n if (owned.length === 0) continue;\n const sourceName = repoName.split(\"/\").pop() || repoName;\n // No synthetic fallback domain — the source node already groups these, so a\n // same-named fallback would just nest the source under itself.\n domains.push(...(await stampDomains(root, sourceName, owned, false)));\n for (const entry of owned) entries.push({ origin: \"source\", entry, group: sourceName });\n }\n return { entries, domains };\n}\n\n/**\n * Factory-asset feed: scan the bundled first-party `factory-assets` tree(s)\n * resolved by `factoryAssetRoots()` (the `SKAILE_FACTORY_ASSETS_DIR` override\n * layer ahead of the bundled tree). Local disk only, no network — the entries are\n * the built-in skills / connectors / bundles that ship with `@skaile/workspaces`.\n * `factoryAssetRoots()` already dedupes, so the env override pointing at the\n * bundled dir collapses to one root.\n */\nasync function factoryAssets(): Promise<{\n entries: CatalogEntry[];\n domains: CatalogDomain[];\n notes: FeedNote[];\n}> {\n const notes: FeedNote[] = [];\n const domains: CatalogDomain[] = [];\n try {\n const entries: CatalogEntry[] = [];\n for (const root of factoryAssetRoots()) {\n const rootEntries = [...(await scanRepo(root, \"skaile-factory\"))];\n domains.push(...(await stampDomains(root, \"skaile-factory\", rootEntries)));\n entries.push(...rootEntries);\n }\n return { entries, domains, notes };\n } catch (err) {\n notes.push({\n feed: \"factory\",\n message: err instanceof Error ? err.message : String(err),\n });\n return { entries: [], domains, notes };\n }\n}\n\n/** Tag a flat entry list with a single origin. */\nfunction tag(origin: AssetOrigin, entries: CatalogEntry[]): OriginEntry[] {\n return entries.map((entry) => ({ origin, entry }));\n}\n\n/**\n * Run all feeds and return a single normalized result.\n *\n * Feeds run in parallel where possible — the store fetch is the slow one\n * (one HTTP call) and is fired alongside the local library walk. The factory\n * scan is local disk only, so it runs inline.\n */\nexport async function gatherAssetFeeds(\n am: AssetManagerLike,\n projectDir: string,\n): Promise<AssetFeedResult> {\n const [libs, store] = await Promise.all([libraryAssets(), storeAssets(projectDir)]);\n const factory = await factoryAssets();\n const src = await sourceAssets(am);\n return {\n entries: [\n ...src.entries,\n ...libs.entries,\n ...tag(\"factory\", factory.entries),\n ...tag(\"store\", store.entries),\n ],\n // Store domains first (server-curated), then the on-disk feeds; dedupe by\n // slug, first-wins, so a store-served domain shadows a same-slug local one.\n domains: dedupeBySlug([...store.domains, ...src.domains, ...libs.domains, ...factory.domains]),\n notes: [...libs.notes, ...store.notes, ...factory.notes],\n };\n}\n\n/** First-wins dedupe of a domain list by `slug`. */\nfunction dedupeBySlug(domains: CatalogDomain[]): CatalogDomain[] {\n const seen = new Set<string>();\n const out: CatalogDomain[] = [];\n for (const d of domains) {\n if (seen.has(d.slug)) continue;\n seen.add(d.slug);\n out.push(d);\n }\n return out;\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../cli/src/asset-feeds.ts"],"names":[],"mappings":"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","file":"asset-feeds-XKPJZ6QT.js","sourcesContent":["/**\n * asset-feeds.ts — gather installable assets from every feed the manage TUI\n * surfaces.\n *\n * Four feeds, normalized into `CatalogEntry`:\n * - **Project sources** — `skaile.yaml` `sources:` entries (scanned via\n * `AssetManager.search()`; the new `sources:` field is merged into the\n * legacy repositories map in `AssetManager.loadConfig`).\n * - **Local libraries** — user authoring places from `LocalIndex` (filesystem\n * scan of each library's `path`).\n * - **Factory assets** — the bundled first-party `factory-assets` tree\n * (`factoryAssetRoots()`), scanned from disk. Always present; no network.\n * - **Remote store** — the configured catalog source when `catalog.url` is\n * not `local`. Failures are non-fatal — they surface as notes.\n */\n\nimport { existsSync, readFileSync } from \"node:fs\";\nimport * as path from \"node:path\";\nimport {\n type AssetKind,\n type CatalogDomain,\n type CatalogEntry,\n factoryAssetRoots,\n parseFrontmatter,\n scanRepo,\n walkDir,\n} from \"@skaile/workspaces/core\";\nimport {\n assignDomain,\n buildDomainIndex,\n DOMAIN_MD_FILENAME,\n type DomainMd,\n parseDomainMd,\n} from \"@skaile/workspaces/discovery\";\n\n/** One non-fatal note returned to the caller for surfacing in the UI. */\nexport interface FeedNote {\n feed: \"sources\" | \"libraries\" | \"store\" | \"factory\";\n message: string;\n}\n\n/**\n * Which feed an asset came from. This is the top-level grouping axis in the\n * manage TUI (\"where is this skill coming from?\") and is intentionally distinct\n * from `publisher` (asset-intrinsic identity): the same publisher can legitimately\n * appear under more than one origin (e.g. a github repo you added as a `source`\n * that is also listed in the remote `store`).\n */\nexport type AssetOrigin = \"source\" | \"library\" | \"factory\" | \"store\";\n\n/** A catalog entry tagged with the feed it was gathered from. */\nexport interface OriginEntry {\n origin: AssetOrigin;\n entry: CatalogEntry;\n /**\n * Second-level grouping label for the manage tree. Defaults (when unset) to the\n * entry's `publisher`; the source feed sets it to the source's short repo name\n * so the Sources band groups by source — \"which repo did this come from\" — not\n * by the asset-intrinsic publisher.\n */\n group?: string;\n}\n\nexport interface AssetFeedResult {\n entries: OriginEntry[];\n /**\n * Display-only domain metadata, keyed (by the consumer) on `slug`. Populated\n * from the store's `catalog.listDomains` when the connected catalog source\n * exposes it; empty otherwise. The manage TUI joins `entry.domainSlug` → a\n * domain for grouping headers, descriptions, and relation badges.\n */\n domains: CatalogDomain[];\n notes: FeedNote[];\n}\n\n// ── Domain stamping (on-disk feeds) ──────────────────────────────────────────\n//\n// `scanRepo` (the source / library / factory scan path) does not read the\n// `DOMAIN.md` sidecars, so its entries arrive with no `domainSlug` and render\n// flat under their publisher band. We re-derive the grouping here from the\n// root's `DOMAIN.md` files (the same sidecars the remote store computes\n// server-side), and fall back to the repo/source name for any entry no domain\n// claims so it still groups instead of landing in the synthetic \"no domain\" pile.\n\n/** Repo-relative POSIX path (DOMAIN.md slugs are matched whole-segment, `/`-joined). */\nfunction toPosix(p: string): string {\n return p.split(path.sep).join(\"/\");\n}\n\n/** Parse every `DOMAIN.md` sidecar under `root` into a {@link DomainMd}. */\nasync function loadDomainMds(root: string): Promise<DomainMd[]> {\n const out: DomainMd[] = [];\n for await (const { path: filePath, name } of walkDir(root)) {\n if (name !== DOMAIN_MD_FILENAME) continue;\n try {\n const { data } = parseFrontmatter(readFileSync(filePath, \"utf8\"));\n out.push(parseDomainMd(toPosix(path.relative(root, filePath)), data));\n } catch {}\n }\n return out;\n}\n\n/**\n * Stamp `domainSlug` onto every entry scanned from `root` using the root's\n * `DOMAIN.md` sidecars. Returns the `CatalogDomain` registry for the real\n * domains, plus a synthetic fallback domain when any entry used the fallback.\n * Mutates `entries` in place (sets `entry.domainSlug`).\n *\n * `synthesizeFallback` (default true): entries no domain claims fall back to\n * `fallbackSlug` (the repo/source name). Pass `false` when the caller already\n * groups these entries one level up (e.g. the source feed groups by source\n * node) — unmatched entries then get no domain (`\"\"`) and hang directly under\n * that parent, instead of nesting under a same-named fallback domain.\n */\nasync function stampDomains(\n root: string,\n fallbackSlug: string,\n entries: CatalogEntry[],\n synthesizeFallback = true,\n): Promise<CatalogDomain[]> {\n const domainMds = await loadDomainMds(root);\n const assignables = entries.map((entry) => ({\n entry,\n ref: `${entry.kind}:${entry.name}`,\n relativePath: toPosix(path.relative(root, entry.source)),\n }));\n\n let usedFallback = false;\n for (const a of assignables) {\n const slug = assignDomain(a.relativePath, domainMds);\n if (slug) a.entry.domainSlug = slug;\n else if (synthesizeFallback) {\n a.entry.domainSlug = fallbackSlug;\n usedFallback = true;\n } else a.entry.domainSlug = \"\";\n }\n\n const { index } = buildDomainIndex(assignables, domainMds);\n const catalog: CatalogDomain[] = Object.values(index).map((d) => ({\n slug: d.slug,\n title: d.title,\n ...(d.description ? { description: d.description } : {}),\n ...(d.relation ? { relation: d.relation } : {}),\n ...(d.order !== undefined ? { order: d.order } : {}),\n ...(d.recommended[0] ? { recommendedRef: d.recommended[0] } : {}),\n }));\n if (usedFallback) catalog.push({ slug: fallbackSlug, title: fallbackSlug });\n return catalog;\n}\n\n/**\n * Pull assets from local libraries (the authoring places under\n * `~/.skaile/libraries/<name>/`, not the `~/.skaile/cache/sources/` cache). Each\n * library's `path` is scanned with `scanRepo` and grouped under the bare library\n * name (`group: <name>`) so the manage TUI shows a clean `<name>` band — no\n * `library:` prefix and no redundant same-named fallback domain (mirrors the\n * source feed).\n */\nasync function libraryAssets(): Promise<{\n entries: OriginEntry[];\n domains: CatalogDomain[];\n notes: FeedNote[];\n}> {\n const notes: FeedNote[] = [];\n const domains: CatalogDomain[] = [];\n try {\n const [{ openLibraryManager }, { skaileHomeDir }, { getGlobalCacheDir }] = await Promise.all([\n import(\"./open-library.ts\"),\n import(\"@skaile/workspaces/library\"),\n import(\"@skaile/workspaces/core\"),\n ]);\n const { manager, close } = await openLibraryManager();\n try {\n // Authoring libraries are the rows that are NOT source clones. index.db\n // rows predating the cache migration still carry the legacy\n // ~/.skaile/sources path, so exclude both roots.\n const newRoot = getGlobalCacheDir();\n const legacyRoot = path.join(skaileHomeDir(), \"sources\");\n const libs = (await manager.listLibraries()).filter(\n (l) => !l.path.startsWith(newRoot) && !l.path.startsWith(legacyRoot),\n );\n const entries: OriginEntry[] = [];\n for (const lib of libs) {\n if (!existsSync(lib.path)) continue;\n // Scan + group under the bare library name. `synthesizeFallback: false`\n // (as the source feed does) keeps domainless assets directly under the\n // library band instead of a redundant same-named fallback domain.\n const libEntries = [...(await scanRepo(lib.path, lib.name))];\n domains.push(...(await stampDomains(lib.path, lib.name, libEntries, false)));\n for (const entry of libEntries) entries.push({ origin: \"library\", entry, group: lib.name });\n }\n return { entries, domains, notes };\n } finally {\n close();\n }\n } catch (err) {\n notes.push({\n feed: \"libraries\",\n message: err instanceof Error ? err.message : String(err),\n });\n return { entries: [], domains, notes };\n }\n}\n\n/**\n * Pull a (best-effort) snapshot of the connected remote store catalog.\n *\n * - Returns no entries when the resolved catalog is local-only or the host\n * is unreachable (the failure becomes a note, not an exception).\n * - Maps `CatalogAsset` → `CatalogEntry`, carrying `publisher`, `repo`, and\n * `category` straight through and using `source = \"store://<id>\"`; per-file\n * `source` paths are not available for remote assets so the canonical ref is\n * a stable placeholder.\n */\nasync function storeAssets(projectDir: string): Promise<{\n entries: CatalogEntry[];\n domains: CatalogDomain[];\n notes: FeedNote[];\n}> {\n const notes: FeedNote[] = [];\n try {\n const { resolveCatalogSource } = await import(\"./open-library.ts\");\n const { source, close } = await resolveCatalogSource({ projectDir });\n try {\n const assets = await source.listAssets();\n const entries: CatalogEntry[] = assets.map((a) => ({\n name: a.name,\n kind: (a.kind as AssetKind) ?? \"skill\",\n description: a.description ?? \"\",\n source: `store://${a.id}`,\n publisher: a.publisher,\n repo: a.repo,\n domainSlug: a.domainSlug,\n category: a.category,\n version: a.version,\n requires: [],\n dependencies: [],\n }));\n // Domains are optional on the catalog source — only the store backend\n // (post Part 4 `catalog.listDomains`) exposes them. Duck-type the call so\n // older sources and the local catalog degrade to no domains, not an error.\n const domains = await loadDomains(source);\n return { entries, domains, notes };\n } finally {\n close();\n }\n } catch (err) {\n const msg = err instanceof Error ? err.message : String(err);\n // Local-only catalog throws a recognizable message — silence it; absence\n // is the user's choice, not an error.\n if (!/local/i.test(msg)) {\n notes.push({ feed: \"store\", message: msg });\n }\n return { entries: [], domains: [], notes };\n }\n}\n\n/** Optional `listDomains` capability — returns `[]` when the source lacks it. */\nasync function loadDomains(source: unknown): Promise<CatalogDomain[]> {\n const fn = (source as { listDomains?: () => Promise<CatalogDomain[]> }).listDomains;\n if (typeof fn !== \"function\") return [];\n const domains = await fn.call(source);\n return Array.isArray(domains) ? domains : [];\n}\n\n/** The slice of `AssetManager` the source feed needs (kept narrow for tests). */\ninterface AssetManagerLike {\n search: () => Promise<CatalogEntry[]>;\n searchRepoRoots: () => { repoName: string; root: string }[];\n}\n\n/**\n * Project-source feed: leans on `AssetManager.search()`, which now merges\n * `skaile.yaml`'s `sources:` field into the repositories map, then stamps\n * `DOMAIN.md`-derived domain grouping onto the scanned entries via\n * `searchRepoRoots()`.\n */\nasync function sourceAssets(\n am: AssetManagerLike,\n): Promise<{ entries: OriginEntry[]; domains: CatalogDomain[] }> {\n // The bundled factory tree is injected into the repositories map as an implicit\n // source, so `am.search()` returns it too. It has its own `factory` origin band,\n // so drop it here — otherwise the same first-party skills list twice under Sources.\n const factoryPrefixes = factoryAssetRoots().map((r) => (r.endsWith(path.sep) ? r : r + path.sep));\n const isFactoryPath = (p: string) =>\n factoryPrefixes.some((fp) => p === fp.slice(0, -1) || p.startsWith(fp));\n\n const all = (await am.search()).filter((e) => !isFactoryPath(e.source));\n const entries: OriginEntry[] = [];\n const domains: CatalogDomain[] = [];\n // Group each source's entries under the source node (its short repo name), not\n // the publisher: under Sources the navigational question is \"which repo did\n // this come from\". Each entry's `source` (absolute manifest path) lives under\n // exactly one declared root, so group + stamp by prefix. The cache slug is\n // URL-keyed `github.com/<org>/<repo>` — take the trailing segment.\n for (const { repoName, root } of am.searchRepoRoots()) {\n if (isFactoryPath(root)) continue;\n const prefix = root.endsWith(path.sep) ? root : root + path.sep;\n const owned = all.filter((e) => e.source === root || e.source.startsWith(prefix));\n if (owned.length === 0) continue;\n const sourceName = repoName.split(\"/\").pop() || repoName;\n // No synthetic fallback domain — the source node already groups these, so a\n // same-named fallback would just nest the source under itself.\n domains.push(...(await stampDomains(root, sourceName, owned, false)));\n for (const entry of owned) entries.push({ origin: \"source\", entry, group: sourceName });\n }\n return { entries, domains };\n}\n\n/**\n * Factory-asset feed: scan the bundled first-party `factory-assets` tree(s)\n * resolved by `factoryAssetRoots()` (the `SKAILE_FACTORY_ASSETS_DIR` override\n * layer ahead of the bundled tree). Local disk only, no network — the entries are\n * the built-in skills / connectors / bundles that ship with `@skaile/workspaces`.\n * `factoryAssetRoots()` already dedupes, so the env override pointing at the\n * bundled dir collapses to one root.\n */\nasync function factoryAssets(): Promise<{\n entries: CatalogEntry[];\n domains: CatalogDomain[];\n notes: FeedNote[];\n}> {\n const notes: FeedNote[] = [];\n const domains: CatalogDomain[] = [];\n try {\n const entries: CatalogEntry[] = [];\n for (const root of factoryAssetRoots()) {\n const rootEntries = [...(await scanRepo(root, \"skaile-factory\"))];\n domains.push(...(await stampDomains(root, \"skaile-factory\", rootEntries)));\n entries.push(...rootEntries);\n }\n return { entries, domains, notes };\n } catch (err) {\n notes.push({\n feed: \"factory\",\n message: err instanceof Error ? err.message : String(err),\n });\n return { entries: [], domains, notes };\n }\n}\n\n/** Tag a flat entry list with a single origin. */\nfunction tag(origin: AssetOrigin, entries: CatalogEntry[]): OriginEntry[] {\n return entries.map((entry) => ({ origin, entry }));\n}\n\n/**\n * Run all feeds and return a single normalized result.\n *\n * Feeds run in parallel where possible — the store fetch is the slow one\n * (one HTTP call) and is fired alongside the local library walk. The factory\n * scan is local disk only, so it runs inline.\n */\nexport async function gatherAssetFeeds(\n am: AssetManagerLike,\n projectDir: string,\n): Promise<AssetFeedResult> {\n const [libs, store] = await Promise.all([libraryAssets(), storeAssets(projectDir)]);\n const factory = await factoryAssets();\n const src = await sourceAssets(am);\n return {\n entries: [\n ...src.entries,\n ...libs.entries,\n ...tag(\"factory\", factory.entries),\n ...tag(\"store\", store.entries),\n ],\n // Store domains first (server-curated), then the on-disk feeds; dedupe by\n // slug, first-wins, so a store-served domain shadows a same-slug local one.\n domains: dedupeBySlug([...store.domains, ...src.domains, ...libs.domains, ...factory.domains]),\n notes: [...libs.notes, ...store.notes, ...factory.notes],\n };\n}\n\n/** First-wins dedupe of a domain list by `slug`. */\nfunction dedupeBySlug(domains: CatalogDomain[]): CatalogDomain[] {\n const seen = new Set<string>();\n const out: CatalogDomain[] = [];\n for (const d of domains) {\n if (seen.has(d.slug)) continue;\n seen.add(d.slug);\n out.push(d);\n }\n return out;\n}\n"]}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
export { AssetManager, FACTORY_SOURCE_URL, MissingManifestError, NON_DEPLOYABLE_KINDS, normalizeRepoUrl, parseCanonicalLockKey, parseRefTolerant, renderMcpServerConfig, softDepName } from '../chunk-
|
|
1
|
+
export { AssetManager, FACTORY_SOURCE_URL, MissingManifestError, NON_DEPLOYABLE_KINDS, normalizeRepoUrl, parseCanonicalLockKey, parseRefTolerant, renderMcpServerConfig, softDepName } from '../chunk-Q6O53D5Q.js';
|
|
2
2
|
import '../chunk-3HVASHBF.js';
|
|
3
3
|
import '../chunk-NU4E7C5I.js';
|
|
4
4
|
import '../chunk-UKJMQZV6.js';
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { SUPPORTED_CLOUDS, buildClaudeCloudEnv } from '../../chunk-ISQWMBKD.js';
|
|
2
2
|
import { dispatchCapability } from '../../chunk-RRVQAE5D.js';
|
|
3
|
-
import { fetchProviderModels } from '../../chunk-
|
|
3
|
+
import { fetchProviderModels } from '../../chunk-V34ZEXSE.js';
|
|
4
4
|
import { AuthError, classifyClaudeSdkError, reclassifyAuthAsAccountUnavailable, AccountUnavailableError } from '../../chunk-GAH4YRCI.js';
|
|
5
|
-
import { BUILTIN_DRIVER_CATALOG, AgentDriver, getBridgeLogger } from '../../chunk-
|
|
5
|
+
import { BUILTIN_DRIVER_CATALOG, AgentDriver, getBridgeLogger } from '../../chunk-SR6NBBWT.js';
|
|
6
6
|
import '../../chunk-6E6PKKAD.js';
|
|
7
7
|
import '../../chunk-P43HBWKK.js';
|
|
8
8
|
import '../../chunk-F3HNW354.js';
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { fetchProviderModels } from '../../chunk-
|
|
1
|
+
import { fetchProviderModels } from '../../chunk-V34ZEXSE.js';
|
|
2
2
|
import { classifyGenericErrorMessage } from '../../chunk-GAH4YRCI.js';
|
|
3
|
-
import { BUILTIN_DRIVER_CATALOG, AgentDriver, getBridgeLogger } from '../../chunk-
|
|
3
|
+
import { BUILTIN_DRIVER_CATALOG, AgentDriver, getBridgeLogger } from '../../chunk-SR6NBBWT.js';
|
|
4
4
|
import '../../chunk-6E6PKKAD.js';
|
|
5
5
|
import '../../chunk-U5POE4BA.js';
|
|
6
6
|
import '../../chunk-7GOCNYUV.js';
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { SubprocessCliDriver, mapApiKeysToEnv, extractText, extractCost, extractTokens } from '../../chunk-
|
|
1
|
+
import { SubprocessCliDriver, mapApiKeysToEnv, extractText, extractCost, extractTokens } from '../../chunk-BJDACPWZ.js';
|
|
2
2
|
import '../../chunk-GAH4YRCI.js';
|
|
3
|
-
import { BUILTIN_DRIVER_CATALOG, getBridgeLogger } from '../../chunk-
|
|
3
|
+
import { BUILTIN_DRIVER_CATALOG, getBridgeLogger } from '../../chunk-SR6NBBWT.js';
|
|
4
4
|
import '../../chunk-6E6PKKAD.js';
|
|
5
5
|
import '../../chunk-U5POE4BA.js';
|
|
6
6
|
import '../../chunk-7GOCNYUV.js';
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { dispatchCapability } from '../../chunk-RRVQAE5D.js';
|
|
2
|
-
import { BUILTIN_DRIVER_CATALOG, AgentDriver, getBridgeLogger } from '../../chunk-
|
|
2
|
+
import { BUILTIN_DRIVER_CATALOG, AgentDriver, getBridgeLogger } from '../../chunk-SR6NBBWT.js';
|
|
3
3
|
import '../../chunk-6E6PKKAD.js';
|
|
4
4
|
import '../../chunk-U5POE4BA.js';
|
|
5
5
|
import '../../chunk-7GOCNYUV.js';
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
export { GeminiDriver, GeminiFamilyDriver, geminiDriverTarget } from '../../chunk-
|
|
2
|
-
import '../../chunk-
|
|
3
|
-
import '../../chunk-
|
|
1
|
+
export { GeminiDriver, GeminiFamilyDriver, geminiDriverTarget } from '../../chunk-KXWUCKP5.js';
|
|
2
|
+
import '../../chunk-BJDACPWZ.js';
|
|
3
|
+
import '../../chunk-V34ZEXSE.js';
|
|
4
4
|
import '../../chunk-GAH4YRCI.js';
|
|
5
|
-
import '../../chunk-
|
|
5
|
+
import '../../chunk-SR6NBBWT.js';
|
|
6
6
|
import '../../chunk-6E6PKKAD.js';
|
|
7
7
|
import '../../chunk-U5POE4BA.js';
|
|
8
8
|
import '../../chunk-7GOCNYUV.js';
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { SubprocessCliDriver, mapApiKeysToEnv, extractText, extractCost, extractTokens } from '../../chunk-
|
|
1
|
+
import { SubprocessCliDriver, mapApiKeysToEnv, extractText, extractCost, extractTokens } from '../../chunk-BJDACPWZ.js';
|
|
2
2
|
import '../../chunk-GAH4YRCI.js';
|
|
3
|
-
import { BUILTIN_DRIVER_CATALOG, getBridgeLogger } from '../../chunk-
|
|
3
|
+
import { BUILTIN_DRIVER_CATALOG, getBridgeLogger } from '../../chunk-SR6NBBWT.js';
|
|
4
4
|
import '../../chunk-6E6PKKAD.js';
|
|
5
5
|
import '../../chunk-U5POE4BA.js';
|
|
6
6
|
import '../../chunk-7GOCNYUV.js';
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { classifyGenericErrorMessage } from '../../chunk-GAH4YRCI.js';
|
|
2
|
-
import { BUILTIN_DRIVER_CATALOG, AgentDriver, getBridgeLogger } from '../../chunk-
|
|
2
|
+
import { BUILTIN_DRIVER_CATALOG, AgentDriver, getBridgeLogger } from '../../chunk-SR6NBBWT.js';
|
|
3
3
|
import '../../chunk-6E6PKKAD.js';
|
|
4
4
|
import '../../chunk-U5POE4BA.js';
|
|
5
5
|
import '../../chunk-7GOCNYUV.js';
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { SubprocessCliDriver, mapApiKeysToEnv, extractText, extractCost, extractTokens } from '../../chunk-
|
|
1
|
+
import { SubprocessCliDriver, mapApiKeysToEnv, extractText, extractCost, extractTokens } from '../../chunk-BJDACPWZ.js';
|
|
2
2
|
import '../../chunk-GAH4YRCI.js';
|
|
3
|
-
import { BUILTIN_DRIVER_CATALOG, getBridgeLogger } from '../../chunk-
|
|
3
|
+
import { BUILTIN_DRIVER_CATALOG, getBridgeLogger } from '../../chunk-SR6NBBWT.js';
|
|
4
4
|
import '../../chunk-6E6PKKAD.js';
|
|
5
5
|
import '../../chunk-U5POE4BA.js';
|
|
6
6
|
import '../../chunk-7GOCNYUV.js';
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { GeminiFamilyDriver } from '../../chunk-
|
|
2
|
-
import '../../chunk-
|
|
3
|
-
import { fetchProviderModels } from '../../chunk-
|
|
1
|
+
import { GeminiFamilyDriver } from '../../chunk-KXWUCKP5.js';
|
|
2
|
+
import '../../chunk-BJDACPWZ.js';
|
|
3
|
+
import { fetchProviderModels } from '../../chunk-V34ZEXSE.js';
|
|
4
4
|
import '../../chunk-GAH4YRCI.js';
|
|
5
|
-
import { BUILTIN_DRIVER_CATALOG, getBridgeLogger } from '../../chunk-
|
|
5
|
+
import { BUILTIN_DRIVER_CATALOG, getBridgeLogger } from '../../chunk-SR6NBBWT.js';
|
|
6
6
|
import '../../chunk-6E6PKKAD.js';
|
|
7
7
|
import '../../chunk-U5POE4BA.js';
|
|
8
8
|
import '../../chunk-7GOCNYUV.js';
|
package/dist/bridge/index.js
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
export { BridgeRuntime, EventNormalizer, createRuntime, detectFileChange, detectFileChanges, summarizeToolCall, summarizeToolResult, validateApiKey } from '../chunk-
|
|
1
|
+
export { BridgeRuntime, EventNormalizer, createRuntime, detectFileChange, detectFileChanges, summarizeToolCall, summarizeToolResult, validateApiKey } from '../chunk-P5W6JVD4.js';
|
|
2
2
|
export { CLOUD_SECRET_ENV_KEYS, SUPPORTED_CLOUDS, buildClaudeCloudEnv } from '../chunk-ISQWMBKD.js';
|
|
3
3
|
export { dispatchCapability, filterRenderCapabilities, renderFallback } from '../chunk-RRVQAE5D.js';
|
|
4
|
-
export { STATIC_MODELS, fetchProviderModels, getModels, getStaticModels } from '../chunk-
|
|
4
|
+
export { ModelTierResolutionError, PROVIDER_MODEL_TIERS, STATIC_MODELS, fetchProviderModels, getModels, getStaticModels, resolveModelTier } from '../chunk-V34ZEXSE.js';
|
|
5
5
|
export { AccountUnavailableError, AuthError, classifyClaudeSdkError, reclassifyAuthAsAccountUnavailable } from '../chunk-GAH4YRCI.js';
|
|
6
|
-
export { AgentDriver, BUILTIN_DRIVER_CATALOG, DRIVER_CATALOG, createDriver, getBridgeLogger, listDrivers, listModelsForDriver, registerBuiltinDrivers } from '../chunk-
|
|
6
|
+
export { AgentDriver, BUILTIN_DRIVER_CATALOG, DRIVER_CATALOG, createDriver, getBridgeLogger, listDrivers, listModelsForDriver, registerBuiltinDrivers } from '../chunk-SR6NBBWT.js';
|
|
7
7
|
import '../chunk-6E6PKKAD.js';
|
|
8
8
|
import '../chunk-U5POE4BA.js';
|
|
9
9
|
import '../chunk-7GOCNYUV.js';
|
|
@@ -87,4 +87,63 @@ export declare const STATIC_MODELS: Record<string, ModelEntry[]>;
|
|
|
87
87
|
* @docLink packages/bridge/api-reference#models
|
|
88
88
|
*/
|
|
89
89
|
export declare function getStaticModels(provider: string): ModelEntry[];
|
|
90
|
+
/** Per-tier concrete model ids for one provider. */
|
|
91
|
+
export interface ModelTierOverrides {
|
|
92
|
+
small?: string;
|
|
93
|
+
default?: string;
|
|
94
|
+
deep?: string;
|
|
95
|
+
}
|
|
96
|
+
/**
|
|
97
|
+
* Built-in tier→model mapping per provider. This is the point of the closed
|
|
98
|
+
* `small | default | deep` vocabulary: an authored flow names an intent and the
|
|
99
|
+
* runtime owns which concrete model serves it, so flows stay portable across
|
|
100
|
+
* model-lineup changes.
|
|
101
|
+
*
|
|
102
|
+
* These are **direct provider-API ids**. A gateway transport (Bedrock, Vertex,
|
|
103
|
+
* Azure) addresses the same models by different ids — Bedrock prefixes
|
|
104
|
+
* `us.anthropic.`, for instance — and that translation belongs to whoever owns
|
|
105
|
+
* the deployment, not here. {@link resolveModelTier} therefore consults this
|
|
106
|
+
* table only on the direct API and demands an explicit override otherwise,
|
|
107
|
+
* rather than handing a gateway an id it cannot serve.
|
|
108
|
+
*
|
|
109
|
+
* Every id here must also appear in {@link STATIC_MODELS} — a test asserts it,
|
|
110
|
+
* so the two cannot drift into naming a model the catalog disowns. That check
|
|
111
|
+
* proves internal consistency only; it cannot tell you an id is still current
|
|
112
|
+
* with a provider's live lineup.
|
|
113
|
+
*
|
|
114
|
+
* Where a provider's lineup has no genuinely distinct model for a tier, the
|
|
115
|
+
* entry deliberately repeats the neighbouring one. That is a reviewable
|
|
116
|
+
* property of that lineup, unlike inheriting whatever model the session
|
|
117
|
+
* happened to start with — which is how `small` could silently mean Opus.
|
|
118
|
+
*/
|
|
119
|
+
export declare const PROVIDER_MODEL_TIERS: Record<string, Required<ModelTierOverrides>>;
|
|
120
|
+
/** Raised when a tier names an intent this provider cannot serve. */
|
|
121
|
+
export declare class ModelTierResolutionError extends Error {
|
|
122
|
+
readonly tier: "small" | "deep";
|
|
123
|
+
readonly provider: string | undefined;
|
|
124
|
+
constructor(tier: "small" | "deep", provider: string | undefined);
|
|
125
|
+
}
|
|
126
|
+
/**
|
|
127
|
+
* Resolve a Flow v2 `run.model` tier to a concrete model id.
|
|
128
|
+
*
|
|
129
|
+
* `"default"` and an absent tier **inherit `sessionModel` first**. The session
|
|
130
|
+
* model is the one id known to work for this deployment — it already carries
|
|
131
|
+
* whatever provider, lineup and gateway translation the host configured — so
|
|
132
|
+
* preferring a built-in over it would silently downgrade a configured model
|
|
133
|
+
* and, on a gateway transport, substitute an id that provider cannot serve.
|
|
134
|
+
*
|
|
135
|
+
* `"small"` and `"deep"` never fall back to `sessionModel`: they resolve from
|
|
136
|
+
* an override, then from {@link PROVIDER_MODEL_TIERS} on the direct provider
|
|
137
|
+
* API, and otherwise throw {@link ModelTierResolutionError}. Inheriting there
|
|
138
|
+
* would run an arbitrary model behind an author's explicit request for a cheap
|
|
139
|
+
* or a strong one — a cost or quality surprise that shows up only in the bill
|
|
140
|
+
* or the output. Failing names it at the node instead.
|
|
141
|
+
*
|
|
142
|
+
* Pure: no I/O, no environment reads.
|
|
143
|
+
*/
|
|
144
|
+
export declare function resolveModelTier(tier: "small" | "default" | "deep" | undefined, sessionModel: string | undefined, options?: {
|
|
145
|
+
provider?: string;
|
|
146
|
+
cloud?: string;
|
|
147
|
+
overrides?: ModelTierOverrides;
|
|
148
|
+
}): string | undefined;
|
|
90
149
|
//# sourceMappingURL=models.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"models.d.ts","sourceRoot":"","sources":["../../../bridge/src/models.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAIH;;;;;;;GAOG;AACH,MAAM,WAAW,UAAU;IACzB,yFAAyF;IACzF,EAAE,EAAE,MAAM,CAAC;IACX,iFAAiF;IACjF,IAAI,EAAE,MAAM,CAAC;CACd;AA6GD;;;;;;;;GAQG;AACH,MAAM,WAAW,iBAAiB;IAChC,iEAAiE;IACjE,EAAE,EAAE,OAAO,CAAC;IACZ,4CAA4C;IAC5C,MAAM,EAAE,UAAU,EAAE,CAAC;IACrB,6DAA6D;IAC7D,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,2EAA2E;IAC3E,MAAM,EAAE,KAAK,GAAG,QAAQ,CAAC;CAC1B;AAED;;;;;;;;;;;;GAYG;AACH,wBAAsB,mBAAmB,CACvC,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,iBAAiB,CAAC,CA+C5B;AAED;;;;;;;;;;;GAWG;AACH,wBAAsB,SAAS,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAkB7F;AAMD;;;;;;;;;GASG;AACH,eAAO,MAAM,aAAa,EAAE,MAAM,CAAC,MAAM,EAAE,UAAU,EAAE,CAgEtD,CAAC;AAEF;;;;;;;;;GASG;AACH,wBAAgB,eAAe,CAAC,QAAQ,EAAE,MAAM,GAAG,UAAU,EAAE,CAE9D"}
|
|
1
|
+
{"version":3,"file":"models.d.ts","sourceRoot":"","sources":["../../../bridge/src/models.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAIH;;;;;;;GAOG;AACH,MAAM,WAAW,UAAU;IACzB,yFAAyF;IACzF,EAAE,EAAE,MAAM,CAAC;IACX,iFAAiF;IACjF,IAAI,EAAE,MAAM,CAAC;CACd;AA6GD;;;;;;;;GAQG;AACH,MAAM,WAAW,iBAAiB;IAChC,iEAAiE;IACjE,EAAE,EAAE,OAAO,CAAC;IACZ,4CAA4C;IAC5C,MAAM,EAAE,UAAU,EAAE,CAAC;IACrB,6DAA6D;IAC7D,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,2EAA2E;IAC3E,MAAM,EAAE,KAAK,GAAG,QAAQ,CAAC;CAC1B;AAED;;;;;;;;;;;;GAYG;AACH,wBAAsB,mBAAmB,CACvC,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,iBAAiB,CAAC,CA+C5B;AAED;;;;;;;;;;;GAWG;AACH,wBAAsB,SAAS,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAkB7F;AAMD;;;;;;;;;GASG;AACH,eAAO,MAAM,aAAa,EAAE,MAAM,CAAC,MAAM,EAAE,UAAU,EAAE,CAgEtD,CAAC;AAEF;;;;;;;;;GASG;AACH,wBAAgB,eAAe,CAAC,QAAQ,EAAE,MAAM,GAAG,UAAU,EAAE,CAE9D;AAMD,oDAAoD;AACpD,MAAM,WAAW,kBAAkB;IACjC,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,eAAO,MAAM,oBAAoB,EAAE,MAAM,CAAC,MAAM,EAAE,QAAQ,CAAC,kBAAkB,CAAC,CAmC7E,CAAC;AAEF,qEAAqE;AACrE,qBAAa,wBAAyB,SAAQ,KAAK;IAE/C,QAAQ,CAAC,IAAI,EAAE,OAAO,GAAG,MAAM;IAC/B,QAAQ,CAAC,QAAQ,EAAE,MAAM,GAAG,SAAS;gBAD5B,IAAI,EAAE,OAAO,GAAG,MAAM,EACtB,QAAQ,EAAE,MAAM,GAAG,SAAS;CAQxC;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,gBAAgB,CAC9B,IAAI,EAAE,OAAO,GAAG,SAAS,GAAG,MAAM,GAAG,SAAS,EAC9C,YAAY,EAAE,MAAM,GAAG,SAAS,EAChC,OAAO,GAAE;IAAE,QAAQ,CAAC,EAAE,MAAM,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,SAAS,CAAC,EAAE,kBAAkB,CAAA;CAAO,GAClF,MAAM,GAAG,SAAS,CAWpB"}
|
|
@@ -600,8 +600,7 @@ var NodeControlSchema = z.strictObject({
|
|
|
600
600
|
optional: z.boolean().optional(),
|
|
601
601
|
retries: z.number().int().min(0).optional(),
|
|
602
602
|
timeoutSec: z.number().positive().optional(),
|
|
603
|
-
parallelGroup: nonEmptyString.optional()
|
|
604
|
-
subagent: z.boolean().optional()
|
|
603
|
+
parallelGroup: nonEmptyString.optional()
|
|
605
604
|
});
|
|
606
605
|
var runAssets = { assets: z.array(nonEmptyString).optional() };
|
|
607
606
|
var modelTier = z.enum(["small", "default", "deep"]);
|
|
@@ -712,7 +711,6 @@ var FlowDefaultsSchema = z.strictObject({
|
|
|
712
711
|
approval: z.enum(["checkpoint", "auto", "manual"]).optional(),
|
|
713
712
|
researchDepth: nonEmptyString.optional(),
|
|
714
713
|
autoReview: z.boolean().optional(),
|
|
715
|
-
subagentMode: z.boolean().optional(),
|
|
716
714
|
verbosity: nonEmptyString.optional(),
|
|
717
715
|
cliMode: z.boolean().optional(),
|
|
718
716
|
run_input: z.json().optional(),
|
|
@@ -1010,7 +1008,6 @@ var LegacyNodeDataSchema = z.looseObject({
|
|
|
1010
1008
|
parallel_group: z.string().min(1).optional(),
|
|
1011
1009
|
flow: z.string().min(1).optional(),
|
|
1012
1010
|
pass_context: z.boolean().optional(),
|
|
1013
|
-
subagent: z.boolean().optional(),
|
|
1014
1011
|
message: z.string().min(1).optional(),
|
|
1015
1012
|
routes: z.array(LegacyRouteSchema).optional(),
|
|
1016
1013
|
assets: z.array(z.string().min(1)).optional()
|
|
@@ -1060,16 +1057,17 @@ var LEGACY_DEFAULT_KEYS = {
|
|
|
1060
1057
|
approval_mode: "approval",
|
|
1061
1058
|
research_depth: "researchDepth",
|
|
1062
1059
|
auto_review: "autoReview",
|
|
1063
|
-
subagent_mode: "subagentMode",
|
|
1064
1060
|
verbosity: "verbosity",
|
|
1065
1061
|
cli_mode: "cliMode",
|
|
1066
1062
|
run_input: "run_input"
|
|
1067
1063
|
};
|
|
1064
|
+
var DROPPED_LEGACY_DEFAULT_KEYS = /* @__PURE__ */ new Set(["subagent_mode"]);
|
|
1068
1065
|
function normalizeDefaults(globals) {
|
|
1069
1066
|
if (!globals) return void 0;
|
|
1070
1067
|
const known = {};
|
|
1071
1068
|
const parameters = {};
|
|
1072
1069
|
for (const [key, value] of Object.entries(globals)) {
|
|
1070
|
+
if (DROPPED_LEGACY_DEFAULT_KEYS.has(key)) continue;
|
|
1073
1071
|
const normalizedKey = LEGACY_DEFAULT_KEYS[key];
|
|
1074
1072
|
if (normalizedKey) {
|
|
1075
1073
|
known[normalizedKey] = key === "approval_mode" && value === "auto_approve" ? "auto" : value;
|
|
@@ -1142,8 +1140,7 @@ function normalizeV1(data) {
|
|
|
1142
1140
|
const parameters2 = data2.parameters ?? {};
|
|
1143
1141
|
const control2 = {
|
|
1144
1142
|
optional: data2.optional,
|
|
1145
|
-
parallelGroup: data2.parallel_group
|
|
1146
|
-
subagent: data2.subagent
|
|
1143
|
+
parallelGroup: data2.parallel_group
|
|
1147
1144
|
};
|
|
1148
1145
|
nodes.push({
|
|
1149
1146
|
id: node.id,
|
|
@@ -1181,7 +1178,7 @@ function normalizeV1(data) {
|
|
|
1181
1178
|
requires: [{ expr: "false" }],
|
|
1182
1179
|
input: Object.keys(parameters2).length > 0 ? normalizeLegacyBinding(parameters2) : void 0
|
|
1183
1180
|
},
|
|
1184
|
-
control: { optional: true, parallelGroup: data2.parallel_group
|
|
1181
|
+
control: { optional: true, parallelGroup: data2.parallel_group }
|
|
1185
1182
|
});
|
|
1186
1183
|
continue;
|
|
1187
1184
|
}
|
|
@@ -1194,8 +1191,7 @@ function normalizeV1(data) {
|
|
|
1194
1191
|
const assets = [...skillAsset ? [skillAsset] : [], ...data2.assets ?? []];
|
|
1195
1192
|
const control = {
|
|
1196
1193
|
optional: data2.optional,
|
|
1197
|
-
parallelGroup: data2.parallel_group
|
|
1198
|
-
subagent: data2.subagent
|
|
1194
|
+
parallelGroup: data2.parallel_group
|
|
1199
1195
|
};
|
|
1200
1196
|
nodes.push({
|
|
1201
1197
|
id: node.id,
|
|
@@ -1256,5 +1252,5 @@ function parseFlowDefinition(data) {
|
|
|
1256
1252
|
}
|
|
1257
1253
|
|
|
1258
1254
|
export { FLOW_EXPRESSION_LIMITS, FlowDefinitionSchema, FlowExpressionError, collectFlowBindingExpressions, evaluate, evaluateFlowExpression, inspectFlowExpression, normalizeV1, parseFlowDefinition, resolveFlowBindings, stableFlowJson };
|
|
1259
|
-
//# sourceMappingURL=chunk-
|
|
1260
|
-
//# sourceMappingURL=chunk-
|
|
1255
|
+
//# sourceMappingURL=chunk-5QGMEPUX.js.map
|
|
1256
|
+
//# sourceMappingURL=chunk-5QGMEPUX.js.map
|