@botbotgo/agent-harness 0.0.101 → 0.0.102
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/dist/package-version.d.ts +1 -1
- package/dist/package-version.js +1 -1
- package/dist/persistence/sqlite-run-context-store.d.ts +22 -0
- package/dist/persistence/sqlite-run-context-store.js +64 -0
- package/dist/persistence/sqlite-run-queue-store.d.ts +41 -0
- package/dist/persistence/sqlite-run-queue-store.js +120 -0
- package/dist/persistence/sqlite-store.d.ts +2 -2
- package/dist/persistence/sqlite-store.js +31 -117
- package/dist/resource/mcp-tool-support.d.ts +21 -0
- package/dist/resource/mcp-tool-support.js +173 -0
- package/dist/resource/resource-impl.d.ts +1 -18
- package/dist/resource/resource-impl.js +3 -166
- package/dist/runtime/adapter/invoke-runtime.d.ts +22 -0
- package/dist/runtime/adapter/invoke-runtime.js +18 -0
- package/dist/runtime/adapter/stream-runtime.d.ts +46 -0
- package/dist/runtime/adapter/stream-runtime.js +93 -0
- package/dist/runtime/agent-runtime-adapter.js +93 -168
- package/dist/runtime/harness/run/run-operations.d.ts +50 -0
- package/dist/runtime/harness/run/run-operations.js +113 -0
- package/dist/runtime/harness/run/run-slot-acquisition.d.ts +64 -0
- package/dist/runtime/harness/run/run-slot-acquisition.js +157 -0
- package/dist/runtime/harness/run/stream-run.d.ts +53 -0
- package/dist/runtime/harness/run/stream-run.js +304 -0
- package/dist/runtime/harness.js +79 -528
- package/dist/workspace/object-loader.d.ts +1 -8
- package/dist/workspace/object-loader.js +3 -197
- package/dist/workspace/yaml-object-reader.d.ts +15 -0
- package/dist/workspace/yaml-object-reader.js +202 -0
- package/package.json +1 -1
|
@@ -1,18 +1,12 @@
|
|
|
1
1
|
import type { ParsedAgentObject, WorkspaceLoadOptions, WorkspaceObject } from "../contracts/types.js";
|
|
2
|
+
export { normalizeYamlItem, readYamlItems } from "./yaml-object-reader.js";
|
|
2
3
|
type RefMap = Map<string, WorkspaceObject | ParsedAgentObject>;
|
|
3
4
|
export type WorkspaceObjects = {
|
|
4
5
|
refs: RefMap;
|
|
5
6
|
agents: ParsedAgentObject[];
|
|
6
7
|
};
|
|
7
8
|
export declare function conventionalPackageRoots(root: string, relativeDir: "tools" | "skills"): string[];
|
|
8
|
-
export declare function normalizeYamlItem(item: Record<string, unknown>): Record<string, unknown>;
|
|
9
9
|
export declare function parseAgentItem(item: Record<string, unknown>, sourcePath: string): ParsedAgentObject;
|
|
10
|
-
export declare function readYamlItems(root: string, relativeDir?: string, options?: {
|
|
11
|
-
recursive?: boolean;
|
|
12
|
-
}): Promise<Array<{
|
|
13
|
-
item: Record<string, unknown>;
|
|
14
|
-
sourcePath: string;
|
|
15
|
-
}>>;
|
|
16
10
|
export declare function readToolModuleItems(root: string): Promise<Array<{
|
|
17
11
|
item: Record<string, unknown>;
|
|
18
12
|
sourcePath: string;
|
|
@@ -30,4 +24,3 @@ export declare function readToolModuleItems(root: string): Promise<Array<{
|
|
|
30
24
|
* - scalars and non-plain objects are replaced
|
|
31
25
|
*/
|
|
32
26
|
export declare function loadWorkspaceObjects(workspaceRoot: string, options?: WorkspaceLoadOptions): Promise<WorkspaceObjects>;
|
|
33
|
-
export {};
|
|
@@ -2,12 +2,12 @@ import path from "node:path";
|
|
|
2
2
|
import { existsSync, statSync } from "node:fs";
|
|
3
3
|
import { readdir, readFile } from "node:fs/promises";
|
|
4
4
|
import { fileURLToPath, pathToFileURL } from "node:url";
|
|
5
|
-
import { parseAllDocuments } from "yaml";
|
|
6
5
|
import { resolveIsolatedResourceModulePath } from "../resource/isolation.js";
|
|
7
6
|
import { isExternalSourceLocator, resolveResourcePackageRoot } from "../resource/sources.js";
|
|
8
7
|
import { discoverToolModuleDefinitions, isSupportedToolModulePath } from "../tool-modules.js";
|
|
9
|
-
import { fileExists
|
|
10
|
-
|
|
8
|
+
import { fileExists } from "../utils/fs.js";
|
|
9
|
+
import { readNamedModelItems, readNamedYamlItems, readYamlItems, } from "./yaml-object-reader.js";
|
|
10
|
+
export { normalizeYamlItem, readYamlItems } from "./yaml-object-reader.js";
|
|
11
11
|
const CONVENTIONAL_OBJECT_DIRECTORIES = ["tools"];
|
|
12
12
|
const MODULE_AGENT_FILENAMES = ["agent.yaml", "agent.yml"];
|
|
13
13
|
const MODULE_TOOL_FILENAMES = ["tool.yaml", "tool.yml"];
|
|
@@ -84,107 +84,6 @@ function asMutableObject(value) {
|
|
|
84
84
|
? { ...value }
|
|
85
85
|
: undefined;
|
|
86
86
|
}
|
|
87
|
-
function normalizeCatalogSpec(document, options = {}) {
|
|
88
|
-
const typed = asObject(document);
|
|
89
|
-
const spec = typed?.spec;
|
|
90
|
-
if (!Array.isArray(spec)) {
|
|
91
|
-
return [];
|
|
92
|
-
}
|
|
93
|
-
const normalized = spec
|
|
94
|
-
.filter((item) => typeof item === "object" && item !== null && !Array.isArray(item))
|
|
95
|
-
.map((item) => {
|
|
96
|
-
const id = typeof item.id === "string" && item.id.trim()
|
|
97
|
-
? item.id
|
|
98
|
-
: typeof item.name === "string" && item.name.trim()
|
|
99
|
-
? item.name
|
|
100
|
-
: undefined;
|
|
101
|
-
const itemKind = typeof item.kind === "string" && item.kind.trim()
|
|
102
|
-
? item.kind
|
|
103
|
-
: options.defaultKind;
|
|
104
|
-
if (!id || !itemKind) {
|
|
105
|
-
return null;
|
|
106
|
-
}
|
|
107
|
-
return {
|
|
108
|
-
...item,
|
|
109
|
-
kind: itemKind,
|
|
110
|
-
id,
|
|
111
|
-
};
|
|
112
|
-
});
|
|
113
|
-
return normalized.filter((item) => item !== null);
|
|
114
|
-
}
|
|
115
|
-
function normalizeKind(kind) {
|
|
116
|
-
switch (kind) {
|
|
117
|
-
case "Agent":
|
|
118
|
-
return "agent";
|
|
119
|
-
case "FileStore":
|
|
120
|
-
return "file-store";
|
|
121
|
-
case "InMemoryStore":
|
|
122
|
-
return "in-memory-store";
|
|
123
|
-
case "RedisStore":
|
|
124
|
-
return "redis-store";
|
|
125
|
-
case "PostgresStore":
|
|
126
|
-
return "postgres-store";
|
|
127
|
-
case "SqliteSaver":
|
|
128
|
-
return "sqlite-saver";
|
|
129
|
-
case "FileCheckpointer":
|
|
130
|
-
return "file-checkpointer";
|
|
131
|
-
case "Checkpointer":
|
|
132
|
-
return "checkpointer";
|
|
133
|
-
case "Model":
|
|
134
|
-
return "model";
|
|
135
|
-
case "EmbeddingModel":
|
|
136
|
-
return "embedding-model";
|
|
137
|
-
case "VectorStore":
|
|
138
|
-
return "vector-store";
|
|
139
|
-
case "Backend":
|
|
140
|
-
return "backend";
|
|
141
|
-
case "Store":
|
|
142
|
-
return "store";
|
|
143
|
-
case "Memory":
|
|
144
|
-
return "memory";
|
|
145
|
-
case "Tool":
|
|
146
|
-
return "tool";
|
|
147
|
-
case "Skill":
|
|
148
|
-
return "skill";
|
|
149
|
-
case "Runtime":
|
|
150
|
-
return "runtime";
|
|
151
|
-
case "RuntimeMemory":
|
|
152
|
-
return "runtime-memory";
|
|
153
|
-
case "Prompt":
|
|
154
|
-
return "prompt";
|
|
155
|
-
case "McpServer":
|
|
156
|
-
return "mcp";
|
|
157
|
-
default:
|
|
158
|
-
return kind;
|
|
159
|
-
}
|
|
160
|
-
}
|
|
161
|
-
export function normalizeYamlItem(item) {
|
|
162
|
-
if (item.kind === "DeepAgent" || item.kind === "LangChainAgent") {
|
|
163
|
-
throw new Error(`YAML object kind ${String(item.kind)} is no longer supported; use kind: Agent with spec.execution.backend instead`);
|
|
164
|
-
}
|
|
165
|
-
const metadata = asObject(item.metadata);
|
|
166
|
-
const spec = asObject(item.spec);
|
|
167
|
-
const kind = typeof item.kind === "string" ? normalizeKind(item.kind) : undefined;
|
|
168
|
-
const name = typeof metadata?.name === "string" ? metadata.name : undefined;
|
|
169
|
-
const description = typeof metadata?.description === "string" ? metadata.description : undefined;
|
|
170
|
-
if (!spec && !metadata) {
|
|
171
|
-
return kind ? { ...item, kind } : item;
|
|
172
|
-
}
|
|
173
|
-
if (!spec && metadata) {
|
|
174
|
-
return {
|
|
175
|
-
...item,
|
|
176
|
-
...(description ? { description } : {}),
|
|
177
|
-
...(name ? { id: name } : {}),
|
|
178
|
-
...(kind ? { kind } : {}),
|
|
179
|
-
};
|
|
180
|
-
}
|
|
181
|
-
return {
|
|
182
|
-
...(spec ?? {}),
|
|
183
|
-
...(description ? { description } : {}),
|
|
184
|
-
...(name ? { id: name } : {}),
|
|
185
|
-
...(kind ? { kind } : {}),
|
|
186
|
-
};
|
|
187
|
-
}
|
|
188
87
|
function readRefArray(items) {
|
|
189
88
|
return toArray(items)
|
|
190
89
|
.map((item) => typeof item === "string"
|
|
@@ -405,32 +304,6 @@ export function parseAgentItem(item, sourcePath) {
|
|
|
405
304
|
sourcePath,
|
|
406
305
|
};
|
|
407
306
|
}
|
|
408
|
-
async function objectItemsFromDocument(document, sourcePath) {
|
|
409
|
-
if (typeof document !== "object" || !document) {
|
|
410
|
-
return [];
|
|
411
|
-
}
|
|
412
|
-
const catalogKind = typeof document.kind === "string"
|
|
413
|
-
? String(document.kind)
|
|
414
|
-
: undefined;
|
|
415
|
-
const catalogItems = catalogKind === "Models"
|
|
416
|
-
? normalizeCatalogSpec(document, { defaultKind: "Model" })
|
|
417
|
-
: catalogKind === "Stores"
|
|
418
|
-
? normalizeCatalogSpec(document)
|
|
419
|
-
: catalogKind === "Backends"
|
|
420
|
-
? normalizeCatalogSpec(document, { defaultKind: "Backend" })
|
|
421
|
-
: catalogKind === "Tools"
|
|
422
|
-
? normalizeCatalogSpec(document, { defaultKind: "Tool" })
|
|
423
|
-
: catalogKind === "McpServers"
|
|
424
|
-
? normalizeCatalogSpec(document, { defaultKind: "McpServer" })
|
|
425
|
-
: [];
|
|
426
|
-
if (catalogItems.length > 0) {
|
|
427
|
-
return catalogItems;
|
|
428
|
-
}
|
|
429
|
-
if ("items" in document) {
|
|
430
|
-
throw new Error(`YAML document ${sourcePath} uses unsupported legacy items wrapper; use kind/spec catalog documents or metadata/spec objects instead`);
|
|
431
|
-
}
|
|
432
|
-
return [document];
|
|
433
|
-
}
|
|
434
307
|
function parseWorkspaceObject(item, sourcePath) {
|
|
435
308
|
if (typeof item.id !== "string") {
|
|
436
309
|
return null;
|
|
@@ -619,73 +492,6 @@ async function loadRootObjects(root, mergedObjects) {
|
|
|
619
492
|
mergeWorkspaceObjectRecord(mergedObjects, workspaceObject, item, sourcePath);
|
|
620
493
|
}
|
|
621
494
|
}
|
|
622
|
-
export async function readYamlItems(root, relativeDir, options = {}) {
|
|
623
|
-
const targetRoot = relativeDir ? path.join(root, relativeDir) : root;
|
|
624
|
-
if (!(await fileExists(targetRoot))) {
|
|
625
|
-
return [];
|
|
626
|
-
}
|
|
627
|
-
const files = options.recursive
|
|
628
|
-
? await listFilesRecursive(targetRoot, ".yaml")
|
|
629
|
-
: (await readdir(targetRoot, { withFileTypes: true }))
|
|
630
|
-
.filter((entry) => entry.isFile() && /\.ya?ml$/i.test(entry.name))
|
|
631
|
-
.map((entry) => path.join(targetRoot, entry.name))
|
|
632
|
-
.sort();
|
|
633
|
-
const records = [];
|
|
634
|
-
for (const filePath of files) {
|
|
635
|
-
const parsedDocuments = parseAllDocuments(await readYamlOrJson(filePath));
|
|
636
|
-
for (const parsedDocument of parsedDocuments) {
|
|
637
|
-
for (const item of await objectItemsFromDocument(parsedDocument.toJSON(), filePath)) {
|
|
638
|
-
records.push({ item: normalizeYamlItem(item), sourcePath: filePath });
|
|
639
|
-
}
|
|
640
|
-
}
|
|
641
|
-
}
|
|
642
|
-
return records;
|
|
643
|
-
}
|
|
644
|
-
async function readNamedYamlItems(root, filenames) {
|
|
645
|
-
const records = [];
|
|
646
|
-
for (const filename of filenames) {
|
|
647
|
-
const filePath = path.join(root, filename);
|
|
648
|
-
if (!(await fileExists(filePath))) {
|
|
649
|
-
continue;
|
|
650
|
-
}
|
|
651
|
-
const parsedDocuments = parseAllDocuments(await readYamlOrJson(filePath));
|
|
652
|
-
for (const parsedDocument of parsedDocuments) {
|
|
653
|
-
for (const item of await objectItemsFromDocument(parsedDocument.toJSON(), filePath)) {
|
|
654
|
-
records.push({ item: normalizeYamlItem(item), sourcePath: filePath });
|
|
655
|
-
}
|
|
656
|
-
}
|
|
657
|
-
}
|
|
658
|
-
return records;
|
|
659
|
-
}
|
|
660
|
-
async function readNamedModelItems(root) {
|
|
661
|
-
const filePaths = new Set();
|
|
662
|
-
for (const filename of MODEL_FILENAMES) {
|
|
663
|
-
const directPath = path.join(root, filename);
|
|
664
|
-
if (await fileExists(directPath)) {
|
|
665
|
-
filePaths.add(directPath);
|
|
666
|
-
}
|
|
667
|
-
}
|
|
668
|
-
for (const extension of [".yaml", ".yml"]) {
|
|
669
|
-
for (const filePath of await listFilesRecursive(root, extension)) {
|
|
670
|
-
if (MODEL_FILENAMES.includes(path.basename(filePath))) {
|
|
671
|
-
filePaths.add(filePath);
|
|
672
|
-
}
|
|
673
|
-
}
|
|
674
|
-
}
|
|
675
|
-
const records = [];
|
|
676
|
-
for (const filePath of [...filePaths].sort()) {
|
|
677
|
-
const parsedDocuments = parseAllDocuments(await readYamlOrJson(filePath));
|
|
678
|
-
for (const parsedDocument of parsedDocuments) {
|
|
679
|
-
for (const item of await objectItemsFromDocument(parsedDocument.toJSON(), filePath)) {
|
|
680
|
-
const normalized = normalizeYamlItem(item);
|
|
681
|
-
if (normalized.kind === "model" && typeof normalized.id === "string" && normalized.id.trim()) {
|
|
682
|
-
records.push({ item: normalized, sourcePath: filePath });
|
|
683
|
-
}
|
|
684
|
-
}
|
|
685
|
-
}
|
|
686
|
-
}
|
|
687
|
-
return records;
|
|
688
|
-
}
|
|
689
495
|
function isAgentKind(kind) {
|
|
690
496
|
return kind === "agent";
|
|
691
497
|
}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
export declare function normalizeYamlItem(item: Record<string, unknown>): Record<string, unknown>;
|
|
2
|
+
export declare function readYamlItems(root: string, relativeDir?: string, options?: {
|
|
3
|
+
recursive?: boolean;
|
|
4
|
+
}): Promise<Array<{
|
|
5
|
+
item: Record<string, unknown>;
|
|
6
|
+
sourcePath: string;
|
|
7
|
+
}>>;
|
|
8
|
+
export declare function readNamedYamlItems(root: string, filenames: string[]): Promise<Array<{
|
|
9
|
+
item: Record<string, unknown>;
|
|
10
|
+
sourcePath: string;
|
|
11
|
+
}>>;
|
|
12
|
+
export declare function readNamedModelItems(root: string): Promise<Array<{
|
|
13
|
+
item: Record<string, unknown>;
|
|
14
|
+
sourcePath: string;
|
|
15
|
+
}>>;
|
|
@@ -0,0 +1,202 @@
|
|
|
1
|
+
import path from "node:path";
|
|
2
|
+
import { readdir } from "node:fs/promises";
|
|
3
|
+
import { parseAllDocuments } from "yaml";
|
|
4
|
+
import { fileExists, listFilesRecursive, readYamlOrJson } from "../utils/fs.js";
|
|
5
|
+
const MODEL_FILENAMES = ["models.yaml", "models.yml"];
|
|
6
|
+
function asObject(value) {
|
|
7
|
+
return typeof value === "object" && value ? value : undefined;
|
|
8
|
+
}
|
|
9
|
+
function normalizeCatalogSpec(document, options = {}) {
|
|
10
|
+
const typed = asObject(document);
|
|
11
|
+
const spec = typed?.spec;
|
|
12
|
+
if (!Array.isArray(spec)) {
|
|
13
|
+
return [];
|
|
14
|
+
}
|
|
15
|
+
const normalized = spec
|
|
16
|
+
.filter((item) => typeof item === "object" && item !== null && !Array.isArray(item))
|
|
17
|
+
.map((item) => {
|
|
18
|
+
const id = typeof item.id === "string" && item.id.trim()
|
|
19
|
+
? item.id
|
|
20
|
+
: typeof item.name === "string" && item.name.trim()
|
|
21
|
+
? item.name
|
|
22
|
+
: undefined;
|
|
23
|
+
const itemKind = typeof item.kind === "string" && item.kind.trim()
|
|
24
|
+
? item.kind
|
|
25
|
+
: options.defaultKind;
|
|
26
|
+
if (!id || !itemKind) {
|
|
27
|
+
return null;
|
|
28
|
+
}
|
|
29
|
+
return {
|
|
30
|
+
...item,
|
|
31
|
+
kind: itemKind,
|
|
32
|
+
id,
|
|
33
|
+
};
|
|
34
|
+
});
|
|
35
|
+
return normalized.filter((item) => item !== null);
|
|
36
|
+
}
|
|
37
|
+
function normalizeKind(kind) {
|
|
38
|
+
switch (kind) {
|
|
39
|
+
case "Agent":
|
|
40
|
+
return "agent";
|
|
41
|
+
case "FileStore":
|
|
42
|
+
return "file-store";
|
|
43
|
+
case "InMemoryStore":
|
|
44
|
+
return "in-memory-store";
|
|
45
|
+
case "RedisStore":
|
|
46
|
+
return "redis-store";
|
|
47
|
+
case "PostgresStore":
|
|
48
|
+
return "postgres-store";
|
|
49
|
+
case "SqliteSaver":
|
|
50
|
+
return "sqlite-saver";
|
|
51
|
+
case "FileCheckpointer":
|
|
52
|
+
return "file-checkpointer";
|
|
53
|
+
case "Checkpointer":
|
|
54
|
+
return "checkpointer";
|
|
55
|
+
case "Model":
|
|
56
|
+
return "model";
|
|
57
|
+
case "EmbeddingModel":
|
|
58
|
+
return "embedding-model";
|
|
59
|
+
case "VectorStore":
|
|
60
|
+
return "vector-store";
|
|
61
|
+
case "Backend":
|
|
62
|
+
return "backend";
|
|
63
|
+
case "Store":
|
|
64
|
+
return "store";
|
|
65
|
+
case "Memory":
|
|
66
|
+
return "memory";
|
|
67
|
+
case "Tool":
|
|
68
|
+
return "tool";
|
|
69
|
+
case "Skill":
|
|
70
|
+
return "skill";
|
|
71
|
+
case "Runtime":
|
|
72
|
+
return "runtime";
|
|
73
|
+
case "RuntimeMemory":
|
|
74
|
+
return "runtime-memory";
|
|
75
|
+
case "Prompt":
|
|
76
|
+
return "prompt";
|
|
77
|
+
case "McpServer":
|
|
78
|
+
return "mcp";
|
|
79
|
+
default:
|
|
80
|
+
return kind;
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
export function normalizeYamlItem(item) {
|
|
84
|
+
if (item.kind === "DeepAgent" || item.kind === "LangChainAgent") {
|
|
85
|
+
throw new Error(`YAML object kind ${String(item.kind)} is no longer supported; use kind: Agent with spec.execution.backend instead`);
|
|
86
|
+
}
|
|
87
|
+
const metadata = asObject(item.metadata);
|
|
88
|
+
const spec = asObject(item.spec);
|
|
89
|
+
const kind = typeof item.kind === "string" ? normalizeKind(item.kind) : undefined;
|
|
90
|
+
const name = typeof metadata?.name === "string" ? metadata.name : undefined;
|
|
91
|
+
const description = typeof metadata?.description === "string" ? metadata.description : undefined;
|
|
92
|
+
if (!spec && !metadata) {
|
|
93
|
+
return kind ? { ...item, kind } : item;
|
|
94
|
+
}
|
|
95
|
+
if (!spec && metadata) {
|
|
96
|
+
return {
|
|
97
|
+
...item,
|
|
98
|
+
...(description ? { description } : {}),
|
|
99
|
+
...(name ? { id: name } : {}),
|
|
100
|
+
...(kind ? { kind } : {}),
|
|
101
|
+
};
|
|
102
|
+
}
|
|
103
|
+
return {
|
|
104
|
+
...(spec ?? {}),
|
|
105
|
+
...(description ? { description } : {}),
|
|
106
|
+
...(name ? { id: name } : {}),
|
|
107
|
+
...(kind ? { kind } : {}),
|
|
108
|
+
};
|
|
109
|
+
}
|
|
110
|
+
async function objectItemsFromDocument(document, sourcePath) {
|
|
111
|
+
if (typeof document !== "object" || !document) {
|
|
112
|
+
return [];
|
|
113
|
+
}
|
|
114
|
+
const catalogKind = typeof document.kind === "string"
|
|
115
|
+
? String(document.kind)
|
|
116
|
+
: undefined;
|
|
117
|
+
const catalogItems = catalogKind === "Models"
|
|
118
|
+
? normalizeCatalogSpec(document, { defaultKind: "Model" })
|
|
119
|
+
: catalogKind === "Stores"
|
|
120
|
+
? normalizeCatalogSpec(document)
|
|
121
|
+
: catalogKind === "Backends"
|
|
122
|
+
? normalizeCatalogSpec(document, { defaultKind: "Backend" })
|
|
123
|
+
: catalogKind === "Tools"
|
|
124
|
+
? normalizeCatalogSpec(document, { defaultKind: "Tool" })
|
|
125
|
+
: catalogKind === "McpServers"
|
|
126
|
+
? normalizeCatalogSpec(document, { defaultKind: "McpServer" })
|
|
127
|
+
: [];
|
|
128
|
+
if (catalogItems.length > 0) {
|
|
129
|
+
return catalogItems;
|
|
130
|
+
}
|
|
131
|
+
if ("items" in document) {
|
|
132
|
+
throw new Error(`YAML document ${sourcePath} uses unsupported legacy items wrapper; use kind/spec catalog documents or metadata/spec objects instead`);
|
|
133
|
+
}
|
|
134
|
+
return [document];
|
|
135
|
+
}
|
|
136
|
+
export async function readYamlItems(root, relativeDir, options = {}) {
|
|
137
|
+
const targetRoot = relativeDir ? path.join(root, relativeDir) : root;
|
|
138
|
+
if (!(await fileExists(targetRoot))) {
|
|
139
|
+
return [];
|
|
140
|
+
}
|
|
141
|
+
const files = options.recursive
|
|
142
|
+
? await listFilesRecursive(targetRoot, ".yaml")
|
|
143
|
+
: (await readdir(targetRoot, { withFileTypes: true }))
|
|
144
|
+
.filter((entry) => entry.isFile() && /\.ya?ml$/i.test(entry.name))
|
|
145
|
+
.map((entry) => path.join(targetRoot, entry.name))
|
|
146
|
+
.sort();
|
|
147
|
+
const records = [];
|
|
148
|
+
for (const filePath of files) {
|
|
149
|
+
const parsedDocuments = parseAllDocuments(await readYamlOrJson(filePath));
|
|
150
|
+
for (const parsedDocument of parsedDocuments) {
|
|
151
|
+
for (const item of await objectItemsFromDocument(parsedDocument.toJSON(), filePath)) {
|
|
152
|
+
records.push({ item: normalizeYamlItem(item), sourcePath: filePath });
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
}
|
|
156
|
+
return records;
|
|
157
|
+
}
|
|
158
|
+
export async function readNamedYamlItems(root, filenames) {
|
|
159
|
+
const records = [];
|
|
160
|
+
for (const filename of filenames) {
|
|
161
|
+
const filePath = path.join(root, filename);
|
|
162
|
+
if (!(await fileExists(filePath))) {
|
|
163
|
+
continue;
|
|
164
|
+
}
|
|
165
|
+
const parsedDocuments = parseAllDocuments(await readYamlOrJson(filePath));
|
|
166
|
+
for (const parsedDocument of parsedDocuments) {
|
|
167
|
+
for (const item of await objectItemsFromDocument(parsedDocument.toJSON(), filePath)) {
|
|
168
|
+
records.push({ item: normalizeYamlItem(item), sourcePath: filePath });
|
|
169
|
+
}
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
return records;
|
|
173
|
+
}
|
|
174
|
+
export async function readNamedModelItems(root) {
|
|
175
|
+
const filePaths = new Set();
|
|
176
|
+
for (const filename of MODEL_FILENAMES) {
|
|
177
|
+
const directPath = path.join(root, filename);
|
|
178
|
+
if (await fileExists(directPath)) {
|
|
179
|
+
filePaths.add(directPath);
|
|
180
|
+
}
|
|
181
|
+
}
|
|
182
|
+
for (const extension of [".yaml", ".yml"]) {
|
|
183
|
+
for (const filePath of await listFilesRecursive(root, extension)) {
|
|
184
|
+
if (MODEL_FILENAMES.includes(path.basename(filePath))) {
|
|
185
|
+
filePaths.add(filePath);
|
|
186
|
+
}
|
|
187
|
+
}
|
|
188
|
+
}
|
|
189
|
+
const records = [];
|
|
190
|
+
for (const filePath of [...filePaths].sort()) {
|
|
191
|
+
const parsedDocuments = parseAllDocuments(await readYamlOrJson(filePath));
|
|
192
|
+
for (const parsedDocument of parsedDocuments) {
|
|
193
|
+
for (const item of await objectItemsFromDocument(parsedDocument.toJSON(), filePath)) {
|
|
194
|
+
const normalized = normalizeYamlItem(item);
|
|
195
|
+
if (normalized.kind === "model" && typeof normalized.id === "string" && normalized.id.trim()) {
|
|
196
|
+
records.push({ item: normalized, sourcePath: filePath });
|
|
197
|
+
}
|
|
198
|
+
}
|
|
199
|
+
}
|
|
200
|
+
}
|
|
201
|
+
return records;
|
|
202
|
+
}
|