@finalai/agent-definition 0.1.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.
Potentially problematic release.
This version of @finalai/agent-definition might be problematic. Click here for more details.
- package/README.md +16 -0
- package/THIRD_PARTY_NOTICES.md +303 -0
- package/dist/compiler-assets/chunk-2CZRHOLL.ts +10 -0
- package/dist/compiler-assets/chunk-32O3ODZE.ts +39 -0
- package/dist/compiler-assets/chunk-5BK6FVRE.ts +75 -0
- package/dist/compiler-assets/chunk-6WR3PGNF.ts +0 -0
- package/dist/compiler-assets/chunk-7QP2CKPI.ts +30 -0
- package/dist/compiler-assets/chunk-7VSSVZM4.ts +55 -0
- package/dist/compiler-assets/chunk-7WGYG73V.ts +42 -0
- package/dist/compiler-assets/chunk-BLB6JGLO.ts +481 -0
- package/dist/compiler-assets/chunk-CWWRTRWW.ts +76 -0
- package/dist/compiler-assets/chunk-EVQIK62B.ts +188 -0
- package/dist/compiler-assets/chunk-GNR7XBPN.ts +3364 -0
- package/dist/compiler-assets/chunk-GTUZOATD.ts +10 -0
- package/dist/compiler-assets/chunk-HFS4KLEL.ts +10 -0
- package/dist/compiler-assets/chunk-HGW4YHAY.ts +6865 -0
- package/dist/compiler-assets/chunk-HNPUTP35.ts +172 -0
- package/dist/compiler-assets/chunk-JIPNTA56.ts +59 -0
- package/dist/compiler-assets/chunk-JNJE72EH.ts +10 -0
- package/dist/compiler-assets/chunk-JPY4L2UJ.ts +349 -0
- package/dist/compiler-assets/chunk-JTGTLYDT.ts +0 -0
- package/dist/compiler-assets/chunk-LUSAAV4L.ts +33 -0
- package/dist/compiler-assets/chunk-MZMSKIKU.ts +472 -0
- package/dist/compiler-assets/chunk-NMYHO2QN.ts +25 -0
- package/dist/compiler-assets/chunk-NYTOYKKF.ts +28 -0
- package/dist/compiler-assets/chunk-OWC6SFFF.ts +295 -0
- package/dist/compiler-assets/chunk-QMKWAFVZ.ts +59 -0
- package/dist/compiler-assets/chunk-QMWTDPNT.ts +79 -0
- package/dist/compiler-assets/chunk-RWUIMTBI.ts +13 -0
- package/dist/compiler-assets/chunk-SKTNMUO7.ts +64 -0
- package/dist/compiler-assets/chunk-T6WG4L4M.ts +19 -0
- package/dist/compiler-assets/chunk-TATN3PYK.ts +81 -0
- package/dist/compiler-assets/chunk-VHXHUU7L.ts +16 -0
- package/dist/compiler-assets/chunk-WMXMVFHM.ts +121 -0
- package/dist/compiler-assets/chunk-XHKPWT3G.ts +55 -0
- package/dist/compiler-assets/chunk-ZDLVA6XF.ts +476 -0
- package/dist/compiler-assets/src/authoring/agent.ts +10 -0
- package/dist/compiler-assets/src/authoring/approval.ts +19 -0
- package/dist/compiler-assets/src/authoring/brand.ts +23 -0
- package/dist/compiler-assets/src/authoring/channels.ts +26 -0
- package/dist/compiler-assets/src/authoring/connections.ts +10 -0
- package/dist/compiler-assets/src/authoring/context.ts +7 -0
- package/dist/compiler-assets/src/authoring/credentials.ts +21 -0
- package/dist/compiler-assets/src/authoring/dynamic.ts +10 -0
- package/dist/compiler-assets/src/authoring/harness.ts +17 -0
- package/dist/compiler-assets/src/authoring/hooks.ts +28 -0
- package/dist/compiler-assets/src/authoring/index.ts +110 -0
- package/dist/compiler-assets/src/authoring/instructions.ts +14 -0
- package/dist/compiler-assets/src/authoring/sandbox.ts +25 -0
- package/dist/compiler-assets/src/authoring/schedules.ts +10 -0
- package/dist/compiler-assets/src/authoring/skills.ts +10 -0
- package/dist/compiler-assets/src/authoring/tools.ts +23 -0
- package/dist/compiler-assets/src/compatibility.ts +14810 -0
- package/dist/compiler-assets/src/compiler/evaluate-child.mjs +77 -0
- package/dist/compiler-assets/src/index.ts +195 -0
- package/dist/compiler-assets/src/manifest.ts +72 -0
- package/dist/compiler-assets/src/resolve.ts +19 -0
- package/dist/compiler-assets/src/runtime/bundle.ts +72 -0
- package/dist/compiler-assets/src/runtime/describe.ts +31 -0
- package/dist/compiler-assets/src/runtime/described.ts +142 -0
- package/dist/compiler-assets/src/runtime/isolate.ts +28 -0
- package/dist/compiler-assets/src/runtime/layout.ts +15 -0
- package/dist/compiler-assets/src/runtime/lower.ts +52 -0
- package/dist/compiler-assets/src/runtime/schema-validation.ts +21 -0
- package/dist/compiler-assets/src/runtime/values.ts +38 -0
- package/dist/modules/authoring/agent.d.mts +22 -0
- package/dist/modules/authoring/agent.mjs +6 -0
- package/dist/modules/authoring/agent.mjs.map +7 -0
- package/dist/modules/authoring/approval.d.mts +17 -0
- package/dist/modules/authoring/approval.mjs +42 -0
- package/dist/modules/authoring/approval.mjs.map +7 -0
- package/dist/modules/authoring/brand.d.mts +27 -0
- package/dist/modules/authoring/brand.mjs +51 -0
- package/dist/modules/authoring/brand.mjs.map +7 -0
- package/dist/modules/authoring/channels.d.mts +41 -0
- package/dist/modules/authoring/channels.mjs +65 -0
- package/dist/modules/authoring/channels.mjs.map +7 -0
- package/dist/modules/authoring/connections.d.mts +23 -0
- package/dist/modules/authoring/connections.mjs +6 -0
- package/dist/modules/authoring/connections.mjs.map +7 -0
- package/dist/modules/authoring/context.d.mts +83 -0
- package/dist/modules/authoring/context.mjs +12 -0
- package/dist/modules/authoring/context.mjs.map +7 -0
- package/dist/modules/authoring/credentials.d.mts +10 -0
- package/dist/modules/authoring/credentials.mjs +31 -0
- package/dist/modules/authoring/credentials.mjs.map +7 -0
- package/dist/modules/authoring/dynamic.d.mts +30 -0
- package/dist/modules/authoring/dynamic.mjs +15 -0
- package/dist/modules/authoring/dynamic.mjs.map +7 -0
- package/dist/modules/authoring/harness.d.mts +85 -0
- package/dist/modules/authoring/harness.mjs +55 -0
- package/dist/modules/authoring/harness.mjs.map +7 -0
- package/dist/modules/authoring/hooks.d.mts +120 -0
- package/dist/modules/authoring/hooks.mjs +72 -0
- package/dist/modules/authoring/hooks.mjs.map +7 -0
- package/dist/modules/authoring/index.d.mts +27 -0
- package/dist/modules/authoring/index.mjs +63 -0
- package/dist/modules/authoring/index.mjs.map +7 -0
- package/dist/modules/authoring/instructions.d.mts +13 -0
- package/dist/modules/authoring/instructions.mjs +15 -0
- package/dist/modules/authoring/instructions.mjs.map +7 -0
- package/dist/modules/authoring/sandbox.d.mts +21 -0
- package/dist/modules/authoring/sandbox.mjs +13 -0
- package/dist/modules/authoring/sandbox.mjs.map +7 -0
- package/dist/modules/authoring/schedules.d.mts +8 -0
- package/dist/modules/authoring/schedules.mjs +6 -0
- package/dist/modules/authoring/schedules.mjs.map +7 -0
- package/dist/modules/authoring/skills.d.mts +8 -0
- package/dist/modules/authoring/skills.mjs +6 -0
- package/dist/modules/authoring/skills.mjs.map +7 -0
- package/dist/modules/authoring/tools.d.mts +80 -0
- package/dist/modules/authoring/tools.mjs +70 -0
- package/dist/modules/authoring/tools.mjs.map +7 -0
- package/dist/modules/compatibility.d.mts +36 -0
- package/dist/modules/compatibility.mjs +536 -0
- package/dist/modules/compatibility.mjs.map +7 -0
- package/dist/modules/compiler/assemble.d.mts +30 -0
- package/dist/modules/compiler/assemble.mjs +923 -0
- package/dist/modules/compiler/assemble.mjs.map +7 -0
- package/dist/modules/compiler/bundle.d.mts +22 -0
- package/dist/modules/compiler/bundle.mjs +385 -0
- package/dist/modules/compiler/bundle.mjs.map +7 -0
- package/dist/modules/compiler/diagnostics.d.mts +40 -0
- package/dist/modules/compiler/diagnostics.mjs +38 -0
- package/dist/modules/compiler/diagnostics.mjs.map +7 -0
- package/dist/modules/compiler/discovery.d.mts +36 -0
- package/dist/modules/compiler/discovery.mjs +158 -0
- package/dist/modules/compiler/discovery.mjs.map +7 -0
- package/dist/modules/compiler/evaluate.d.mts +13 -0
- package/dist/modules/compiler/evaluate.mjs +194 -0
- package/dist/modules/compiler/evaluate.mjs.map +7 -0
- package/dist/modules/compiler/files.d.mts +19 -0
- package/dist/modules/compiler/files.mjs +90 -0
- package/dist/modules/compiler/files.mjs.map +7 -0
- package/dist/modules/compiler/frontmatter.d.mts +9 -0
- package/dist/modules/compiler/frontmatter.mjs +34 -0
- package/dist/modules/compiler/frontmatter.mjs.map +7 -0
- package/dist/modules/compiler/index.d.mts +49 -0
- package/dist/modules/compiler/index.mjs +244 -0
- package/dist/modules/compiler/index.mjs.map +7 -0
- package/dist/modules/compiler/load.d.mts +8 -0
- package/dist/modules/compiler/load.mjs +45 -0
- package/dist/modules/compiler/load.mjs.map +7 -0
- package/dist/modules/compiler/local-isolate.d.mts +20 -0
- package/dist/modules/compiler/local-isolate.mjs +93 -0
- package/dist/modules/compiler/local-isolate.mjs.map +7 -0
- package/dist/modules/compiler/packages.d.mts +66 -0
- package/dist/modules/compiler/packages.mjs +307 -0
- package/dist/modules/compiler/packages.mjs.map +7 -0
- package/dist/modules/index.d.mts +7 -0
- package/dist/modules/index.mjs +25 -0
- package/dist/modules/index.mjs.map +7 -0
- package/dist/modules/manifest.d.mts +2 -0
- package/dist/modules/manifest.mjs +67 -0
- package/dist/modules/manifest.mjs.map +7 -0
- package/dist/modules/resolve.d.mts +24 -0
- package/dist/modules/resolve.mjs +176 -0
- package/dist/modules/resolve.mjs.map +7 -0
- package/dist/modules/runtime/bundle.d.mts +12 -0
- package/dist/modules/runtime/bundle.mjs +48 -0
- package/dist/modules/runtime/bundle.mjs.map +7 -0
- package/dist/modules/runtime/describe.d.mts +19 -0
- package/dist/modules/runtime/describe.mjs +471 -0
- package/dist/modules/runtime/describe.mjs.map +7 -0
- package/dist/modules/runtime/described.d.mts +376 -0
- package/dist/modules/runtime/described.mjs +116 -0
- package/dist/modules/runtime/described.mjs.map +7 -0
- package/dist/modules/runtime/isolate.d.mts +70 -0
- package/dist/modules/runtime/isolate.mjs +454 -0
- package/dist/modules/runtime/isolate.mjs.map +7 -0
- package/dist/modules/runtime/layout.d.mts +21 -0
- package/dist/modules/runtime/layout.mjs +24 -0
- package/dist/modules/runtime/layout.mjs.map +7 -0
- package/dist/modules/runtime/lower.d.mts +73 -0
- package/dist/modules/runtime/lower.mjs +463 -0
- package/dist/modules/runtime/lower.mjs.map +7 -0
- package/dist/modules/runtime/schema-validation.d.mts +21 -0
- package/dist/modules/runtime/schema-validation.mjs +238 -0
- package/dist/modules/runtime/schema-validation.mjs.map +7 -0
- package/dist/modules/runtime/values.d.mts +20 -0
- package/dist/modules/runtime/values.mjs +48 -0
- package/dist/modules/runtime/values.mjs.map +7 -0
- package/fixtures/acme-fleet/agent/agent.ts +74 -0
- package/fixtures/acme-fleet/agent/instructions.md +1 -0
- package/fixtures/assistant/agent/agent.ts +16 -0
- package/fixtures/assistant/agent/instructions.md +1 -0
- package/fixtures/assistant/agent/tools/current_time.ts +9 -0
- package/fixtures/assistant-with-tools/agent/agent.ts +16 -0
- package/fixtures/assistant-with-tools/agent/instructions.md +1 -0
- package/fixtures/assistant-with-tools/agent/tools/current_time.ts +9 -0
- package/fixtures/final-connection/agent/agent.ts +15 -0
- package/fixtures/final-connection/agent/connections/final.ts +9 -0
- package/fixtures/release-scout/agent/agent.ts +22 -0
- package/fixtures/release-scout/agent/channels/github-signature.ts +27 -0
- package/fixtures/release-scout/agent/channels/github.ts +38 -0
- package/fixtures/release-scout/agent/connections/linear.ts +9 -0
- package/fixtures/release-scout/agent/hooks/audit.ts +24 -0
- package/fixtures/release-scout/agent/instructions/org-context.ts +26 -0
- package/fixtures/release-scout/agent/instructions.md +2 -0
- package/fixtures/release-scout/agent/sandbox.ts +20 -0
- package/fixtures/release-scout/agent/schedules/daily-digest.md +7 -0
- package/fixtures/release-scout/agent/skills/triage/SKILL.md +8 -0
- package/fixtures/release-scout/agent/skills/triage/checklist.md +3 -0
- package/fixtures/release-scout/agent/tools/lookup_release_notes.ts +24 -0
- package/fixtures/tsconfig.json +5 -0
- package/package.json +94 -0
|
@@ -0,0 +1,238 @@
|
|
|
1
|
+
import {
|
|
2
|
+
jsonObjectSchema,
|
|
3
|
+
jsonValueSchema
|
|
4
|
+
} from "@finalai/agent-provider";
|
|
5
|
+
import { compileSchema, isSchemaNode } from "json-schema-library";
|
|
6
|
+
import { remotes } from "json-schema-library/remotes";
|
|
7
|
+
import * as z from "zod";
|
|
8
|
+
import { callableSchema, fieldOf } from "./values.mjs";
|
|
9
|
+
var SchemaIo = /* @__PURE__ */ ((SchemaIo2) => {
|
|
10
|
+
SchemaIo2["Input"] = "input";
|
|
11
|
+
SchemaIo2["Output"] = "output";
|
|
12
|
+
return SchemaIo2;
|
|
13
|
+
})(SchemaIo || {});
|
|
14
|
+
const dialects = /* @__PURE__ */ new Set([
|
|
15
|
+
"https://json-schema.org/draft/2020-12/schema",
|
|
16
|
+
"https://json-schema.org/draft/2019-09/schema",
|
|
17
|
+
"http://json-schema.org/draft-07/schema#",
|
|
18
|
+
"https://json-schema.org/draft-07/schema#",
|
|
19
|
+
"http://json-schema.org/draft-06/schema#",
|
|
20
|
+
"https://json-schema.org/draft-06/schema#",
|
|
21
|
+
"http://json-schema.org/draft-04/schema#",
|
|
22
|
+
"https://json-schema.org/draft-04/schema#"
|
|
23
|
+
]);
|
|
24
|
+
const vocabularies = /* @__PURE__ */ new Set([
|
|
25
|
+
"https://json-schema.org/draft/2020-12/vocab/core",
|
|
26
|
+
"https://json-schema.org/draft/2020-12/vocab/applicator",
|
|
27
|
+
"https://json-schema.org/draft/2020-12/vocab/validation",
|
|
28
|
+
"https://json-schema.org/draft/2020-12/vocab/unevaluated",
|
|
29
|
+
"https://json-schema.org/draft/2020-12/vocab/meta-data",
|
|
30
|
+
"https://json-schema.org/draft/2020-12/vocab/format-annotation",
|
|
31
|
+
"https://json-schema.org/draft/2020-12/vocab/format-assertion",
|
|
32
|
+
"https://json-schema.org/draft/2020-12/vocab/content",
|
|
33
|
+
"https://json-schema.org/draft/2019-09/vocab/core",
|
|
34
|
+
"https://json-schema.org/draft/2019-09/vocab/applicator",
|
|
35
|
+
"https://json-schema.org/draft/2019-09/vocab/validation",
|
|
36
|
+
"https://json-schema.org/draft/2019-09/vocab/meta-data",
|
|
37
|
+
"https://json-schema.org/draft/2019-09/vocab/format",
|
|
38
|
+
"https://json-schema.org/draft/2019-09/vocab/content"
|
|
39
|
+
]);
|
|
40
|
+
const declarationSchema = z.looseObject({
|
|
41
|
+
$schema: z.string().optional(),
|
|
42
|
+
$vocabulary: z.record(z.string(), z.boolean()).optional()
|
|
43
|
+
});
|
|
44
|
+
const checkDialect = (value) => {
|
|
45
|
+
if (z.boolean().safeParse(value).success) return;
|
|
46
|
+
const schema = declarationSchema.parse(value);
|
|
47
|
+
if (schema.$schema != null && !dialects.has(schema.$schema))
|
|
48
|
+
throw new Error(`Unsupported JSON Schema dialect ${schema.$schema}`);
|
|
49
|
+
for (const [name, required] of Object.entries(schema.$vocabulary ?? {})) {
|
|
50
|
+
if (required && !vocabularies.has(name))
|
|
51
|
+
throw new Error(`Unsupported required JSON Schema vocabulary ${name}`);
|
|
52
|
+
}
|
|
53
|
+
};
|
|
54
|
+
const dialectByVersion = {
|
|
55
|
+
"draft-04": "http://json-schema.org/draft-04/schema#",
|
|
56
|
+
"draft-06": "http://json-schema.org/draft-06/schema#",
|
|
57
|
+
"draft-07": "http://json-schema.org/draft-07/schema#",
|
|
58
|
+
"draft-2019-09": "https://json-schema.org/draft/2019-09/schema",
|
|
59
|
+
"draft-2020-12": "https://json-schema.org/draft/2020-12/schema"
|
|
60
|
+
};
|
|
61
|
+
let metaRoot = null;
|
|
62
|
+
const metaSchemas = () => {
|
|
63
|
+
if (metaRoot != null) return metaRoot;
|
|
64
|
+
const schemas = z.array(jsonObjectSchema).parse(remotes).map((schema) => {
|
|
65
|
+
const identity = z.string().parse(schema.$id ?? schema.id).replace(/#$/, "");
|
|
66
|
+
const remote = { ...schema, $id: identity };
|
|
67
|
+
if (schema.id != null) remote["id"] = identity;
|
|
68
|
+
return remote;
|
|
69
|
+
});
|
|
70
|
+
metaRoot = compileSchema(
|
|
71
|
+
{},
|
|
72
|
+
{ remotes: schemas, formatAssertion: true, throwOnInvalidRef: true }
|
|
73
|
+
);
|
|
74
|
+
return metaRoot;
|
|
75
|
+
};
|
|
76
|
+
const schemaKeywords = /* @__PURE__ */ new Set([
|
|
77
|
+
"additionalItems",
|
|
78
|
+
"additionalProperties",
|
|
79
|
+
"contains",
|
|
80
|
+
"propertyNames",
|
|
81
|
+
"unevaluatedItems",
|
|
82
|
+
"unevaluatedProperties",
|
|
83
|
+
"not",
|
|
84
|
+
"if",
|
|
85
|
+
"then",
|
|
86
|
+
"else"
|
|
87
|
+
]);
|
|
88
|
+
const schemaMaps = /* @__PURE__ */ new Set([
|
|
89
|
+
"properties",
|
|
90
|
+
"patternProperties",
|
|
91
|
+
"$defs",
|
|
92
|
+
"definitions",
|
|
93
|
+
"dependentSchemas",
|
|
94
|
+
"dependencies"
|
|
95
|
+
]);
|
|
96
|
+
const schemaArrays = /* @__PURE__ */ new Set(["allOf", "anyOf", "oneOf", "prefixItems"]);
|
|
97
|
+
const childPlaceholder = (value) => jsonObjectSchema.safeParse(value).success ? {} : value;
|
|
98
|
+
const shallowDeclaration = (schema) => Object.fromEntries(
|
|
99
|
+
Object.entries(schema).map(([key, value]) => {
|
|
100
|
+
if (schemaKeywords.has(key)) return [key, childPlaceholder(value)];
|
|
101
|
+
if ((schemaArrays.has(key) || key === "items") && Array.isArray(value))
|
|
102
|
+
return [key, value.map(childPlaceholder)];
|
|
103
|
+
if (key === "items") return [key, childPlaceholder(value)];
|
|
104
|
+
const object = jsonObjectSchema.safeParse(value);
|
|
105
|
+
if (schemaMaps.has(key) && object.success)
|
|
106
|
+
return [
|
|
107
|
+
key,
|
|
108
|
+
Object.fromEntries(
|
|
109
|
+
Object.entries(object.data).map(([name, child]) => [name, childPlaceholder(child)])
|
|
110
|
+
)
|
|
111
|
+
];
|
|
112
|
+
return [key, value];
|
|
113
|
+
})
|
|
114
|
+
);
|
|
115
|
+
const checkDeclaration = (node) => {
|
|
116
|
+
if (z.boolean().safeParse(node.schema).success) return;
|
|
117
|
+
const schema = jsonObjectSchema.parse(node.schema);
|
|
118
|
+
checkDialect(schema);
|
|
119
|
+
const dialect = Object.entries(dialectByVersion).find(
|
|
120
|
+
([version]) => version === node.context.version
|
|
121
|
+
)?.[1];
|
|
122
|
+
if (dialect == null) throw new Error(`Unsupported JSON Schema version ${node.context.version}`);
|
|
123
|
+
const meta = metaSchemas().getNodeRef(dialect);
|
|
124
|
+
if (!isSchemaNode(meta)) throw new Error(`Missing JSON Schema metaschema ${dialect}`);
|
|
125
|
+
const result = meta.validate(shallowDeclaration(schema));
|
|
126
|
+
if (!result.valid) throw new Error(result.errors.map((issue) => issue.message).join("; "));
|
|
127
|
+
};
|
|
128
|
+
const canonicalJson = (value) => {
|
|
129
|
+
if (Array.isArray(value)) return value.map(canonicalJson);
|
|
130
|
+
const object = jsonObjectSchema.safeParse(value);
|
|
131
|
+
if (!object.success) return value;
|
|
132
|
+
return Object.fromEntries(
|
|
133
|
+
Object.entries(object.data).sort(([left], [right]) => left.localeCompare(right)).map(([key, item]) => [key, canonicalJson(item)])
|
|
134
|
+
);
|
|
135
|
+
};
|
|
136
|
+
const validatorFor = (schema) => {
|
|
137
|
+
const text = JSON.stringify(schema);
|
|
138
|
+
if (text == null) throw new Error("Expected a JSON Schema object");
|
|
139
|
+
const parsed = jsonObjectSchema.parse(canonicalJson(jsonObjectSchema.parse(JSON.parse(text))));
|
|
140
|
+
checkDialect(parsed);
|
|
141
|
+
const node = compileSchema(parsed, { formatAssertion: true, throwOnInvalidRef: true });
|
|
142
|
+
if (node.schemaErrors != null && node.schemaErrors.length > 0)
|
|
143
|
+
throw new Error(node.schemaErrors.map((issue) => issue.message).join("; "));
|
|
144
|
+
const nodes = /* @__PURE__ */ new Set([node, ...Object.values(node.context.refs)]);
|
|
145
|
+
for (const child of nodes) {
|
|
146
|
+
checkDeclaration(child);
|
|
147
|
+
const ref = fieldOf(child.schema, "$ref") ?? fieldOf(child.schema, "$dynamicRef") ?? fieldOf(child.schema, "$recursiveRef");
|
|
148
|
+
if (ref == null) continue;
|
|
149
|
+
const resolved = child.resolveRef();
|
|
150
|
+
if (!isSchemaNode(resolved))
|
|
151
|
+
throw new Error(`Unresolved JSON Schema reference ${String(ref)} at ${child.schemaLocation}`);
|
|
152
|
+
}
|
|
153
|
+
return node;
|
|
154
|
+
};
|
|
155
|
+
const jsonSchemaError = (schema, value) => {
|
|
156
|
+
const validator = validatorFor(schema);
|
|
157
|
+
const parsed = jsonValueSchema.safeParse(value);
|
|
158
|
+
if (!parsed.success) return "Expected a JSON-compatible value";
|
|
159
|
+
const result = validator.validate(canonicalJson(parsed.data));
|
|
160
|
+
return result.valid ? null : result.errors.map((issue) => issue.message).join("; ");
|
|
161
|
+
};
|
|
162
|
+
const jsonSchemaDeclarationError = (schema) => {
|
|
163
|
+
try {
|
|
164
|
+
validatorFor(schema);
|
|
165
|
+
return null;
|
|
166
|
+
} catch (cause) {
|
|
167
|
+
return cause instanceof Error ? cause.message : String(cause);
|
|
168
|
+
}
|
|
169
|
+
};
|
|
170
|
+
const standardValidatorSchema = z.looseObject({
|
|
171
|
+
"~standard": z.looseObject({
|
|
172
|
+
version: z.literal(1),
|
|
173
|
+
vendor: z.string(),
|
|
174
|
+
validate: callableSchema
|
|
175
|
+
})
|
|
176
|
+
});
|
|
177
|
+
const validationResultSchema = z.looseObject({
|
|
178
|
+
value: z.unknown().optional(),
|
|
179
|
+
issues: z.array(z.looseObject({ message: z.string().optional() })).optional()
|
|
180
|
+
});
|
|
181
|
+
const validateSchemaValue = async (args) => {
|
|
182
|
+
if (args.schema == null) return args.value;
|
|
183
|
+
const standard = standardValidatorSchema.safeParse(args.schema);
|
|
184
|
+
if (standard.success) {
|
|
185
|
+
if (standard.data["~standard"].vendor === "zod") {
|
|
186
|
+
const parser = callableSchema.safeParse(fieldOf(args.schema, "safeParseAsync"));
|
|
187
|
+
if (parser.success) {
|
|
188
|
+
const result2 = z.looseObject({
|
|
189
|
+
success: z.boolean(),
|
|
190
|
+
data: z.unknown().optional(),
|
|
191
|
+
error: z.looseObject({ issues: z.array(z.object({ message: z.string() })) }).optional()
|
|
192
|
+
}).parse(await parser.data.call(args.schema, args.value));
|
|
193
|
+
if (!result2.success)
|
|
194
|
+
throw new Error(
|
|
195
|
+
`Invalid ${args.what}: ${result2.error?.issues.map((issue) => issue.message).join("; ") ?? "invalid"}`
|
|
196
|
+
);
|
|
197
|
+
return result2.data;
|
|
198
|
+
}
|
|
199
|
+
}
|
|
200
|
+
const raw = await standard.data["~standard"].validate.call(
|
|
201
|
+
fieldOf(args.schema, "~standard"),
|
|
202
|
+
args.value
|
|
203
|
+
);
|
|
204
|
+
const result = validationResultSchema.parse(raw);
|
|
205
|
+
if (result.issues != null)
|
|
206
|
+
throw new Error(
|
|
207
|
+
`Invalid ${args.what}: ${result.issues.map((issue) => issue.message ?? "invalid").join("; ") || "invalid"}`
|
|
208
|
+
);
|
|
209
|
+
if (!Object.hasOwn(result, "value"))
|
|
210
|
+
throw new Error(`Invalid ${args.what}: schema validator returned no value`);
|
|
211
|
+
return result.value;
|
|
212
|
+
}
|
|
213
|
+
const error = jsonSchemaError(args.schema, args.value);
|
|
214
|
+
if (error != null) throw new Error(`Invalid ${args.what}: ${error}`);
|
|
215
|
+
return args.value;
|
|
216
|
+
};
|
|
217
|
+
const resultMatchesSchema = (schema, value) => {
|
|
218
|
+
if (schema == null) return true;
|
|
219
|
+
try {
|
|
220
|
+
const standard = standardValidatorSchema.safeParse(schema);
|
|
221
|
+
if (!standard.success) return jsonSchemaError(schema, value) == null;
|
|
222
|
+
const jsonSchemas = fieldOf(fieldOf(schema, "~standard"), "jsonSchema");
|
|
223
|
+
const converter = callableSchema.safeParse(fieldOf(jsonSchemas, "output" /* Output */));
|
|
224
|
+
if (!converter.success) return false;
|
|
225
|
+
return jsonSchemaError(converter.data.call(jsonSchemas, { target: "draft-2020-12" }), value) == null;
|
|
226
|
+
} catch {
|
|
227
|
+
return false;
|
|
228
|
+
}
|
|
229
|
+
};
|
|
230
|
+
export {
|
|
231
|
+
SchemaIo,
|
|
232
|
+
jsonSchemaDeclarationError,
|
|
233
|
+
jsonSchemaError,
|
|
234
|
+
resultMatchesSchema,
|
|
235
|
+
standardValidatorSchema,
|
|
236
|
+
validateSchemaValue
|
|
237
|
+
};
|
|
238
|
+
//# sourceMappingURL=schema-validation.mjs.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../../../src/runtime/schema-validation.ts"],
|
|
4
|
+
"sourcesContent": ["import {\n jsonObjectSchema,\n jsonValueSchema,\n type JsonObject,\n type JsonValue,\n} from '@finalai/agent-provider';\nimport { compileSchema, isSchemaNode, type SchemaNode } from 'json-schema-library';\nimport { remotes } from 'json-schema-library/remotes';\nimport * as z from 'zod';\nimport { callableSchema, fieldOf, type AuthoredValue } from \"./values.mjs\";\n\nexport enum SchemaIo {\n Input = 'input',\n Output = 'output',\n}\n\nconst dialects = new Set([\n 'https://json-schema.org/draft/2020-12/schema',\n 'https://json-schema.org/draft/2019-09/schema',\n 'http://json-schema.org/draft-07/schema#',\n 'https://json-schema.org/draft-07/schema#',\n 'http://json-schema.org/draft-06/schema#',\n 'https://json-schema.org/draft-06/schema#',\n 'http://json-schema.org/draft-04/schema#',\n 'https://json-schema.org/draft-04/schema#',\n]);\nconst vocabularies = new Set([\n 'https://json-schema.org/draft/2020-12/vocab/core',\n 'https://json-schema.org/draft/2020-12/vocab/applicator',\n 'https://json-schema.org/draft/2020-12/vocab/validation',\n 'https://json-schema.org/draft/2020-12/vocab/unevaluated',\n 'https://json-schema.org/draft/2020-12/vocab/meta-data',\n 'https://json-schema.org/draft/2020-12/vocab/format-annotation',\n 'https://json-schema.org/draft/2020-12/vocab/format-assertion',\n 'https://json-schema.org/draft/2020-12/vocab/content',\n 'https://json-schema.org/draft/2019-09/vocab/core',\n 'https://json-schema.org/draft/2019-09/vocab/applicator',\n 'https://json-schema.org/draft/2019-09/vocab/validation',\n 'https://json-schema.org/draft/2019-09/vocab/meta-data',\n 'https://json-schema.org/draft/2019-09/vocab/format',\n 'https://json-schema.org/draft/2019-09/vocab/content',\n]);\nconst declarationSchema = z.looseObject({\n $schema: z.string().optional(),\n $vocabulary: z.record(z.string(), z.boolean()).optional(),\n});\n\nconst checkDialect = (value: AuthoredValue): void => {\n if (z.boolean().safeParse(value).success) return;\n const schema = declarationSchema.parse(value);\n if (schema.$schema != null && !dialects.has(schema.$schema))\n throw new Error(`Unsupported JSON Schema dialect ${schema.$schema}`);\n for (const [name, required] of Object.entries(schema.$vocabulary ?? {})) {\n if (required && !vocabularies.has(name))\n throw new Error(`Unsupported required JSON Schema vocabulary ${name}`);\n }\n};\n\nconst dialectByVersion = {\n 'draft-04': 'http://json-schema.org/draft-04/schema#',\n 'draft-06': 'http://json-schema.org/draft-06/schema#',\n 'draft-07': 'http://json-schema.org/draft-07/schema#',\n 'draft-2019-09': 'https://json-schema.org/draft/2019-09/schema',\n 'draft-2020-12': 'https://json-schema.org/draft/2020-12/schema',\n} satisfies Record<string, string>;\nlet metaRoot: SchemaNode | null = null;\nconst metaSchemas = (): SchemaNode => {\n if (metaRoot != null) return metaRoot;\n const schemas = z\n .array(jsonObjectSchema)\n .parse(remotes)\n .map((schema) => {\n const identity = z\n .string()\n .parse(schema.$id ?? schema.id)\n .replace(/#$/, '');\n const remote: JsonObject = { ...schema, $id: identity };\n if (schema.id != null) remote['id'] = identity;\n return remote;\n });\n metaRoot = compileSchema(\n {},\n { remotes: schemas, formatAssertion: true, throwOnInvalidRef: true },\n );\n return metaRoot;\n};\n\nconst schemaKeywords = new Set([\n 'additionalItems',\n 'additionalProperties',\n 'contains',\n 'propertyNames',\n 'unevaluatedItems',\n 'unevaluatedProperties',\n 'not',\n 'if',\n 'then',\n 'else',\n]);\nconst schemaMaps = new Set([\n 'properties',\n 'patternProperties',\n '$defs',\n 'definitions',\n 'dependentSchemas',\n 'dependencies',\n]);\nconst schemaArrays = new Set(['allOf', 'anyOf', 'oneOf', 'prefixItems']);\nconst childPlaceholder = (value: JsonValue): JsonValue =>\n jsonObjectSchema.safeParse(value).success ? {} : value;\n\n// Validate each parsed node against its own dialect. Child schemas are checked\n// separately, so an embedded resource can declare a different dialect.\nconst shallowDeclaration = (schema: JsonObject): JsonObject =>\n Object.fromEntries(\n Object.entries(schema).map(([key, value]) => {\n if (schemaKeywords.has(key)) return [key, childPlaceholder(value)];\n if ((schemaArrays.has(key) || key === 'items') && Array.isArray(value))\n return [key, value.map(childPlaceholder)];\n if (key === 'items') return [key, childPlaceholder(value)];\n const object = jsonObjectSchema.safeParse(value);\n if (schemaMaps.has(key) && object.success)\n return [\n key,\n Object.fromEntries(\n Object.entries(object.data).map(([name, child]) => [name, childPlaceholder(child)]),\n ),\n ];\n return [key, value];\n }),\n );\nconst checkDeclaration = (node: SchemaNode): void => {\n if (z.boolean().safeParse(node.schema).success) return;\n const schema = jsonObjectSchema.parse(node.schema);\n checkDialect(schema);\n const dialect = Object.entries(dialectByVersion).find(\n ([version]) => version === node.context.version,\n )?.[1];\n if (dialect == null) throw new Error(`Unsupported JSON Schema version ${node.context.version}`);\n const meta = metaSchemas().getNodeRef(dialect);\n if (!isSchemaNode(meta)) throw new Error(`Missing JSON Schema metaschema ${dialect}`);\n const result = meta.validate(shallowDeclaration(schema));\n if (!result.valid) throw new Error(result.errors.map((issue) => issue.message).join('; '));\n};\n\nconst canonicalJson = (value: JsonValue): JsonValue => {\n if (Array.isArray(value)) return value.map(canonicalJson);\n const object = jsonObjectSchema.safeParse(value);\n if (!object.success) return value;\n return Object.fromEntries(\n Object.entries(object.data)\n .sort(([left], [right]) => left.localeCompare(right))\n .map(([key, item]) => [key, canonicalJson(item)]),\n );\n};\n\n// Compile a private tree for each validation. The interpreter never fetches\n// references or shares a schema registry, and retains no tool data between calls.\nconst validatorFor = (schema: AuthoredValue): SchemaNode => {\n const text = JSON.stringify(schema);\n if (text == null) throw new Error('Expected a JSON Schema object');\n const parsed = jsonObjectSchema.parse(canonicalJson(jsonObjectSchema.parse(JSON.parse(text))));\n checkDialect(parsed);\n const node = compileSchema(parsed, { formatAssertion: true, throwOnInvalidRef: true });\n if (node.schemaErrors != null && node.schemaErrors.length > 0)\n throw new Error(node.schemaErrors.map((issue) => issue.message).join('; '));\n // Check even unused declarations: an unresolved reference must fail publish,\n // rather than surviving until some input happens to select that branch.\n const nodes = new Set([node, ...Object.values(node.context.refs)]);\n for (const child of nodes) {\n checkDeclaration(child);\n const ref =\n fieldOf(child.schema, '$ref') ??\n fieldOf(child.schema, '$dynamicRef') ??\n fieldOf(child.schema, '$recursiveRef');\n if (ref == null) continue;\n const resolved = child.resolveRef();\n if (!isSchemaNode(resolved))\n throw new Error(`Unresolved JSON Schema reference ${String(ref)} at ${child.schemaLocation}`);\n }\n return node;\n};\n\nexport const jsonSchemaError = (schema: AuthoredValue, value: AuthoredValue): string | null => {\n const validator = validatorFor(schema);\n const parsed = jsonValueSchema.safeParse(value);\n if (!parsed.success) return 'Expected a JSON-compatible value';\n // JSON object order is immaterial, including inside enum assertions.\n const result = validator.validate(canonicalJson(parsed.data));\n return result.valid ? null : result.errors.map((issue) => issue.message).join('; ');\n};\n\nexport const jsonSchemaDeclarationError = (schema: AuthoredValue): string | null => {\n try {\n validatorFor(schema);\n return null;\n } catch (cause) {\n return cause instanceof Error ? cause.message : String(cause);\n }\n};\n\nexport const standardValidatorSchema = z.looseObject({\n '~standard': z.looseObject({\n version: z.literal(1),\n vendor: z.string(),\n validate: callableSchema,\n }),\n});\nconst validationResultSchema = z.looseObject({\n value: z.unknown().optional(),\n issues: z.array(z.looseObject({ message: z.string().optional() })).optional(),\n});\n\nexport const validateSchemaValue = async (args: {\n schema: AuthoredValue;\n value: AuthoredValue;\n what: string;\n}): Promise<AuthoredValue> => {\n if (args.schema == null) return args.value;\n const standard = standardValidatorSchema.safeParse(args.schema);\n if (standard.success) {\n // Zod's Standard Schema validator retries asynchronous transforms after a\n // synchronous attempt; its public async parser performs them only once.\n if (standard.data['~standard'].vendor === 'zod') {\n const parser = callableSchema.safeParse(fieldOf(args.schema, 'safeParseAsync'));\n if (parser.success) {\n const result = z\n .looseObject({\n success: z.boolean(),\n data: z.unknown().optional(),\n error: z.looseObject({ issues: z.array(z.object({ message: z.string() })) }).optional(),\n })\n .parse(await parser.data.call(args.schema, args.value));\n if (!result.success)\n throw new Error(\n `Invalid ${args.what}: ${result.error?.issues.map((issue) => issue.message).join('; ') ?? 'invalid'}`,\n );\n return result.data;\n }\n }\n const raw = await standard.data['~standard'].validate.call(\n fieldOf(args.schema, '~standard'),\n args.value,\n );\n const result = validationResultSchema.parse(raw);\n if (result.issues != null)\n throw new Error(\n `Invalid ${args.what}: ${result.issues.map((issue) => issue.message ?? 'invalid').join('; ') || 'invalid'}`,\n );\n if (!Object.hasOwn(result, 'value'))\n throw new Error(`Invalid ${args.what}: schema validator returned no value`);\n return result.value;\n }\n const error = jsonSchemaError(args.schema, args.value);\n if (error != null) throw new Error(`Invalid ${args.what}: ${error}`);\n return args.value;\n};\n\n// Published results have already been transformed. Never run their input\n// validator again: use the output JSON Schema for synchronous hook narrowing.\nexport const resultMatchesSchema = (schema: AuthoredValue, value: AuthoredValue): boolean => {\n if (schema == null) return true;\n try {\n const standard = standardValidatorSchema.safeParse(schema);\n if (!standard.success) return jsonSchemaError(schema, value) == null;\n const jsonSchemas = fieldOf(fieldOf(schema, '~standard'), 'jsonSchema');\n const converter = callableSchema.safeParse(fieldOf(jsonSchemas, SchemaIo.Output));\n if (!converter.success) return false;\n return (\n jsonSchemaError(converter.data.call(jsonSchemas, { target: 'draft-2020-12' }), value) == null\n );\n } catch {\n return false;\n }\n};\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": ["SchemaIo", "result"]
|
|
7
|
+
}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import * as z from 'zod';
|
|
2
|
+
export declare const authoredValueSchema: z.ZodUnknown;
|
|
3
|
+
export type AuthoredValue = z.output<typeof authoredValueSchema>;
|
|
4
|
+
export declare const optionalValueSchema: z.ZodOptional<z.ZodUnknown>;
|
|
5
|
+
export type AuthoredCallable = (...args: AuthoredValue[]) => AuthoredValue;
|
|
6
|
+
export declare const callableSchema: z.ZodCustom<AuthoredCallable, AuthoredCallable>;
|
|
7
|
+
export declare const authoredRecordSchema: z.ZodRecord<z.ZodString, z.ZodUnknown>;
|
|
8
|
+
export type AuthoredRecord = z.output<typeof authoredRecordSchema>;
|
|
9
|
+
export declare const isCallable: (value: AuthoredValue) => value is AuthoredCallable;
|
|
10
|
+
export declare const isString: (value: AuthoredValue) => value is string;
|
|
11
|
+
export declare const isNumber: (value: AuthoredValue) => value is number;
|
|
12
|
+
export declare const isBoolean: (value: AuthoredValue) => value is boolean;
|
|
13
|
+
export declare const stringOrNull: (value: AuthoredValue) => string | null;
|
|
14
|
+
export declare const isObjectLike: (value: AuthoredValue) => value is object;
|
|
15
|
+
export declare const isPlainObject: (value: AuthoredValue) => value is AuthoredRecord;
|
|
16
|
+
export declare const fieldOf: (value: AuthoredValue, key: string) => AuthoredValue;
|
|
17
|
+
export declare const entriesOf: (value: AuthoredValue) => [string, AuthoredValue][];
|
|
18
|
+
export declare const isPromiseLike: (value: AuthoredValue) => value is PromiseLike<AuthoredValue>;
|
|
19
|
+
export declare const isAsyncIterable: (value: AuthoredValue) => value is AsyncIterable<AuthoredValue>;
|
|
20
|
+
export declare const messageOf: (cause: unknown) => string;
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
import * as z from "zod";
|
|
2
|
+
const authoredValueSchema = z.unknown();
|
|
3
|
+
const optionalValueSchema = authoredValueSchema.optional();
|
|
4
|
+
const functionSchema = z.function();
|
|
5
|
+
const callableSchema = z.custom(
|
|
6
|
+
(value) => functionSchema.safeParse(value).success
|
|
7
|
+
);
|
|
8
|
+
const authoredRecordSchema = z.record(z.string(), authoredValueSchema);
|
|
9
|
+
const isCallable = (value) => callableSchema.safeParse(value).success;
|
|
10
|
+
const isString = (value) => z.string().safeParse(value).success;
|
|
11
|
+
const isNumber = (value) => z.number().safeParse(value).success;
|
|
12
|
+
const isBoolean = (value) => z.boolean().safeParse(value).success;
|
|
13
|
+
const stringOrNull = (value) => isString(value) ? value : null;
|
|
14
|
+
const isObjectLike = (value) => value instanceof Object;
|
|
15
|
+
const isPlainObject = (value) => {
|
|
16
|
+
if (!isObjectLike(value) || Array.isArray(value) || isCallable(value)) return false;
|
|
17
|
+
const proto = Object.getPrototypeOf(value);
|
|
18
|
+
return proto == null || Object.getPrototypeOf(proto) == null;
|
|
19
|
+
};
|
|
20
|
+
const fieldOf = (value, key) => {
|
|
21
|
+
if (!isObjectLike(value) || !(key in value)) return void 0;
|
|
22
|
+
const parsed = z.looseObject({ [key]: optionalValueSchema }).safeParse(value);
|
|
23
|
+
if (parsed.success) return parsed.data[key];
|
|
24
|
+
return Object.getOwnPropertyDescriptor(value, key)?.value;
|
|
25
|
+
};
|
|
26
|
+
const entriesOf = (value) => isObjectLike(value) ? Object.entries(value) : [];
|
|
27
|
+
const isPromiseLike = (value) => isCallable(fieldOf(value, "then"));
|
|
28
|
+
const isAsyncIterable = (value) => isObjectLike(value) && Symbol.asyncIterator in value;
|
|
29
|
+
const messageOf = (cause) => cause instanceof Error ? cause.message : String(cause);
|
|
30
|
+
export {
|
|
31
|
+
authoredRecordSchema,
|
|
32
|
+
authoredValueSchema,
|
|
33
|
+
callableSchema,
|
|
34
|
+
entriesOf,
|
|
35
|
+
fieldOf,
|
|
36
|
+
isAsyncIterable,
|
|
37
|
+
isBoolean,
|
|
38
|
+
isCallable,
|
|
39
|
+
isNumber,
|
|
40
|
+
isObjectLike,
|
|
41
|
+
isPlainObject,
|
|
42
|
+
isPromiseLike,
|
|
43
|
+
isString,
|
|
44
|
+
messageOf,
|
|
45
|
+
optionalValueSchema,
|
|
46
|
+
stringOrNull
|
|
47
|
+
};
|
|
48
|
+
//# sourceMappingURL=values.mjs.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../../../src/runtime/values.ts"],
|
|
4
|
+
"sourcesContent": ["import * as z from 'zod';\n\n// Authored modules hand the compiler and the isolate arbitrary values; these\n// schemas decode them at that boundary. Each slot then parses the decoded\n// value with the schema of what it must be (a tool, a connection, ...).\n\n// A value produced by authored code, before its slot's schema has parsed it.\nexport const authoredValueSchema = z.unknown();\nexport type AuthoredValue = z.output<typeof authoredValueSchema>;\n\n// An object field that may be absent.\nexport const optionalValueSchema = authoredValueSchema.optional();\n\nexport type AuthoredCallable = (...args: AuthoredValue[]) => AuthoredValue;\n\n// zod's function check, not instanceof, so functions from another realm (the\n// local dev isolate's) are callable too.\nconst functionSchema = z.function();\nexport const callableSchema = z.custom<AuthoredCallable>(\n (value) => functionSchema.safeParse(value).success,\n);\n\nexport const authoredRecordSchema = z.record(z.string(), authoredValueSchema);\nexport type AuthoredRecord = z.output<typeof authoredRecordSchema>;\n\nexport const isCallable = (value: AuthoredValue): value is AuthoredCallable =>\n callableSchema.safeParse(value).success;\n\nexport const isString = (value: AuthoredValue): value is string =>\n z.string().safeParse(value).success;\n\nexport const isNumber = (value: AuthoredValue): value is number =>\n z.number().safeParse(value).success;\n\nexport const isBoolean = (value: AuthoredValue): value is boolean =>\n z.boolean().safeParse(value).success;\n\nexport const stringOrNull = (value: AuthoredValue): string | null =>\n isString(value) ? value : null;\n\n// Objects and functions (which may carry properties, like a defined harness).\nexport const isObjectLike = (value: AuthoredValue): value is object => value instanceof Object;\n\n// A plain object literal (from any realm): Object.prototype or null prototype.\nexport const isPlainObject = (value: AuthoredValue): value is AuthoredRecord => {\n if (!isObjectLike(value) || Array.isArray(value) || isCallable(value)) return false;\n const proto: AuthoredValue = Object.getPrototypeOf(value);\n // Object.prototype itself is not `instanceof Object`; its own prototype is null.\n return proto == null || Object.getPrototypeOf(proto) == null;\n};\n\n// Reads one named property of an authored object or function, including\n// getters and inherited properties.\nexport const fieldOf = (value: AuthoredValue, key: string): AuthoredValue => {\n if (!isObjectLike(value) || !(key in value)) return undefined;\n const parsed = z.looseObject({ [key]: optionalValueSchema }).safeParse(value);\n if (parsed.success) return parsed.data[key];\n return Object.getOwnPropertyDescriptor(value, key)?.value;\n};\n\n// Own enumerable entries of an authored object or function.\nexport const entriesOf = (value: AuthoredValue): [string, AuthoredValue][] =>\n isObjectLike(value) ? Object.entries(value) : [];\n\nexport const isPromiseLike = (value: AuthoredValue): value is PromiseLike<AuthoredValue> =>\n isCallable(fieldOf(value, 'then'));\n\nexport const isAsyncIterable = (value: AuthoredValue): value is AsyncIterable<AuthoredValue> =>\n isObjectLike(value) && Symbol.asyncIterator in value;\n\nexport const messageOf = (cause: unknown): string =>\n cause instanceof Error ? cause.message : String(cause);\n"],
|
|
5
|
+
"mappings": "AAAA,YAAY,OAAO;AAOZ,MAAM,sBAAsB,EAAE,QAAQ;AAItC,MAAM,sBAAsB,oBAAoB,SAAS;AAMhE,MAAM,iBAAiB,EAAE,SAAS;AAC3B,MAAM,iBAAiB,EAAE;AAAA,EAC9B,CAAC,UAAU,eAAe,UAAU,KAAK,EAAE;AAC7C;AAEO,MAAM,uBAAuB,EAAE,OAAO,EAAE,OAAO,GAAG,mBAAmB;AAGrE,MAAM,aAAa,CAAC,UACzB,eAAe,UAAU,KAAK,EAAE;AAE3B,MAAM,WAAW,CAAC,UACvB,EAAE,OAAO,EAAE,UAAU,KAAK,EAAE;AAEvB,MAAM,WAAW,CAAC,UACvB,EAAE,OAAO,EAAE,UAAU,KAAK,EAAE;AAEvB,MAAM,YAAY,CAAC,UACxB,EAAE,QAAQ,EAAE,UAAU,KAAK,EAAE;AAExB,MAAM,eAAe,CAAC,UAC3B,SAAS,KAAK,IAAI,QAAQ;AAGrB,MAAM,eAAe,CAAC,UAA0C,iBAAiB;AAGjF,MAAM,gBAAgB,CAAC,UAAkD;AAC9E,MAAI,CAAC,aAAa,KAAK,KAAK,MAAM,QAAQ,KAAK,KAAK,WAAW,KAAK,EAAG,QAAO;AAC9E,QAAM,QAAuB,OAAO,eAAe,KAAK;AAExD,SAAO,SAAS,QAAQ,OAAO,eAAe,KAAK,KAAK;AAC1D;AAIO,MAAM,UAAU,CAAC,OAAsB,QAA+B;AAC3E,MAAI,CAAC,aAAa,KAAK,KAAK,EAAE,OAAO,OAAQ,QAAO;AACpD,QAAM,SAAS,EAAE,YAAY,EAAE,CAAC,GAAG,GAAG,oBAAoB,CAAC,EAAE,UAAU,KAAK;AAC5E,MAAI,OAAO,QAAS,QAAO,OAAO,KAAK,GAAG;AAC1C,SAAO,OAAO,yBAAyB,OAAO,GAAG,GAAG;AACtD;AAGO,MAAM,YAAY,CAAC,UACxB,aAAa,KAAK,IAAI,OAAO,QAAQ,KAAK,IAAI,CAAC;AAE1C,MAAM,gBAAgB,CAAC,UAC5B,WAAW,QAAQ,OAAO,MAAM,CAAC;AAE5B,MAAM,kBAAkB,CAAC,UAC9B,aAAa,KAAK,KAAK,OAAO,iBAAiB;AAE1C,MAAM,YAAY,CAAC,UACxB,iBAAiB,QAAQ,MAAM,UAAU,OAAO,KAAK;",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
import {
|
|
2
|
+
credentials,
|
|
3
|
+
defineAgent,
|
|
4
|
+
defineHarness,
|
|
5
|
+
type CredentialPolicyIface,
|
|
6
|
+
} from '@finalai/agents';
|
|
7
|
+
|
|
8
|
+
// Custom harness configuration is a type argument. Resume returns an endpoint,
|
|
9
|
+
// and the API key secret read through a computed name is declared in `secrets`.
|
|
10
|
+
const acmeFleet = defineHarness<{
|
|
11
|
+
region?: string;
|
|
12
|
+
apiKeySecret: string;
|
|
13
|
+
credentials: CredentialPolicyIface;
|
|
14
|
+
}>({
|
|
15
|
+
describe: async () => ({
|
|
16
|
+
configSchema: {
|
|
17
|
+
type: 'object',
|
|
18
|
+
properties: {
|
|
19
|
+
credentials: { $ref: 'final://schemas/credential-policy' },
|
|
20
|
+
region: { type: 'string' },
|
|
21
|
+
apiKeySecret: { type: 'string' },
|
|
22
|
+
},
|
|
23
|
+
required: ['apiKeySecret', 'credentials'],
|
|
24
|
+
},
|
|
25
|
+
acp: { transports: ['ws'], mcp: ['http'] },
|
|
26
|
+
supports: { observe: false, resumeReplay: true, fork: false },
|
|
27
|
+
}),
|
|
28
|
+
open: async ({ sessionId, config, secrets }) => {
|
|
29
|
+
// Acme's fleet: ask it to start a Claude Code container in the chosen region and hand back an ACP WebSocket
|
|
30
|
+
const res = await fetch('https://fleet.acme.dev/sessions', {
|
|
31
|
+
method: 'POST',
|
|
32
|
+
headers: { authorization: `Bearer ${await secrets.get(config.apiKeySecret)}` },
|
|
33
|
+
body: JSON.stringify({
|
|
34
|
+
region: config.region,
|
|
35
|
+
program: 'claude-code',
|
|
36
|
+
externalId: sessionId,
|
|
37
|
+
}),
|
|
38
|
+
});
|
|
39
|
+
const { id, wsUrl, token } = await res.json();
|
|
40
|
+
return {
|
|
41
|
+
ref: { harnessSessionRef: id, generation: 1 },
|
|
42
|
+
transport: 'ws',
|
|
43
|
+
url: wsUrl,
|
|
44
|
+
headers: { authorization: `Bearer ${token}` },
|
|
45
|
+
};
|
|
46
|
+
},
|
|
47
|
+
resume: async ({ ref, config, secrets }) => {
|
|
48
|
+
const res = await fetch(`https://fleet.acme.dev/sessions/${ref.harnessSessionRef}/resume`, {
|
|
49
|
+
method: 'POST',
|
|
50
|
+
headers: { authorization: `Bearer ${await secrets.get(config.apiKeySecret)}` },
|
|
51
|
+
});
|
|
52
|
+
const { wsUrl, token } = await res.json();
|
|
53
|
+
return { ref, transport: 'ws', url: wsUrl, headers: { authorization: `Bearer ${token}` } };
|
|
54
|
+
},
|
|
55
|
+
park: async ({ ref }) => {
|
|
56
|
+
await fetch(`https://fleet.acme.dev/sessions/${ref.harnessSessionRef}/pause`, {
|
|
57
|
+
method: 'POST',
|
|
58
|
+
});
|
|
59
|
+
},
|
|
60
|
+
close: async ({ ref }) => {
|
|
61
|
+
await fetch(`https://fleet.acme.dev/sessions/${ref.harnessSessionRef}`, { method: 'DELETE' });
|
|
62
|
+
},
|
|
63
|
+
health: async () => ({ ok: true }),
|
|
64
|
+
});
|
|
65
|
+
|
|
66
|
+
export default defineAgent({
|
|
67
|
+
name: 'Release Scout',
|
|
68
|
+
secrets: ['acme-fleet-key'],
|
|
69
|
+
harness: acmeFleet({
|
|
70
|
+
credentials: credentials.chain({ payer: 'agent-owner', tryInOrder: [credentials.harness()] }),
|
|
71
|
+
region: 'eu',
|
|
72
|
+
apiKeySecret: 'acme-fleet-key',
|
|
73
|
+
}),
|
|
74
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
You are Release Scout for the Final engineering team. Be brief. Cite release tags.
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { defineAgent, credentials as definitionCredentials } from '@finalai/agents';
|
|
2
|
+
import { serverlessPi } from '@finalai/final-agent-provider/harnesses';
|
|
3
|
+
|
|
4
|
+
export default defineAgent({
|
|
5
|
+
harness: serverlessPi({
|
|
6
|
+
credentials: definitionCredentials.chain({
|
|
7
|
+
payer: 'organization',
|
|
8
|
+
tryInOrder: [
|
|
9
|
+
definitionCredentials.subscription({ owner: 'organization' }),
|
|
10
|
+
definitionCredentials.platform(),
|
|
11
|
+
],
|
|
12
|
+
}),
|
|
13
|
+
model: 'gpt-6-sol',
|
|
14
|
+
reasoning: 'low',
|
|
15
|
+
}),
|
|
16
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Help the user with their requests.
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { defineTool } from '@finalai/agents';
|
|
2
|
+
import * as z from 'zod';
|
|
3
|
+
|
|
4
|
+
export default defineTool({
|
|
5
|
+
description: 'Read the current UTC time from the execution environment.',
|
|
6
|
+
inputSchema: z.strictObject({}),
|
|
7
|
+
outputSchema: z.object({ utc: z.string() }),
|
|
8
|
+
execute: () => ({ utc: new Date().toISOString() }),
|
|
9
|
+
});
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { defineAgent, credentials as definitionCredentials } from '@finalai/agents';
|
|
2
|
+
import { serverlessPi } from '@finalai/final-agent-provider/harnesses';
|
|
3
|
+
|
|
4
|
+
export default defineAgent({
|
|
5
|
+
harness: serverlessPi({
|
|
6
|
+
credentials: definitionCredentials.chain({
|
|
7
|
+
payer: 'organization',
|
|
8
|
+
tryInOrder: [
|
|
9
|
+
definitionCredentials.subscription({ owner: 'organization' }),
|
|
10
|
+
definitionCredentials.platform(),
|
|
11
|
+
],
|
|
12
|
+
}),
|
|
13
|
+
model: 'gpt-5.5',
|
|
14
|
+
reasoning: 'low',
|
|
15
|
+
}),
|
|
16
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
Help the user with their requests.
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { defineTool } from '@finalai/agents';
|
|
2
|
+
import * as z from 'zod';
|
|
3
|
+
|
|
4
|
+
export default defineTool({
|
|
5
|
+
description: 'Read the current UTC time from the execution environment.',
|
|
6
|
+
inputSchema: z.strictObject({}),
|
|
7
|
+
outputSchema: z.object({ utc: z.string() }),
|
|
8
|
+
execute: () => ({ utc: new Date().toISOString() }),
|
|
9
|
+
});
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { defineAgent, credentials as definitionCredentials } from '@finalai/agents';
|
|
2
|
+
import { serverlessFinal } from '@finalai/final-agent-provider/harnesses';
|
|
3
|
+
|
|
4
|
+
export default defineAgent({
|
|
5
|
+
description: 'Works with Goals and conversations through Final.',
|
|
6
|
+
harness: serverlessFinal({
|
|
7
|
+
credentials: definitionCredentials.chain({
|
|
8
|
+
payer: 'organization',
|
|
9
|
+
tryInOrder: [
|
|
10
|
+
definitionCredentials.subscription({ owner: 'organization' }),
|
|
11
|
+
definitionCredentials.platform(),
|
|
12
|
+
],
|
|
13
|
+
}),
|
|
14
|
+
}),
|
|
15
|
+
});
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { defineFinalConnection } from '@finalai/agents';
|
|
2
|
+
import { always } from '@finalai/agents/approval';
|
|
3
|
+
|
|
4
|
+
// Final's MCP server: the session service resolves `final-session` auth to a
|
|
5
|
+
// grant scoped to the calling session.
|
|
6
|
+
export default defineFinalConnection({
|
|
7
|
+
url: 'https://console.final.test/api/mcp/tools',
|
|
8
|
+
tools: { approval: { cancel_goal: always() } },
|
|
9
|
+
});
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import { baseTools, credentials, defineAgent } from '@finalai/agents';
|
|
2
|
+
import { serverlessPi } from '@finalai/agents/harnesses';
|
|
3
|
+
import { computer } from './sandbox';
|
|
4
|
+
|
|
5
|
+
export default defineAgent({
|
|
6
|
+
name: 'Release Scout',
|
|
7
|
+
description: 'Answers release questions, runs checks, posts the daily digest.',
|
|
8
|
+
// Read by tools/lookup_release_notes.ts and channels/github.ts; linear-token
|
|
9
|
+
// comes from connections/linear.ts.
|
|
10
|
+
secrets: ['github-token', 'github-webhook-secret'],
|
|
11
|
+
// Off unless declared; each capability is bound to a named sandbox target.
|
|
12
|
+
tools: baseTools({ shell: computer, files: computer }),
|
|
13
|
+
harness: serverlessPi({
|
|
14
|
+
model: 'gpt-6-sol',
|
|
15
|
+
reasoning: 'medium',
|
|
16
|
+
credentials: credentials.chain({
|
|
17
|
+
payer: 'organization',
|
|
18
|
+
tryInOrder: [credentials.apiKey({ owner: 'organization' }), credentials.platform()],
|
|
19
|
+
}),
|
|
20
|
+
permissionMode: 'ask',
|
|
21
|
+
}),
|
|
22
|
+
});
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
// A helper next to the channel (no default export, so not a channel itself).
|
|
2
|
+
export const verifyGithubSignature = async (
|
|
3
|
+
request: Request,
|
|
4
|
+
body: string,
|
|
5
|
+
secret: string | null,
|
|
6
|
+
): Promise<boolean> => {
|
|
7
|
+
const signature = request.headers.get('x-hub-signature-256');
|
|
8
|
+
if (
|
|
9
|
+
secret == null ||
|
|
10
|
+
secret.length === 0 ||
|
|
11
|
+
signature == null ||
|
|
12
|
+
!/^sha256=[a-f0-9]{64}$/i.test(signature)
|
|
13
|
+
)
|
|
14
|
+
return false;
|
|
15
|
+
const digest = Uint8Array.from(signature.slice(7).match(/.{2}/g) ?? [], (byte) =>
|
|
16
|
+
Number.parseInt(byte, 16),
|
|
17
|
+
);
|
|
18
|
+
const encoder = new TextEncoder();
|
|
19
|
+
const key = await crypto.subtle.importKey(
|
|
20
|
+
'raw',
|
|
21
|
+
encoder.encode(secret),
|
|
22
|
+
{ name: 'HMAC', hash: 'SHA-256' },
|
|
23
|
+
false,
|
|
24
|
+
['verify'],
|
|
25
|
+
);
|
|
26
|
+
return crypto.subtle.verify('HMAC', key, digest, encoder.encode(body));
|
|
27
|
+
};
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import { defineChannel, POST } from '@finalai/agents/channels';
|
|
2
|
+
import * as z from 'zod';
|
|
3
|
+
import { verifyGithubSignature } from './github-signature';
|
|
4
|
+
|
|
5
|
+
const actionSchema = z.object({ action: z.string() });
|
|
6
|
+
const releaseEventSchema = actionSchema.extend({ release: z.object({ tag_name: z.string() }) });
|
|
7
|
+
|
|
8
|
+
export default defineChannel({
|
|
9
|
+
routes: [
|
|
10
|
+
POST('/webhook', async ({ request, secrets, receive }) => {
|
|
11
|
+
const body = await request.text();
|
|
12
|
+
if (
|
|
13
|
+
!(await verifyGithubSignature(request, body, await secrets.get('github-webhook-secret')))
|
|
14
|
+
) {
|
|
15
|
+
return new Response(null, { status: 401 });
|
|
16
|
+
}
|
|
17
|
+
let raw: unknown;
|
|
18
|
+
try {
|
|
19
|
+
raw = JSON.parse(body);
|
|
20
|
+
} catch {
|
|
21
|
+
return new Response(null, { status: 400 });
|
|
22
|
+
}
|
|
23
|
+
const action = actionSchema.safeParse(raw);
|
|
24
|
+
if (!action.success) return new Response(null, { status: 400 });
|
|
25
|
+
if (action.data.action !== 'published') return new Response(null, { status: 204 });
|
|
26
|
+
const parsed = releaseEventSchema.safeParse(raw);
|
|
27
|
+
if (!parsed.success) return new Response(null, { status: 400 });
|
|
28
|
+
await receive({
|
|
29
|
+
target: { kind: 'bound-conversation' },
|
|
30
|
+
content: [
|
|
31
|
+
{ type: 'text', text: `GitHub release published: ${parsed.data.release.tag_name}` },
|
|
32
|
+
],
|
|
33
|
+
});
|
|
34
|
+
return new Response(null, { status: 202 });
|
|
35
|
+
}),
|
|
36
|
+
],
|
|
37
|
+
turnPolicy: 'steer',
|
|
38
|
+
});
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { defineMcpClientConnection } from '@finalai/agents';
|
|
2
|
+
import { always } from '@finalai/agents/approval';
|
|
3
|
+
|
|
4
|
+
export default defineMcpClientConnection({
|
|
5
|
+
url: 'https://mcp.linear.app/mcp',
|
|
6
|
+
// Bearer from the secrets manager; the secret never reaches the harness.
|
|
7
|
+
auth: { secretKey: 'linear-token', headerName: null },
|
|
8
|
+
tools: { allow: ['search_issues', 'create_issue'], approval: { create_issue: always() } },
|
|
9
|
+
});
|