llmist 0.5.1 → 0.6.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/{chunk-MH4TQ5AD.js → chunk-KB7LMYC2.js} +745 -287
- package/dist/chunk-KB7LMYC2.js.map +1 -0
- package/dist/{chunk-VF2WOCHM.js → chunk-YWJSGEYT.js} +4 -2
- package/dist/{chunk-VF2WOCHM.js.map → chunk-YWJSGEYT.js.map} +1 -1
- package/dist/cli.cjs +3167 -2686
- package/dist/cli.cjs.map +1 -1
- package/dist/cli.js +94 -48
- package/dist/cli.js.map +1 -1
- package/dist/index.cjs +751 -304
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +112 -3
- package/dist/index.d.ts +112 -3
- package/dist/index.js +16 -5
- package/dist/index.js.map +1 -1
- package/dist/{mock-stream-C8mBXRzJ.d.cts → mock-stream-CCe8vISa.d.cts} +45 -1
- package/dist/{mock-stream-C8mBXRzJ.d.ts → mock-stream-CCe8vISa.d.ts} +45 -1
- package/dist/testing/index.cjs +740 -287
- package/dist/testing/index.cjs.map +1 -1
- package/dist/testing/index.d.cts +2 -2
- package/dist/testing/index.d.ts +2 -2
- package/dist/testing/index.js +2 -2
- package/package.json +1 -1
- package/dist/chunk-LKIBXQ5I.js +0 -23
- package/dist/chunk-LKIBXQ5I.js.map +0 -1
- package/dist/chunk-MH4TQ5AD.js.map +0 -1
package/dist/index.cjs
CHANGED
|
@@ -345,12 +345,16 @@ var init_registry = __esm({
|
|
|
345
345
|
});
|
|
346
346
|
|
|
347
347
|
// src/core/constants.ts
|
|
348
|
-
var GADGET_START_PREFIX, GADGET_END_PREFIX;
|
|
348
|
+
var GADGET_START_PREFIX, GADGET_END_PREFIX, DEFAULT_GADGET_OUTPUT_LIMIT, DEFAULT_GADGET_OUTPUT_LIMIT_PERCENT, CHARS_PER_TOKEN, FALLBACK_CONTEXT_WINDOW;
|
|
349
349
|
var init_constants = __esm({
|
|
350
350
|
"src/core/constants.ts"() {
|
|
351
351
|
"use strict";
|
|
352
352
|
GADGET_START_PREFIX = "!!!GADGET_START:";
|
|
353
353
|
GADGET_END_PREFIX = "!!!GADGET_END";
|
|
354
|
+
DEFAULT_GADGET_OUTPUT_LIMIT = true;
|
|
355
|
+
DEFAULT_GADGET_OUTPUT_LIMIT_PERCENT = 15;
|
|
356
|
+
CHARS_PER_TOKEN = 4;
|
|
357
|
+
FALLBACK_CONTEXT_WINDOW = 128e3;
|
|
354
358
|
}
|
|
355
359
|
});
|
|
356
360
|
|
|
@@ -384,7 +388,7 @@ var init_prompt_config = __esm({
|
|
|
384
388
|
criticalUsage: "INVOKE gadgets using the markers - do not describe what you want to do.",
|
|
385
389
|
formatDescriptionYaml: "Parameters in YAML format (one per line)",
|
|
386
390
|
formatDescriptionJson: "Parameters in JSON format (valid JSON object)",
|
|
387
|
-
formatDescriptionToml: "Parameters in TOML format (key = value pairs, use
|
|
391
|
+
formatDescriptionToml: "Parameters in TOML format (key = value pairs, use heredoc for multiline: key = <<<EOF ... EOF)",
|
|
388
392
|
rules: () => [
|
|
389
393
|
"Output ONLY plain text with the exact markers - never use function/tool calling",
|
|
390
394
|
"You can invoke multiple gadgets in a single response",
|
|
@@ -565,10 +569,11 @@ ${this.endPrefix}
|
|
|
565
569
|
${this.startPrefix}analyze
|
|
566
570
|
type: economic_analysis
|
|
567
571
|
matter: "Polish Economy"
|
|
568
|
-
question:
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
|
|
572
|
+
question: <<<EOF
|
|
573
|
+
Analyze the following:
|
|
574
|
+
- Polish arms exports 2025
|
|
575
|
+
- Economic implications
|
|
576
|
+
EOF
|
|
572
577
|
${this.endPrefix}`,
|
|
573
578
|
json: `${this.startPrefix}translate
|
|
574
579
|
{"from": "English", "to": "Polish", "content": "Paris is the capital of France: a beautiful city."}
|
|
@@ -584,11 +589,11 @@ ${this.endPrefix}
|
|
|
584
589
|
${this.startPrefix}analyze
|
|
585
590
|
type = "economic_analysis"
|
|
586
591
|
matter = "Polish Economy"
|
|
587
|
-
question =
|
|
592
|
+
question = <<<EOF
|
|
588
593
|
Analyze the following:
|
|
589
594
|
- Polish arms exports 2025
|
|
590
595
|
- Economic implications
|
|
591
|
-
|
|
596
|
+
EOF
|
|
592
597
|
${this.endPrefix}`,
|
|
593
598
|
auto: `${this.startPrefix}translate
|
|
594
599
|
{"from": "English", "to": "Polish", "content": "Paris is the capital of France: a beautiful city."}
|
|
@@ -605,37 +610,38 @@ ${multipleExamples[parameterFormat]}`);
|
|
|
605
610
|
if (parameterFormat === "yaml") {
|
|
606
611
|
parts.push(`
|
|
607
612
|
|
|
608
|
-
YAML
|
|
609
|
-
For string values with
|
|
610
|
-
|
|
613
|
+
YAML HEREDOC SYNTAX:
|
|
614
|
+
For string values with multiple lines, use heredoc syntax (<<<DELIMITER...DELIMITER):
|
|
615
|
+
|
|
616
|
+
filePath: "README.md"
|
|
617
|
+
content: <<<EOF
|
|
618
|
+
# Project Title
|
|
611
619
|
|
|
612
|
-
|
|
613
|
-
|
|
614
|
-
|
|
615
|
-
|
|
616
|
-
|
|
617
|
-
Please choose one.
|
|
620
|
+
This content can contain:
|
|
621
|
+
- Markdown lists
|
|
622
|
+
- Special characters: # : -
|
|
623
|
+
- Multiple paragraphs
|
|
624
|
+
EOF
|
|
618
625
|
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
Which option do you prefer?
|
|
622
|
-
- Option A: fast
|
|
623
|
-
Please choose one. <-- ERROR: not indented, breaks out of the block`);
|
|
626
|
+
The delimiter (EOF) can be any identifier. The closing delimiter must be on its own line.
|
|
627
|
+
No indentation is required for the content.`);
|
|
624
628
|
} else if (parameterFormat === "toml") {
|
|
625
629
|
parts.push(`
|
|
626
630
|
|
|
627
|
-
TOML
|
|
628
|
-
For string values with multiple lines
|
|
631
|
+
TOML HEREDOC SYNTAX:
|
|
632
|
+
For string values with multiple lines, use heredoc syntax (<<<DELIMITER...DELIMITER):
|
|
629
633
|
|
|
630
634
|
filePath = "README.md"
|
|
631
|
-
content =
|
|
635
|
+
content = <<<EOF
|
|
632
636
|
# Project Title
|
|
633
637
|
|
|
634
638
|
This content can contain:
|
|
635
639
|
- Markdown lists
|
|
636
640
|
- Special characters: # : -
|
|
637
641
|
- Multiple paragraphs
|
|
638
|
-
|
|
642
|
+
EOF
|
|
643
|
+
|
|
644
|
+
The delimiter (EOF) can be any identifier. The closing delimiter must be on its own line.`);
|
|
639
645
|
}
|
|
640
646
|
return parts.join("");
|
|
641
647
|
}
|
|
@@ -714,18 +720,28 @@ function parseLogLevel(value) {
|
|
|
714
720
|
}
|
|
715
721
|
return LEVEL_NAME_TO_ID[normalized];
|
|
716
722
|
}
|
|
723
|
+
function parseEnvBoolean(value) {
|
|
724
|
+
if (!value) return void 0;
|
|
725
|
+
const normalized = value.trim().toLowerCase();
|
|
726
|
+
if (normalized === "true" || normalized === "1") return true;
|
|
727
|
+
if (normalized === "false" || normalized === "0") return false;
|
|
728
|
+
return void 0;
|
|
729
|
+
}
|
|
717
730
|
function createLogger(options = {}) {
|
|
718
731
|
const envMinLevel = parseLogLevel(process.env.LLMIST_LOG_LEVEL);
|
|
719
732
|
const envLogFile = process.env.LLMIST_LOG_FILE?.trim() ?? "";
|
|
733
|
+
const envLogReset = parseEnvBoolean(process.env.LLMIST_LOG_RESET);
|
|
720
734
|
const minLevel = options.minLevel ?? envMinLevel ?? 4;
|
|
721
735
|
const defaultType = options.type ?? "pretty";
|
|
722
736
|
const name = options.name ?? "llmist";
|
|
737
|
+
const logReset = options.logReset ?? envLogReset ?? false;
|
|
723
738
|
let logFileStream;
|
|
724
739
|
let finalType = defaultType;
|
|
725
740
|
if (envLogFile) {
|
|
726
741
|
try {
|
|
727
742
|
(0, import_node_fs.mkdirSync)((0, import_node_path.dirname)(envLogFile), { recursive: true });
|
|
728
|
-
|
|
743
|
+
const flags = logReset ? "w" : "a";
|
|
744
|
+
logFileStream = (0, import_node_fs.createWriteStream)(envLogFile, { flags });
|
|
729
745
|
finalType = "hidden";
|
|
730
746
|
} catch (error) {
|
|
731
747
|
console.error("Failed to initialize LLMIST_LOG_FILE output:", error);
|
|
@@ -768,6 +784,532 @@ var init_logger = __esm({
|
|
|
768
784
|
}
|
|
769
785
|
});
|
|
770
786
|
|
|
787
|
+
// src/gadgets/schema-to-json.ts
|
|
788
|
+
function schemaToJSONSchema(schema, options) {
|
|
789
|
+
const jsonSchema = z2.toJSONSchema(schema, options ?? { target: "draft-7" });
|
|
790
|
+
const mismatches = detectDescriptionMismatch(schema, jsonSchema);
|
|
791
|
+
if (mismatches.length > 0) {
|
|
792
|
+
defaultLogger.warn(
|
|
793
|
+
`Zod instance mismatch detected: ${mismatches.length} description(s) lost. For best results, use: import { z } from "llmist"`
|
|
794
|
+
);
|
|
795
|
+
return mergeDescriptions(schema, jsonSchema);
|
|
796
|
+
}
|
|
797
|
+
return jsonSchema;
|
|
798
|
+
}
|
|
799
|
+
function detectDescriptionMismatch(schema, jsonSchema) {
|
|
800
|
+
const mismatches = [];
|
|
801
|
+
function checkSchema(zodSchema, json, path) {
|
|
802
|
+
if (!zodSchema || typeof zodSchema !== "object") return;
|
|
803
|
+
const def = zodSchema._def;
|
|
804
|
+
const jsonObj = json;
|
|
805
|
+
if (def?.description && !jsonObj?.description) {
|
|
806
|
+
mismatches.push(path || "root");
|
|
807
|
+
}
|
|
808
|
+
if (def?.typeName === "ZodObject" && def?.shape) {
|
|
809
|
+
const shape = typeof def.shape === "function" ? def.shape() : def.shape;
|
|
810
|
+
for (const [key, fieldSchema] of Object.entries(shape)) {
|
|
811
|
+
const properties = jsonObj?.properties;
|
|
812
|
+
const jsonProp = properties?.[key];
|
|
813
|
+
checkSchema(fieldSchema, jsonProp, path ? `${path}.${key}` : key);
|
|
814
|
+
}
|
|
815
|
+
}
|
|
816
|
+
if (def?.typeName === "ZodArray" && def?.type) {
|
|
817
|
+
checkSchema(def.type, jsonObj?.items, path ? `${path}[]` : "[]");
|
|
818
|
+
}
|
|
819
|
+
if ((def?.typeName === "ZodOptional" || def?.typeName === "ZodNullable") && def?.innerType) {
|
|
820
|
+
checkSchema(def.innerType, json, path);
|
|
821
|
+
}
|
|
822
|
+
if (def?.typeName === "ZodDefault" && def?.innerType) {
|
|
823
|
+
checkSchema(def.innerType, json, path);
|
|
824
|
+
}
|
|
825
|
+
}
|
|
826
|
+
checkSchema(schema, jsonSchema, "");
|
|
827
|
+
return mismatches;
|
|
828
|
+
}
|
|
829
|
+
function mergeDescriptions(schema, jsonSchema) {
|
|
830
|
+
function merge(zodSchema, json) {
|
|
831
|
+
if (!json || typeof json !== "object") return json;
|
|
832
|
+
const def = zodSchema._def;
|
|
833
|
+
const jsonObj = json;
|
|
834
|
+
const merged = { ...jsonObj };
|
|
835
|
+
if (def?.description && !jsonObj.description) {
|
|
836
|
+
merged.description = def.description;
|
|
837
|
+
}
|
|
838
|
+
if (def?.typeName === "ZodObject" && def?.shape && jsonObj.properties) {
|
|
839
|
+
const shape = typeof def.shape === "function" ? def.shape() : def.shape;
|
|
840
|
+
const properties = jsonObj.properties;
|
|
841
|
+
merged.properties = { ...properties };
|
|
842
|
+
for (const [key, fieldSchema] of Object.entries(shape)) {
|
|
843
|
+
if (properties[key]) {
|
|
844
|
+
merged.properties[key] = merge(fieldSchema, properties[key]);
|
|
845
|
+
}
|
|
846
|
+
}
|
|
847
|
+
}
|
|
848
|
+
if (def?.typeName === "ZodArray" && def?.type && jsonObj.items) {
|
|
849
|
+
merged.items = merge(def.type, jsonObj.items);
|
|
850
|
+
}
|
|
851
|
+
if ((def?.typeName === "ZodOptional" || def?.typeName === "ZodNullable") && def?.innerType) {
|
|
852
|
+
return merge(def.innerType, json);
|
|
853
|
+
}
|
|
854
|
+
if (def?.typeName === "ZodDefault" && def?.innerType) {
|
|
855
|
+
return merge(def.innerType, json);
|
|
856
|
+
}
|
|
857
|
+
return merged;
|
|
858
|
+
}
|
|
859
|
+
return merge(schema, jsonSchema);
|
|
860
|
+
}
|
|
861
|
+
var z2;
|
|
862
|
+
var init_schema_to_json = __esm({
|
|
863
|
+
"src/gadgets/schema-to-json.ts"() {
|
|
864
|
+
"use strict";
|
|
865
|
+
z2 = __toESM(require("zod"), 1);
|
|
866
|
+
init_logger();
|
|
867
|
+
}
|
|
868
|
+
});
|
|
869
|
+
|
|
870
|
+
// src/gadgets/gadget.ts
|
|
871
|
+
function findSafeDelimiter(content) {
|
|
872
|
+
const lines = content.split("\n");
|
|
873
|
+
for (const delimiter of HEREDOC_DELIMITERS) {
|
|
874
|
+
const regex = new RegExp(`^${delimiter}\\s*$`);
|
|
875
|
+
const isUsed = lines.some((line) => regex.test(line));
|
|
876
|
+
if (!isUsed) {
|
|
877
|
+
return delimiter;
|
|
878
|
+
}
|
|
879
|
+
}
|
|
880
|
+
let counter = 1;
|
|
881
|
+
while (counter < 1e3) {
|
|
882
|
+
const delimiter = `HEREDOC_${counter}`;
|
|
883
|
+
const regex = new RegExp(`^${delimiter}\\s*$`);
|
|
884
|
+
const isUsed = lines.some((line) => regex.test(line));
|
|
885
|
+
if (!isUsed) {
|
|
886
|
+
return delimiter;
|
|
887
|
+
}
|
|
888
|
+
counter++;
|
|
889
|
+
}
|
|
890
|
+
return "HEREDOC_FALLBACK";
|
|
891
|
+
}
|
|
892
|
+
function formatYamlValue(value, indent = "") {
|
|
893
|
+
if (typeof value === "string") {
|
|
894
|
+
const lines = value.split("\n");
|
|
895
|
+
if (lines.length === 1 && !value.includes(":") && !value.startsWith("-")) {
|
|
896
|
+
return value;
|
|
897
|
+
}
|
|
898
|
+
const delimiter = findSafeDelimiter(value);
|
|
899
|
+
return `<<<${delimiter}
|
|
900
|
+
${value}
|
|
901
|
+
${delimiter}`;
|
|
902
|
+
}
|
|
903
|
+
if (typeof value === "number" || typeof value === "boolean") {
|
|
904
|
+
return String(value);
|
|
905
|
+
}
|
|
906
|
+
if (value === null || value === void 0) {
|
|
907
|
+
return "null";
|
|
908
|
+
}
|
|
909
|
+
if (Array.isArray(value)) {
|
|
910
|
+
if (value.length === 0) return "[]";
|
|
911
|
+
const items = value.map((item) => `${indent}- ${formatYamlValue(item, indent + " ")}`);
|
|
912
|
+
return "\n" + items.join("\n");
|
|
913
|
+
}
|
|
914
|
+
if (typeof value === "object") {
|
|
915
|
+
const entries = Object.entries(value);
|
|
916
|
+
if (entries.length === 0) return "{}";
|
|
917
|
+
const lines = entries.map(([k, v]) => {
|
|
918
|
+
const formattedValue = formatYamlValue(v, indent + " ");
|
|
919
|
+
if (formattedValue.startsWith("\n") || formattedValue.startsWith("|")) {
|
|
920
|
+
return `${indent}${k}: ${formattedValue}`;
|
|
921
|
+
}
|
|
922
|
+
return `${indent}${k}: ${formattedValue}`;
|
|
923
|
+
});
|
|
924
|
+
return "\n" + lines.join("\n");
|
|
925
|
+
}
|
|
926
|
+
return yaml.dump(value).trimEnd();
|
|
927
|
+
}
|
|
928
|
+
function formatParamsAsYaml(params) {
|
|
929
|
+
const lines = [];
|
|
930
|
+
for (const [key, value] of Object.entries(params)) {
|
|
931
|
+
const formattedValue = formatYamlValue(value, "");
|
|
932
|
+
if (formattedValue.startsWith("\n")) {
|
|
933
|
+
lines.push(`${key}:${formattedValue}`);
|
|
934
|
+
} else {
|
|
935
|
+
lines.push(`${key}: ${formattedValue}`);
|
|
936
|
+
}
|
|
937
|
+
}
|
|
938
|
+
return lines.join("\n");
|
|
939
|
+
}
|
|
940
|
+
function formatTomlValue(value) {
|
|
941
|
+
if (typeof value === "string") {
|
|
942
|
+
if (value.includes("\n")) {
|
|
943
|
+
const delimiter = findSafeDelimiter(value);
|
|
944
|
+
return `<<<${delimiter}
|
|
945
|
+
${value}
|
|
946
|
+
${delimiter}`;
|
|
947
|
+
}
|
|
948
|
+
return JSON.stringify(value);
|
|
949
|
+
}
|
|
950
|
+
if (typeof value === "number" || typeof value === "boolean") {
|
|
951
|
+
return String(value);
|
|
952
|
+
}
|
|
953
|
+
if (value === null || value === void 0) {
|
|
954
|
+
return '""';
|
|
955
|
+
}
|
|
956
|
+
if (Array.isArray(value)) {
|
|
957
|
+
return JSON.stringify(value);
|
|
958
|
+
}
|
|
959
|
+
if (typeof value === "object") {
|
|
960
|
+
return JSON.stringify(value);
|
|
961
|
+
}
|
|
962
|
+
return JSON.stringify(value);
|
|
963
|
+
}
|
|
964
|
+
function formatParamsAsToml(params) {
|
|
965
|
+
const lines = [];
|
|
966
|
+
for (const [key, value] of Object.entries(params)) {
|
|
967
|
+
lines.push(`${key} = ${formatTomlValue(value)}`);
|
|
968
|
+
}
|
|
969
|
+
return lines.join("\n");
|
|
970
|
+
}
|
|
971
|
+
var yaml, HEREDOC_DELIMITERS, BaseGadget;
|
|
972
|
+
var init_gadget = __esm({
|
|
973
|
+
"src/gadgets/gadget.ts"() {
|
|
974
|
+
"use strict";
|
|
975
|
+
yaml = __toESM(require("js-yaml"), 1);
|
|
976
|
+
init_schema_to_json();
|
|
977
|
+
init_schema_validator();
|
|
978
|
+
HEREDOC_DELIMITERS = ["EOF", "END", "DOC", "CONTENT", "TEXT", "HEREDOC", "DATA", "BLOCK"];
|
|
979
|
+
BaseGadget = class {
|
|
980
|
+
/**
|
|
981
|
+
* The name of the gadget. Used for identification when LLM calls it.
|
|
982
|
+
* If not provided, defaults to the class name.
|
|
983
|
+
*/
|
|
984
|
+
name;
|
|
985
|
+
/**
|
|
986
|
+
* Optional Zod schema describing the expected input payload. When provided,
|
|
987
|
+
* it will be validated before execution and transformed into a JSON Schema
|
|
988
|
+
* representation that is surfaced to the LLM as part of the instructions.
|
|
989
|
+
*/
|
|
990
|
+
parameterSchema;
|
|
991
|
+
/**
|
|
992
|
+
* Optional timeout in milliseconds for gadget execution.
|
|
993
|
+
* If execution exceeds this timeout, a TimeoutException will be thrown.
|
|
994
|
+
* If not set, the global defaultGadgetTimeoutMs from runtime options will be used.
|
|
995
|
+
* Set to 0 or undefined to disable timeout for this gadget.
|
|
996
|
+
*/
|
|
997
|
+
timeoutMs;
|
|
998
|
+
/**
|
|
999
|
+
* Optional usage examples to help LLMs understand proper invocation.
|
|
1000
|
+
* Examples are rendered in getInstruction() alongside the schema.
|
|
1001
|
+
*
|
|
1002
|
+
* Note: Uses broader `unknown` type to allow typed examples from subclasses
|
|
1003
|
+
* while maintaining runtime compatibility.
|
|
1004
|
+
*/
|
|
1005
|
+
examples;
|
|
1006
|
+
/**
|
|
1007
|
+
* Auto-generated instruction text for the LLM.
|
|
1008
|
+
* Combines name, description, and parameter schema into a formatted instruction.
|
|
1009
|
+
* @deprecated Use getInstruction(format) instead for format-specific schemas
|
|
1010
|
+
*/
|
|
1011
|
+
get instruction() {
|
|
1012
|
+
return this.getInstruction("yaml");
|
|
1013
|
+
}
|
|
1014
|
+
/**
|
|
1015
|
+
* Generate instruction text for the LLM with format-specific schema.
|
|
1016
|
+
* Combines name, description, and parameter schema into a formatted instruction.
|
|
1017
|
+
*
|
|
1018
|
+
* @param format - Format for the schema representation ('json' | 'yaml' | 'toml' | 'auto')
|
|
1019
|
+
* @returns Formatted instruction string
|
|
1020
|
+
*/
|
|
1021
|
+
getInstruction(format = "json") {
|
|
1022
|
+
const parts = [];
|
|
1023
|
+
parts.push(this.description);
|
|
1024
|
+
if (this.parameterSchema) {
|
|
1025
|
+
const gadgetName = this.name ?? this.constructor.name;
|
|
1026
|
+
validateGadgetSchema(this.parameterSchema, gadgetName);
|
|
1027
|
+
const jsonSchema = schemaToJSONSchema(this.parameterSchema, {
|
|
1028
|
+
target: "draft-7"
|
|
1029
|
+
});
|
|
1030
|
+
if (format === "json" || format === "auto") {
|
|
1031
|
+
parts.push("\n\nInput Schema (JSON):");
|
|
1032
|
+
parts.push(JSON.stringify(jsonSchema, null, 2));
|
|
1033
|
+
} else if (format === "toml") {
|
|
1034
|
+
parts.push("\n\nInput Schema (TOML):");
|
|
1035
|
+
parts.push(JSON.stringify(jsonSchema, null, 2));
|
|
1036
|
+
} else {
|
|
1037
|
+
const yamlSchema = yaml.dump(jsonSchema).trimEnd();
|
|
1038
|
+
parts.push("\n\nInput Schema (YAML):");
|
|
1039
|
+
parts.push(yamlSchema);
|
|
1040
|
+
}
|
|
1041
|
+
}
|
|
1042
|
+
if (this.examples && this.examples.length > 0) {
|
|
1043
|
+
parts.push("\n\nExamples:");
|
|
1044
|
+
this.examples.forEach((example, index) => {
|
|
1045
|
+
if (index > 0) {
|
|
1046
|
+
parts.push("");
|
|
1047
|
+
}
|
|
1048
|
+
if (example.comment) {
|
|
1049
|
+
parts.push(`# ${example.comment}`);
|
|
1050
|
+
}
|
|
1051
|
+
parts.push("Input:");
|
|
1052
|
+
if (format === "json" || format === "auto") {
|
|
1053
|
+
parts.push(JSON.stringify(example.params, null, 2));
|
|
1054
|
+
} else if (format === "toml") {
|
|
1055
|
+
parts.push(formatParamsAsToml(example.params));
|
|
1056
|
+
} else {
|
|
1057
|
+
parts.push(formatParamsAsYaml(example.params));
|
|
1058
|
+
}
|
|
1059
|
+
if (example.output !== void 0) {
|
|
1060
|
+
parts.push("Output:");
|
|
1061
|
+
parts.push(example.output);
|
|
1062
|
+
}
|
|
1063
|
+
});
|
|
1064
|
+
}
|
|
1065
|
+
return parts.join("\n");
|
|
1066
|
+
}
|
|
1067
|
+
};
|
|
1068
|
+
}
|
|
1069
|
+
});
|
|
1070
|
+
|
|
1071
|
+
// src/gadgets/create-gadget.ts
|
|
1072
|
+
function createGadget(config) {
|
|
1073
|
+
class DynamicGadget extends BaseGadget {
|
|
1074
|
+
name = config.name;
|
|
1075
|
+
description = config.description;
|
|
1076
|
+
parameterSchema = config.schema;
|
|
1077
|
+
timeoutMs = config.timeoutMs;
|
|
1078
|
+
examples = config.examples;
|
|
1079
|
+
execute(params) {
|
|
1080
|
+
return config.execute(params);
|
|
1081
|
+
}
|
|
1082
|
+
}
|
|
1083
|
+
return new DynamicGadget();
|
|
1084
|
+
}
|
|
1085
|
+
var init_create_gadget = __esm({
|
|
1086
|
+
"src/gadgets/create-gadget.ts"() {
|
|
1087
|
+
"use strict";
|
|
1088
|
+
init_gadget();
|
|
1089
|
+
}
|
|
1090
|
+
});
|
|
1091
|
+
|
|
1092
|
+
// src/gadgets/output-viewer.ts
|
|
1093
|
+
function applyPattern(lines, pattern) {
|
|
1094
|
+
const regex = new RegExp(pattern.regex);
|
|
1095
|
+
if (!pattern.include) {
|
|
1096
|
+
return lines.filter((line) => !regex.test(line));
|
|
1097
|
+
}
|
|
1098
|
+
const matchIndices = /* @__PURE__ */ new Set();
|
|
1099
|
+
for (let i = 0; i < lines.length; i++) {
|
|
1100
|
+
if (regex.test(lines[i])) {
|
|
1101
|
+
const start = Math.max(0, i - pattern.before);
|
|
1102
|
+
const end = Math.min(lines.length - 1, i + pattern.after);
|
|
1103
|
+
for (let j = start; j <= end; j++) {
|
|
1104
|
+
matchIndices.add(j);
|
|
1105
|
+
}
|
|
1106
|
+
}
|
|
1107
|
+
}
|
|
1108
|
+
return lines.filter((_, index) => matchIndices.has(index));
|
|
1109
|
+
}
|
|
1110
|
+
function applyPatterns(lines, patterns) {
|
|
1111
|
+
let result = lines;
|
|
1112
|
+
for (const pattern of patterns) {
|
|
1113
|
+
result = applyPattern(result, pattern);
|
|
1114
|
+
}
|
|
1115
|
+
return result;
|
|
1116
|
+
}
|
|
1117
|
+
function applyLineLimit(lines, limit) {
|
|
1118
|
+
const trimmed = limit.trim();
|
|
1119
|
+
if (trimmed.endsWith("-") && !trimmed.startsWith("-")) {
|
|
1120
|
+
const n = parseInt(trimmed.slice(0, -1), 10);
|
|
1121
|
+
if (!isNaN(n) && n > 0) {
|
|
1122
|
+
return lines.slice(0, n);
|
|
1123
|
+
}
|
|
1124
|
+
}
|
|
1125
|
+
if (trimmed.startsWith("-") && !trimmed.includes("-", 1)) {
|
|
1126
|
+
const n = parseInt(trimmed, 10);
|
|
1127
|
+
if (!isNaN(n) && n < 0) {
|
|
1128
|
+
return lines.slice(n);
|
|
1129
|
+
}
|
|
1130
|
+
}
|
|
1131
|
+
const rangeMatch = trimmed.match(/^(\d+)-(\d+)$/);
|
|
1132
|
+
if (rangeMatch) {
|
|
1133
|
+
const start = parseInt(rangeMatch[1], 10);
|
|
1134
|
+
const end = parseInt(rangeMatch[2], 10);
|
|
1135
|
+
if (!isNaN(start) && !isNaN(end) && start > 0 && end >= start) {
|
|
1136
|
+
return lines.slice(start - 1, end);
|
|
1137
|
+
}
|
|
1138
|
+
}
|
|
1139
|
+
return lines;
|
|
1140
|
+
}
|
|
1141
|
+
function createGadgetOutputViewer(store) {
|
|
1142
|
+
return createGadget({
|
|
1143
|
+
name: "GadgetOutputViewer",
|
|
1144
|
+
description: "View stored output from gadgets that returned too much data. Use patterns to filter lines (like grep) and limit to control output size. Patterns are applied first in order, then the limit is applied to the result.",
|
|
1145
|
+
schema: import_zod.z.object({
|
|
1146
|
+
id: import_zod.z.string().describe("ID of the stored output (from the truncation message)"),
|
|
1147
|
+
patterns: import_zod.z.array(patternSchema).optional().describe(
|
|
1148
|
+
"Filter patterns applied in order (like piping through grep). Each pattern can include or exclude lines with optional before/after context."
|
|
1149
|
+
),
|
|
1150
|
+
limit: import_zod.z.string().optional().describe(
|
|
1151
|
+
"Line range to return after filtering. Formats: '100-' (first 100), '-25' (last 25), '50-100' (lines 50-100)"
|
|
1152
|
+
)
|
|
1153
|
+
}),
|
|
1154
|
+
examples: [
|
|
1155
|
+
{
|
|
1156
|
+
comment: "View first 50 lines of stored output",
|
|
1157
|
+
params: { id: "Search_abc12345", limit: "50-" }
|
|
1158
|
+
},
|
|
1159
|
+
{
|
|
1160
|
+
comment: "Filter for error lines with context",
|
|
1161
|
+
params: {
|
|
1162
|
+
id: "Search_abc12345",
|
|
1163
|
+
patterns: [{ regex: "error|Error|ERROR", include: true, before: 2, after: 5 }]
|
|
1164
|
+
}
|
|
1165
|
+
},
|
|
1166
|
+
{
|
|
1167
|
+
comment: "Exclude blank lines, then show first 100",
|
|
1168
|
+
params: {
|
|
1169
|
+
id: "Search_abc12345",
|
|
1170
|
+
patterns: [{ regex: "^\\s*$", include: false, before: 0, after: 0 }],
|
|
1171
|
+
limit: "100-"
|
|
1172
|
+
}
|
|
1173
|
+
},
|
|
1174
|
+
{
|
|
1175
|
+
comment: "Chain filters: find TODOs, exclude tests, limit to 50 lines",
|
|
1176
|
+
params: {
|
|
1177
|
+
id: "Search_abc12345",
|
|
1178
|
+
patterns: [
|
|
1179
|
+
{ regex: "TODO", include: true, before: 1, after: 1 },
|
|
1180
|
+
{ regex: "test|spec", include: false, before: 0, after: 0 }
|
|
1181
|
+
],
|
|
1182
|
+
limit: "50-"
|
|
1183
|
+
}
|
|
1184
|
+
}
|
|
1185
|
+
],
|
|
1186
|
+
execute: ({ id, patterns, limit }) => {
|
|
1187
|
+
const stored = store.get(id);
|
|
1188
|
+
if (!stored) {
|
|
1189
|
+
return `Error: No stored output with id "${id}". Available IDs: ${store.getIds().join(", ") || "(none)"}`;
|
|
1190
|
+
}
|
|
1191
|
+
let lines = stored.content.split("\n");
|
|
1192
|
+
if (patterns && patterns.length > 0) {
|
|
1193
|
+
lines = applyPatterns(
|
|
1194
|
+
lines,
|
|
1195
|
+
patterns.map((p) => ({
|
|
1196
|
+
regex: p.regex,
|
|
1197
|
+
include: p.include ?? true,
|
|
1198
|
+
before: p.before ?? 0,
|
|
1199
|
+
after: p.after ?? 0
|
|
1200
|
+
}))
|
|
1201
|
+
);
|
|
1202
|
+
}
|
|
1203
|
+
if (limit) {
|
|
1204
|
+
lines = applyLineLimit(lines, limit);
|
|
1205
|
+
}
|
|
1206
|
+
const totalLines = stored.lineCount;
|
|
1207
|
+
const returnedLines = lines.length;
|
|
1208
|
+
if (returnedLines === 0) {
|
|
1209
|
+
return `No lines matched the filters. Original output had ${totalLines} lines.`;
|
|
1210
|
+
}
|
|
1211
|
+
const header = returnedLines < totalLines ? `[Showing ${returnedLines} of ${totalLines} lines]
|
|
1212
|
+
` : `[Showing all ${totalLines} lines]
|
|
1213
|
+
`;
|
|
1214
|
+
return header + lines.join("\n");
|
|
1215
|
+
}
|
|
1216
|
+
});
|
|
1217
|
+
}
|
|
1218
|
+
var import_zod, patternSchema;
|
|
1219
|
+
var init_output_viewer = __esm({
|
|
1220
|
+
"src/gadgets/output-viewer.ts"() {
|
|
1221
|
+
"use strict";
|
|
1222
|
+
import_zod = require("zod");
|
|
1223
|
+
init_create_gadget();
|
|
1224
|
+
patternSchema = import_zod.z.object({
|
|
1225
|
+
regex: import_zod.z.string().describe("Regular expression to match"),
|
|
1226
|
+
include: import_zod.z.boolean().default(true).describe("true = keep matching lines, false = exclude matching lines"),
|
|
1227
|
+
before: import_zod.z.number().int().min(0).default(0).describe("Context lines before each match (like grep -B)"),
|
|
1228
|
+
after: import_zod.z.number().int().min(0).default(0).describe("Context lines after each match (like grep -A)")
|
|
1229
|
+
});
|
|
1230
|
+
}
|
|
1231
|
+
});
|
|
1232
|
+
|
|
1233
|
+
// src/agent/gadget-output-store.ts
|
|
1234
|
+
var import_node_crypto, GadgetOutputStore;
|
|
1235
|
+
var init_gadget_output_store = __esm({
|
|
1236
|
+
"src/agent/gadget-output-store.ts"() {
|
|
1237
|
+
"use strict";
|
|
1238
|
+
import_node_crypto = require("crypto");
|
|
1239
|
+
GadgetOutputStore = class {
|
|
1240
|
+
outputs = /* @__PURE__ */ new Map();
|
|
1241
|
+
/**
|
|
1242
|
+
* Store a gadget output and return its ID.
|
|
1243
|
+
*
|
|
1244
|
+
* @param gadgetName - Name of the gadget that produced the output
|
|
1245
|
+
* @param content - Full output content to store
|
|
1246
|
+
* @returns Generated ID for retrieving the output later
|
|
1247
|
+
*/
|
|
1248
|
+
store(gadgetName, content) {
|
|
1249
|
+
const id = this.generateId(gadgetName);
|
|
1250
|
+
const encoder = new TextEncoder();
|
|
1251
|
+
const stored = {
|
|
1252
|
+
id,
|
|
1253
|
+
gadgetName,
|
|
1254
|
+
content,
|
|
1255
|
+
byteSize: encoder.encode(content).length,
|
|
1256
|
+
lineCount: content.split("\n").length,
|
|
1257
|
+
timestamp: /* @__PURE__ */ new Date()
|
|
1258
|
+
};
|
|
1259
|
+
this.outputs.set(id, stored);
|
|
1260
|
+
return id;
|
|
1261
|
+
}
|
|
1262
|
+
/**
|
|
1263
|
+
* Retrieve a stored output by ID.
|
|
1264
|
+
*
|
|
1265
|
+
* @param id - The output ID (e.g., "Search_d34db33f")
|
|
1266
|
+
* @returns The stored output or undefined if not found
|
|
1267
|
+
*/
|
|
1268
|
+
get(id) {
|
|
1269
|
+
return this.outputs.get(id);
|
|
1270
|
+
}
|
|
1271
|
+
/**
|
|
1272
|
+
* Check if an output exists.
|
|
1273
|
+
*
|
|
1274
|
+
* @param id - The output ID to check
|
|
1275
|
+
* @returns True if the output exists
|
|
1276
|
+
*/
|
|
1277
|
+
has(id) {
|
|
1278
|
+
return this.outputs.has(id);
|
|
1279
|
+
}
|
|
1280
|
+
/**
|
|
1281
|
+
* Get all stored output IDs.
|
|
1282
|
+
*
|
|
1283
|
+
* @returns Array of output IDs
|
|
1284
|
+
*/
|
|
1285
|
+
getIds() {
|
|
1286
|
+
return Array.from(this.outputs.keys());
|
|
1287
|
+
}
|
|
1288
|
+
/**
|
|
1289
|
+
* Get the number of stored outputs.
|
|
1290
|
+
*/
|
|
1291
|
+
get size() {
|
|
1292
|
+
return this.outputs.size;
|
|
1293
|
+
}
|
|
1294
|
+
/**
|
|
1295
|
+
* Clear all stored outputs.
|
|
1296
|
+
* Called when the agent run completes.
|
|
1297
|
+
*/
|
|
1298
|
+
clear() {
|
|
1299
|
+
this.outputs.clear();
|
|
1300
|
+
}
|
|
1301
|
+
/**
|
|
1302
|
+
* Generate a unique ID for a stored output.
|
|
1303
|
+
* Format: {GadgetName}_{8 hex chars}
|
|
1304
|
+
*/
|
|
1305
|
+
generateId(gadgetName) {
|
|
1306
|
+
const hex = (0, import_node_crypto.randomBytes)(4).toString("hex");
|
|
1307
|
+
return `${gadgetName}_${hex}`;
|
|
1308
|
+
}
|
|
1309
|
+
};
|
|
1310
|
+
}
|
|
1311
|
+
});
|
|
1312
|
+
|
|
771
1313
|
// src/agent/agent-internal-key.ts
|
|
772
1314
|
function isValidAgentKey(key) {
|
|
773
1315
|
return key === AGENT_INTERNAL_KEY;
|
|
@@ -1305,6 +1847,25 @@ function preprocessYaml(yamlStr) {
|
|
|
1305
1847
|
let i = 0;
|
|
1306
1848
|
while (i < lines.length) {
|
|
1307
1849
|
const line = lines[i];
|
|
1850
|
+
const heredocMatch = line.match(/^(\s*)([\w-]+):\s*<<<([A-Za-z_][A-Za-z0-9_]*)\s*$/);
|
|
1851
|
+
if (heredocMatch) {
|
|
1852
|
+
const [, indent, key, delimiter] = heredocMatch;
|
|
1853
|
+
const bodyLines = [];
|
|
1854
|
+
i++;
|
|
1855
|
+
const closingRegex = new RegExp(`^${delimiter}\\s*$`);
|
|
1856
|
+
while (i < lines.length && !closingRegex.test(lines[i])) {
|
|
1857
|
+
bodyLines.push(lines[i]);
|
|
1858
|
+
i++;
|
|
1859
|
+
}
|
|
1860
|
+
if (i < lines.length) {
|
|
1861
|
+
i++;
|
|
1862
|
+
}
|
|
1863
|
+
result.push(`${indent}${key}: |`);
|
|
1864
|
+
for (const bodyLine of bodyLines) {
|
|
1865
|
+
result.push(`${indent} ${bodyLine}`);
|
|
1866
|
+
}
|
|
1867
|
+
continue;
|
|
1868
|
+
}
|
|
1308
1869
|
const match = line.match(/^(\s*)([\w-]+):\s+(.+)$/);
|
|
1309
1870
|
if (match) {
|
|
1310
1871
|
const [, indent, key, value] = match;
|
|
@@ -1396,11 +1957,53 @@ function preprocessYaml(yamlStr) {
|
|
|
1396
1957
|
}
|
|
1397
1958
|
return result.join("\n");
|
|
1398
1959
|
}
|
|
1399
|
-
|
|
1960
|
+
function preprocessTomlHeredoc(tomlStr) {
|
|
1961
|
+
const lines = tomlStr.split("\n");
|
|
1962
|
+
const result = [];
|
|
1963
|
+
let i = 0;
|
|
1964
|
+
const heredocStartRegex = /^(\s*)([\w-]+)\s*=\s*<<<([A-Za-z_][A-Za-z0-9_]*)\s*$/;
|
|
1965
|
+
while (i < lines.length) {
|
|
1966
|
+
const line = lines[i];
|
|
1967
|
+
const match = line.match(heredocStartRegex);
|
|
1968
|
+
if (match) {
|
|
1969
|
+
const [, indent, key, delimiter] = match;
|
|
1970
|
+
const bodyLines = [];
|
|
1971
|
+
i++;
|
|
1972
|
+
const closingRegex = new RegExp(`^${delimiter}\\s*$`);
|
|
1973
|
+
let foundClosing = false;
|
|
1974
|
+
while (i < lines.length) {
|
|
1975
|
+
const bodyLine = lines[i];
|
|
1976
|
+
if (closingRegex.test(bodyLine)) {
|
|
1977
|
+
foundClosing = true;
|
|
1978
|
+
i++;
|
|
1979
|
+
break;
|
|
1980
|
+
}
|
|
1981
|
+
bodyLines.push(bodyLine);
|
|
1982
|
+
i++;
|
|
1983
|
+
}
|
|
1984
|
+
if (bodyLines.length === 0) {
|
|
1985
|
+
result.push(`${indent}${key} = """"""`);
|
|
1986
|
+
} else {
|
|
1987
|
+
result.push(`${indent}${key} = """`);
|
|
1988
|
+
for (let j = 0; j < bodyLines.length - 1; j++) {
|
|
1989
|
+
result.push(bodyLines[j]);
|
|
1990
|
+
}
|
|
1991
|
+
result.push(`${bodyLines[bodyLines.length - 1]}"""`);
|
|
1992
|
+
}
|
|
1993
|
+
if (!foundClosing) {
|
|
1994
|
+
}
|
|
1995
|
+
continue;
|
|
1996
|
+
}
|
|
1997
|
+
result.push(line);
|
|
1998
|
+
i++;
|
|
1999
|
+
}
|
|
2000
|
+
return result.join("\n");
|
|
2001
|
+
}
|
|
2002
|
+
var yaml2, import_js_toml, globalInvocationCounter, StreamParser;
|
|
1400
2003
|
var init_parser = __esm({
|
|
1401
2004
|
"src/gadgets/parser.ts"() {
|
|
1402
2005
|
"use strict";
|
|
1403
|
-
|
|
2006
|
+
yaml2 = __toESM(require("js-yaml"), 1);
|
|
1404
2007
|
import_js_toml = require("js-toml");
|
|
1405
2008
|
init_constants();
|
|
1406
2009
|
globalInvocationCounter = 0;
|
|
@@ -1447,14 +2050,14 @@ var init_parser = __esm({
|
|
|
1447
2050
|
}
|
|
1448
2051
|
if (this.parameterFormat === "yaml") {
|
|
1449
2052
|
try {
|
|
1450
|
-
return { parameters:
|
|
2053
|
+
return { parameters: yaml2.load(preprocessYaml(raw)) };
|
|
1451
2054
|
} catch (error) {
|
|
1452
2055
|
return { parseError: error instanceof Error ? error.message : "Failed to parse YAML" };
|
|
1453
2056
|
}
|
|
1454
2057
|
}
|
|
1455
2058
|
if (this.parameterFormat === "toml") {
|
|
1456
2059
|
try {
|
|
1457
|
-
return { parameters: (0, import_js_toml.load)(raw) };
|
|
2060
|
+
return { parameters: (0, import_js_toml.load)(preprocessTomlHeredoc(raw)) };
|
|
1458
2061
|
} catch (error) {
|
|
1459
2062
|
return { parseError: error instanceof Error ? error.message : "Failed to parse TOML" };
|
|
1460
2063
|
}
|
|
@@ -1463,10 +2066,10 @@ var init_parser = __esm({
|
|
|
1463
2066
|
return { parameters: JSON.parse(raw) };
|
|
1464
2067
|
} catch {
|
|
1465
2068
|
try {
|
|
1466
|
-
return { parameters: (0, import_js_toml.load)(raw) };
|
|
2069
|
+
return { parameters: (0, import_js_toml.load)(preprocessTomlHeredoc(raw)) };
|
|
1467
2070
|
} catch {
|
|
1468
2071
|
try {
|
|
1469
|
-
return { parameters:
|
|
2072
|
+
return { parameters: yaml2.load(preprocessYaml(raw)) };
|
|
1470
2073
|
} catch (error) {
|
|
1471
2074
|
return {
|
|
1472
2075
|
parseError: error instanceof Error ? error.message : "Failed to parse as JSON, TOML, or YAML"
|
|
@@ -1988,9 +2591,12 @@ var Agent;
|
|
|
1988
2591
|
var init_agent = __esm({
|
|
1989
2592
|
"src/agent/agent.ts"() {
|
|
1990
2593
|
"use strict";
|
|
2594
|
+
init_constants();
|
|
1991
2595
|
init_messages();
|
|
1992
2596
|
init_model_shortcuts();
|
|
2597
|
+
init_output_viewer();
|
|
1993
2598
|
init_logger();
|
|
2599
|
+
init_gadget_output_store();
|
|
1994
2600
|
init_agent_internal_key();
|
|
1995
2601
|
init_conversation_manager();
|
|
1996
2602
|
init_event_handlers();
|
|
@@ -2015,6 +2621,10 @@ var init_agent = __esm({
|
|
|
2015
2621
|
defaultGadgetTimeoutMs;
|
|
2016
2622
|
defaultMaxTokens;
|
|
2017
2623
|
userPromptProvided;
|
|
2624
|
+
// Gadget output limiting
|
|
2625
|
+
outputStore;
|
|
2626
|
+
outputLimitEnabled;
|
|
2627
|
+
outputLimitCharLimit;
|
|
2018
2628
|
/**
|
|
2019
2629
|
* Creates a new Agent instance.
|
|
2020
2630
|
* @internal This constructor is private. Use LLMist.createAgent() or AgentBuilder instead.
|
|
@@ -2030,7 +2640,6 @@ var init_agent = __esm({
|
|
|
2030
2640
|
this.maxIterations = options.maxIterations ?? 10;
|
|
2031
2641
|
this.temperature = options.temperature;
|
|
2032
2642
|
this.logger = options.logger ?? createLogger({ name: "llmist:agent" });
|
|
2033
|
-
this.hooks = options.hooks ?? {};
|
|
2034
2643
|
this.registry = options.registry;
|
|
2035
2644
|
this.parameterFormat = options.parameterFormat ?? "json";
|
|
2036
2645
|
this.gadgetStartPrefix = options.gadgetStartPrefix;
|
|
@@ -2041,6 +2650,16 @@ var init_agent = __esm({
|
|
|
2041
2650
|
this.shouldContinueAfterError = options.shouldContinueAfterError;
|
|
2042
2651
|
this.defaultGadgetTimeoutMs = options.defaultGadgetTimeoutMs;
|
|
2043
2652
|
this.defaultMaxTokens = this.resolveMaxTokensFromCatalog(options.model);
|
|
2653
|
+
this.outputLimitEnabled = options.gadgetOutputLimit ?? DEFAULT_GADGET_OUTPUT_LIMIT;
|
|
2654
|
+
this.outputStore = new GadgetOutputStore();
|
|
2655
|
+
const limitPercent = options.gadgetOutputLimitPercent ?? DEFAULT_GADGET_OUTPUT_LIMIT_PERCENT;
|
|
2656
|
+
const limits = this.client.modelRegistry.getModelLimits(this.model);
|
|
2657
|
+
const contextWindow = limits?.contextWindow ?? FALLBACK_CONTEXT_WINDOW;
|
|
2658
|
+
this.outputLimitCharLimit = Math.floor(contextWindow * (limitPercent / 100) * CHARS_PER_TOKEN);
|
|
2659
|
+
if (this.outputLimitEnabled) {
|
|
2660
|
+
this.registry.register("GadgetOutputViewer", createGadgetOutputViewer(this.outputStore));
|
|
2661
|
+
}
|
|
2662
|
+
this.hooks = this.mergeOutputLimiterHook(options.hooks);
|
|
2044
2663
|
const baseBuilder = new LLMMessageBuilder(options.promptConfig);
|
|
2045
2664
|
if (options.systemPrompt) {
|
|
2046
2665
|
baseBuilder.addSystem(options.systemPrompt);
|
|
@@ -2345,6 +2964,43 @@ var init_agent = __esm({
|
|
|
2345
2964
|
}
|
|
2346
2965
|
return this.client.modelRegistry.getModelLimits(unprefixedModelId)?.maxOutputTokens;
|
|
2347
2966
|
}
|
|
2967
|
+
/**
|
|
2968
|
+
* Merge the output limiter interceptor into user-provided hooks.
|
|
2969
|
+
* The limiter runs first, then chains to any user interceptor.
|
|
2970
|
+
*/
|
|
2971
|
+
mergeOutputLimiterHook(userHooks) {
|
|
2972
|
+
if (!this.outputLimitEnabled) {
|
|
2973
|
+
return userHooks ?? {};
|
|
2974
|
+
}
|
|
2975
|
+
const limiterInterceptor = (result, ctx) => {
|
|
2976
|
+
if (ctx.gadgetName === "GadgetOutputViewer") {
|
|
2977
|
+
return result;
|
|
2978
|
+
}
|
|
2979
|
+
if (result.length > this.outputLimitCharLimit) {
|
|
2980
|
+
const id = this.outputStore.store(ctx.gadgetName, result);
|
|
2981
|
+
const lines = result.split("\n").length;
|
|
2982
|
+
const bytes = new TextEncoder().encode(result).length;
|
|
2983
|
+
this.logger.info("Gadget output exceeded limit, stored for browsing", {
|
|
2984
|
+
gadgetName: ctx.gadgetName,
|
|
2985
|
+
outputId: id,
|
|
2986
|
+
bytes,
|
|
2987
|
+
lines,
|
|
2988
|
+
charLimit: this.outputLimitCharLimit
|
|
2989
|
+
});
|
|
2990
|
+
return `[Gadget "${ctx.gadgetName}" returned too much data: ${bytes.toLocaleString()} bytes, ${lines.toLocaleString()} lines. Use GadgetOutputViewer with id "${id}" to read it]`;
|
|
2991
|
+
}
|
|
2992
|
+
return result;
|
|
2993
|
+
};
|
|
2994
|
+
const userInterceptor = userHooks?.interceptors?.interceptGadgetResult;
|
|
2995
|
+
const chainedInterceptor = userInterceptor ? (result, ctx) => userInterceptor(limiterInterceptor(result, ctx), ctx) : limiterInterceptor;
|
|
2996
|
+
return {
|
|
2997
|
+
...userHooks,
|
|
2998
|
+
interceptors: {
|
|
2999
|
+
...userHooks?.interceptors,
|
|
3000
|
+
interceptGadgetResult: chainedInterceptor
|
|
3001
|
+
}
|
|
3002
|
+
};
|
|
3003
|
+
}
|
|
2348
3004
|
/**
|
|
2349
3005
|
* Run agent with named event handlers (syntactic sugar).
|
|
2350
3006
|
*
|
|
@@ -4086,6 +4742,8 @@ var init_builder = __esm({
|
|
|
4086
4742
|
stopOnGadgetError;
|
|
4087
4743
|
shouldContinueAfterError;
|
|
4088
4744
|
defaultGadgetTimeoutMs;
|
|
4745
|
+
gadgetOutputLimit;
|
|
4746
|
+
gadgetOutputLimitPercent;
|
|
4089
4747
|
constructor(client) {
|
|
4090
4748
|
this.client = client;
|
|
4091
4749
|
}
|
|
@@ -4418,6 +5076,45 @@ var init_builder = __esm({
|
|
|
4418
5076
|
this.defaultGadgetTimeoutMs = timeoutMs;
|
|
4419
5077
|
return this;
|
|
4420
5078
|
}
|
|
5079
|
+
/**
|
|
5080
|
+
* Enable or disable gadget output limiting.
|
|
5081
|
+
*
|
|
5082
|
+
* When enabled, gadget outputs exceeding the configured limit are stored
|
|
5083
|
+
* and can be browsed using the GadgetOutputViewer gadget.
|
|
5084
|
+
*
|
|
5085
|
+
* @param enabled - Whether to enable output limiting (default: true)
|
|
5086
|
+
* @returns This builder for chaining
|
|
5087
|
+
*
|
|
5088
|
+
* @example
|
|
5089
|
+
* ```typescript
|
|
5090
|
+
* .withGadgetOutputLimit(false) // Disable output limiting
|
|
5091
|
+
* ```
|
|
5092
|
+
*/
|
|
5093
|
+
withGadgetOutputLimit(enabled) {
|
|
5094
|
+
this.gadgetOutputLimit = enabled;
|
|
5095
|
+
return this;
|
|
5096
|
+
}
|
|
5097
|
+
/**
|
|
5098
|
+
* Set the maximum gadget output as a percentage of the model's context window.
|
|
5099
|
+
*
|
|
5100
|
+
* Outputs exceeding this limit are stored for later browsing with GadgetOutputViewer.
|
|
5101
|
+
*
|
|
5102
|
+
* @param percent - Percentage of context window (1-100, default: 15)
|
|
5103
|
+
* @returns This builder for chaining
|
|
5104
|
+
* @throws {Error} If percent is not between 1 and 100
|
|
5105
|
+
*
|
|
5106
|
+
* @example
|
|
5107
|
+
* ```typescript
|
|
5108
|
+
* .withGadgetOutputLimitPercent(25) // 25% of context window
|
|
5109
|
+
* ```
|
|
5110
|
+
*/
|
|
5111
|
+
withGadgetOutputLimitPercent(percent) {
|
|
5112
|
+
if (percent < 1 || percent > 100) {
|
|
5113
|
+
throw new Error("Output limit percent must be between 1 and 100");
|
|
5114
|
+
}
|
|
5115
|
+
this.gadgetOutputLimitPercent = percent;
|
|
5116
|
+
return this;
|
|
5117
|
+
}
|
|
4421
5118
|
/**
|
|
4422
5119
|
* Build and create the agent with the given user prompt.
|
|
4423
5120
|
* Returns the Agent instance ready to run.
|
|
@@ -4462,7 +5159,9 @@ var init_builder = __esm({
|
|
|
4462
5159
|
textOnlyHandler: this.textOnlyHandler,
|
|
4463
5160
|
stopOnGadgetError: this.stopOnGadgetError,
|
|
4464
5161
|
shouldContinueAfterError: this.shouldContinueAfterError,
|
|
4465
|
-
defaultGadgetTimeoutMs: this.defaultGadgetTimeoutMs
|
|
5162
|
+
defaultGadgetTimeoutMs: this.defaultGadgetTimeoutMs,
|
|
5163
|
+
gadgetOutputLimit: this.gadgetOutputLimit,
|
|
5164
|
+
gadgetOutputLimitPercent: this.gadgetOutputLimitPercent
|
|
4466
5165
|
};
|
|
4467
5166
|
return new Agent(AGENT_INTERNAL_KEY, options);
|
|
4468
5167
|
}
|
|
@@ -4561,7 +5260,9 @@ var init_builder = __esm({
|
|
|
4561
5260
|
textOnlyHandler: this.textOnlyHandler,
|
|
4562
5261
|
stopOnGadgetError: this.stopOnGadgetError,
|
|
4563
5262
|
shouldContinueAfterError: this.shouldContinueAfterError,
|
|
4564
|
-
defaultGadgetTimeoutMs: this.defaultGadgetTimeoutMs
|
|
5263
|
+
defaultGadgetTimeoutMs: this.defaultGadgetTimeoutMs,
|
|
5264
|
+
gadgetOutputLimit: this.gadgetOutputLimit,
|
|
5265
|
+
gadgetOutputLimitPercent: this.gadgetOutputLimitPercent
|
|
4565
5266
|
};
|
|
4566
5267
|
return new Agent(AGENT_INTERNAL_KEY, options);
|
|
4567
5268
|
}
|
|
@@ -4580,6 +5281,7 @@ __export(index_exports, {
|
|
|
4580
5281
|
DEFAULT_PROMPTS: () => DEFAULT_PROMPTS,
|
|
4581
5282
|
Gadget: () => Gadget,
|
|
4582
5283
|
GadgetExecutor: () => GadgetExecutor,
|
|
5284
|
+
GadgetOutputStore: () => GadgetOutputStore,
|
|
4583
5285
|
GadgetRegistry: () => GadgetRegistry,
|
|
4584
5286
|
GeminiGenerativeProvider: () => GeminiGenerativeProvider,
|
|
4585
5287
|
HookPresets: () => HookPresets,
|
|
@@ -4600,6 +5302,7 @@ __export(index_exports, {
|
|
|
4600
5302
|
complete: () => complete,
|
|
4601
5303
|
createAnthropicProviderFromEnv: () => createAnthropicProviderFromEnv,
|
|
4602
5304
|
createGadget: () => createGadget,
|
|
5305
|
+
createGadgetOutputViewer: () => createGadgetOutputViewer,
|
|
4603
5306
|
createGeminiProviderFromEnv: () => createGeminiProviderFromEnv,
|
|
4604
5307
|
createLogger: () => createLogger,
|
|
4605
5308
|
createMockAdapter: () => createMockAdapter,
|
|
@@ -4621,10 +5324,10 @@ __export(index_exports, {
|
|
|
4621
5324
|
stream: () => stream,
|
|
4622
5325
|
validateAndApplyDefaults: () => validateAndApplyDefaults,
|
|
4623
5326
|
validateGadgetParams: () => validateGadgetParams,
|
|
4624
|
-
z: () =>
|
|
5327
|
+
z: () => import_zod2.z
|
|
4625
5328
|
});
|
|
4626
5329
|
module.exports = __toCommonJS(index_exports);
|
|
4627
|
-
var
|
|
5330
|
+
var import_zod2 = require("zod");
|
|
4628
5331
|
init_builder();
|
|
4629
5332
|
init_event_handlers();
|
|
4630
5333
|
|
|
@@ -5356,6 +6059,7 @@ var HookPresets = class _HookPresets {
|
|
|
5356
6059
|
// src/agent/index.ts
|
|
5357
6060
|
init_conversation_manager();
|
|
5358
6061
|
init_stream_processor();
|
|
6062
|
+
init_gadget_output_store();
|
|
5359
6063
|
|
|
5360
6064
|
// src/index.ts
|
|
5361
6065
|
init_client();
|
|
@@ -5365,278 +6069,16 @@ init_model_shortcuts();
|
|
|
5365
6069
|
init_options();
|
|
5366
6070
|
init_prompt_config();
|
|
5367
6071
|
init_quick_methods();
|
|
5368
|
-
|
|
5369
|
-
|
|
5370
|
-
var yaml2 = __toESM(require("js-yaml"), 1);
|
|
5371
|
-
|
|
5372
|
-
// src/gadgets/schema-to-json.ts
|
|
5373
|
-
var z2 = __toESM(require("zod"), 1);
|
|
5374
|
-
init_logger();
|
|
5375
|
-
function schemaToJSONSchema(schema, options) {
|
|
5376
|
-
const jsonSchema = z2.toJSONSchema(schema, options ?? { target: "draft-7" });
|
|
5377
|
-
const mismatches = detectDescriptionMismatch(schema, jsonSchema);
|
|
5378
|
-
if (mismatches.length > 0) {
|
|
5379
|
-
defaultLogger.warn(
|
|
5380
|
-
`Zod instance mismatch detected: ${mismatches.length} description(s) lost. For best results, use: import { z } from "llmist"`
|
|
5381
|
-
);
|
|
5382
|
-
return mergeDescriptions(schema, jsonSchema);
|
|
5383
|
-
}
|
|
5384
|
-
return jsonSchema;
|
|
5385
|
-
}
|
|
5386
|
-
function detectDescriptionMismatch(schema, jsonSchema) {
|
|
5387
|
-
const mismatches = [];
|
|
5388
|
-
function checkSchema(zodSchema, json, path) {
|
|
5389
|
-
if (!zodSchema || typeof zodSchema !== "object") return;
|
|
5390
|
-
const def = zodSchema._def;
|
|
5391
|
-
const jsonObj = json;
|
|
5392
|
-
if (def?.description && !jsonObj?.description) {
|
|
5393
|
-
mismatches.push(path || "root");
|
|
5394
|
-
}
|
|
5395
|
-
if (def?.typeName === "ZodObject" && def?.shape) {
|
|
5396
|
-
const shape = typeof def.shape === "function" ? def.shape() : def.shape;
|
|
5397
|
-
for (const [key, fieldSchema] of Object.entries(shape)) {
|
|
5398
|
-
const properties = jsonObj?.properties;
|
|
5399
|
-
const jsonProp = properties?.[key];
|
|
5400
|
-
checkSchema(fieldSchema, jsonProp, path ? `${path}.${key}` : key);
|
|
5401
|
-
}
|
|
5402
|
-
}
|
|
5403
|
-
if (def?.typeName === "ZodArray" && def?.type) {
|
|
5404
|
-
checkSchema(def.type, jsonObj?.items, path ? `${path}[]` : "[]");
|
|
5405
|
-
}
|
|
5406
|
-
if ((def?.typeName === "ZodOptional" || def?.typeName === "ZodNullable") && def?.innerType) {
|
|
5407
|
-
checkSchema(def.innerType, json, path);
|
|
5408
|
-
}
|
|
5409
|
-
if (def?.typeName === "ZodDefault" && def?.innerType) {
|
|
5410
|
-
checkSchema(def.innerType, json, path);
|
|
5411
|
-
}
|
|
5412
|
-
}
|
|
5413
|
-
checkSchema(schema, jsonSchema, "");
|
|
5414
|
-
return mismatches;
|
|
5415
|
-
}
|
|
5416
|
-
function mergeDescriptions(schema, jsonSchema) {
|
|
5417
|
-
function merge(zodSchema, json) {
|
|
5418
|
-
if (!json || typeof json !== "object") return json;
|
|
5419
|
-
const def = zodSchema._def;
|
|
5420
|
-
const jsonObj = json;
|
|
5421
|
-
const merged = { ...jsonObj };
|
|
5422
|
-
if (def?.description && !jsonObj.description) {
|
|
5423
|
-
merged.description = def.description;
|
|
5424
|
-
}
|
|
5425
|
-
if (def?.typeName === "ZodObject" && def?.shape && jsonObj.properties) {
|
|
5426
|
-
const shape = typeof def.shape === "function" ? def.shape() : def.shape;
|
|
5427
|
-
const properties = jsonObj.properties;
|
|
5428
|
-
merged.properties = { ...properties };
|
|
5429
|
-
for (const [key, fieldSchema] of Object.entries(shape)) {
|
|
5430
|
-
if (properties[key]) {
|
|
5431
|
-
merged.properties[key] = merge(fieldSchema, properties[key]);
|
|
5432
|
-
}
|
|
5433
|
-
}
|
|
5434
|
-
}
|
|
5435
|
-
if (def?.typeName === "ZodArray" && def?.type && jsonObj.items) {
|
|
5436
|
-
merged.items = merge(def.type, jsonObj.items);
|
|
5437
|
-
}
|
|
5438
|
-
if ((def?.typeName === "ZodOptional" || def?.typeName === "ZodNullable") && def?.innerType) {
|
|
5439
|
-
return merge(def.innerType, json);
|
|
5440
|
-
}
|
|
5441
|
-
if (def?.typeName === "ZodDefault" && def?.innerType) {
|
|
5442
|
-
return merge(def.innerType, json);
|
|
5443
|
-
}
|
|
5444
|
-
return merged;
|
|
5445
|
-
}
|
|
5446
|
-
return merge(schema, jsonSchema);
|
|
5447
|
-
}
|
|
5448
|
-
|
|
5449
|
-
// src/gadgets/gadget.ts
|
|
5450
|
-
init_schema_validator();
|
|
5451
|
-
function formatYamlValue(value, indent = "") {
|
|
5452
|
-
if (typeof value === "string") {
|
|
5453
|
-
const lines = value.split("\n");
|
|
5454
|
-
if (lines.length === 1 && !value.includes(":") && !value.startsWith("-")) {
|
|
5455
|
-
return value;
|
|
5456
|
-
}
|
|
5457
|
-
const indentedLines = lines.map((line) => `${indent} ${line}`).join("\n");
|
|
5458
|
-
return `|
|
|
5459
|
-
${indentedLines}`;
|
|
5460
|
-
}
|
|
5461
|
-
if (typeof value === "number" || typeof value === "boolean") {
|
|
5462
|
-
return String(value);
|
|
5463
|
-
}
|
|
5464
|
-
if (value === null || value === void 0) {
|
|
5465
|
-
return "null";
|
|
5466
|
-
}
|
|
5467
|
-
if (Array.isArray(value)) {
|
|
5468
|
-
if (value.length === 0) return "[]";
|
|
5469
|
-
const items = value.map((item) => `${indent}- ${formatYamlValue(item, indent + " ")}`);
|
|
5470
|
-
return "\n" + items.join("\n");
|
|
5471
|
-
}
|
|
5472
|
-
if (typeof value === "object") {
|
|
5473
|
-
const entries = Object.entries(value);
|
|
5474
|
-
if (entries.length === 0) return "{}";
|
|
5475
|
-
const lines = entries.map(([k, v]) => {
|
|
5476
|
-
const formattedValue = formatYamlValue(v, indent + " ");
|
|
5477
|
-
if (formattedValue.startsWith("\n") || formattedValue.startsWith("|")) {
|
|
5478
|
-
return `${indent}${k}: ${formattedValue}`;
|
|
5479
|
-
}
|
|
5480
|
-
return `${indent}${k}: ${formattedValue}`;
|
|
5481
|
-
});
|
|
5482
|
-
return "\n" + lines.join("\n");
|
|
5483
|
-
}
|
|
5484
|
-
return yaml2.dump(value).trimEnd();
|
|
5485
|
-
}
|
|
5486
|
-
function formatParamsAsYaml(params) {
|
|
5487
|
-
const lines = [];
|
|
5488
|
-
for (const [key, value] of Object.entries(params)) {
|
|
5489
|
-
const formattedValue = formatYamlValue(value, "");
|
|
5490
|
-
if (formattedValue.startsWith("\n")) {
|
|
5491
|
-
lines.push(`${key}:${formattedValue}`);
|
|
5492
|
-
} else {
|
|
5493
|
-
lines.push(`${key}: ${formattedValue}`);
|
|
5494
|
-
}
|
|
5495
|
-
}
|
|
5496
|
-
return lines.join("\n");
|
|
5497
|
-
}
|
|
5498
|
-
function formatTomlValue(value) {
|
|
5499
|
-
if (typeof value === "string") {
|
|
5500
|
-
if (value.includes("\n")) {
|
|
5501
|
-
return `"""
|
|
5502
|
-
${value}
|
|
5503
|
-
"""`;
|
|
5504
|
-
}
|
|
5505
|
-
return JSON.stringify(value);
|
|
5506
|
-
}
|
|
5507
|
-
if (typeof value === "number" || typeof value === "boolean") {
|
|
5508
|
-
return String(value);
|
|
5509
|
-
}
|
|
5510
|
-
if (value === null || value === void 0) {
|
|
5511
|
-
return '""';
|
|
5512
|
-
}
|
|
5513
|
-
if (Array.isArray(value)) {
|
|
5514
|
-
return JSON.stringify(value);
|
|
5515
|
-
}
|
|
5516
|
-
if (typeof value === "object") {
|
|
5517
|
-
return JSON.stringify(value);
|
|
5518
|
-
}
|
|
5519
|
-
return JSON.stringify(value);
|
|
5520
|
-
}
|
|
5521
|
-
function formatParamsAsToml(params) {
|
|
5522
|
-
const lines = [];
|
|
5523
|
-
for (const [key, value] of Object.entries(params)) {
|
|
5524
|
-
lines.push(`${key} = ${formatTomlValue(value)}`);
|
|
5525
|
-
}
|
|
5526
|
-
return lines.join("\n");
|
|
5527
|
-
}
|
|
5528
|
-
var BaseGadget = class {
|
|
5529
|
-
/**
|
|
5530
|
-
* The name of the gadget. Used for identification when LLM calls it.
|
|
5531
|
-
* If not provided, defaults to the class name.
|
|
5532
|
-
*/
|
|
5533
|
-
name;
|
|
5534
|
-
/**
|
|
5535
|
-
* Optional Zod schema describing the expected input payload. When provided,
|
|
5536
|
-
* it will be validated before execution and transformed into a JSON Schema
|
|
5537
|
-
* representation that is surfaced to the LLM as part of the instructions.
|
|
5538
|
-
*/
|
|
5539
|
-
parameterSchema;
|
|
5540
|
-
/**
|
|
5541
|
-
* Optional timeout in milliseconds for gadget execution.
|
|
5542
|
-
* If execution exceeds this timeout, a TimeoutException will be thrown.
|
|
5543
|
-
* If not set, the global defaultGadgetTimeoutMs from runtime options will be used.
|
|
5544
|
-
* Set to 0 or undefined to disable timeout for this gadget.
|
|
5545
|
-
*/
|
|
5546
|
-
timeoutMs;
|
|
5547
|
-
/**
|
|
5548
|
-
* Optional usage examples to help LLMs understand proper invocation.
|
|
5549
|
-
* Examples are rendered in getInstruction() alongside the schema.
|
|
5550
|
-
*
|
|
5551
|
-
* Note: Uses broader `unknown` type to allow typed examples from subclasses
|
|
5552
|
-
* while maintaining runtime compatibility.
|
|
5553
|
-
*/
|
|
5554
|
-
examples;
|
|
5555
|
-
/**
|
|
5556
|
-
* Auto-generated instruction text for the LLM.
|
|
5557
|
-
* Combines name, description, and parameter schema into a formatted instruction.
|
|
5558
|
-
* @deprecated Use getInstruction(format) instead for format-specific schemas
|
|
5559
|
-
*/
|
|
5560
|
-
get instruction() {
|
|
5561
|
-
return this.getInstruction("yaml");
|
|
5562
|
-
}
|
|
5563
|
-
/**
|
|
5564
|
-
* Generate instruction text for the LLM with format-specific schema.
|
|
5565
|
-
* Combines name, description, and parameter schema into a formatted instruction.
|
|
5566
|
-
*
|
|
5567
|
-
* @param format - Format for the schema representation ('json' | 'yaml' | 'toml' | 'auto')
|
|
5568
|
-
* @returns Formatted instruction string
|
|
5569
|
-
*/
|
|
5570
|
-
getInstruction(format = "json") {
|
|
5571
|
-
const parts = [];
|
|
5572
|
-
parts.push(this.description);
|
|
5573
|
-
if (this.parameterSchema) {
|
|
5574
|
-
const gadgetName = this.name ?? this.constructor.name;
|
|
5575
|
-
validateGadgetSchema(this.parameterSchema, gadgetName);
|
|
5576
|
-
const jsonSchema = schemaToJSONSchema(this.parameterSchema, {
|
|
5577
|
-
target: "draft-7"
|
|
5578
|
-
});
|
|
5579
|
-
if (format === "json" || format === "auto") {
|
|
5580
|
-
parts.push("\n\nInput Schema (JSON):");
|
|
5581
|
-
parts.push(JSON.stringify(jsonSchema, null, 2));
|
|
5582
|
-
} else if (format === "toml") {
|
|
5583
|
-
parts.push("\n\nInput Schema (TOML):");
|
|
5584
|
-
parts.push(JSON.stringify(jsonSchema, null, 2));
|
|
5585
|
-
} else {
|
|
5586
|
-
const yamlSchema = yaml2.dump(jsonSchema).trimEnd();
|
|
5587
|
-
parts.push("\n\nInput Schema (YAML):");
|
|
5588
|
-
parts.push(yamlSchema);
|
|
5589
|
-
}
|
|
5590
|
-
}
|
|
5591
|
-
if (this.examples && this.examples.length > 0) {
|
|
5592
|
-
parts.push("\n\nExamples:");
|
|
5593
|
-
this.examples.forEach((example, index) => {
|
|
5594
|
-
if (index > 0) {
|
|
5595
|
-
parts.push("");
|
|
5596
|
-
}
|
|
5597
|
-
if (example.comment) {
|
|
5598
|
-
parts.push(`# ${example.comment}`);
|
|
5599
|
-
}
|
|
5600
|
-
parts.push("Input:");
|
|
5601
|
-
if (format === "json" || format === "auto") {
|
|
5602
|
-
parts.push(JSON.stringify(example.params, null, 2));
|
|
5603
|
-
} else if (format === "toml") {
|
|
5604
|
-
parts.push(formatParamsAsToml(example.params));
|
|
5605
|
-
} else {
|
|
5606
|
-
parts.push(formatParamsAsYaml(example.params));
|
|
5607
|
-
}
|
|
5608
|
-
if (example.output !== void 0) {
|
|
5609
|
-
parts.push("Output:");
|
|
5610
|
-
parts.push(example.output);
|
|
5611
|
-
}
|
|
5612
|
-
});
|
|
5613
|
-
}
|
|
5614
|
-
return parts.join("\n");
|
|
5615
|
-
}
|
|
5616
|
-
};
|
|
5617
|
-
|
|
5618
|
-
// src/gadgets/create-gadget.ts
|
|
5619
|
-
function createGadget(config) {
|
|
5620
|
-
class DynamicGadget extends BaseGadget {
|
|
5621
|
-
name = config.name;
|
|
5622
|
-
description = config.description;
|
|
5623
|
-
parameterSchema = config.schema;
|
|
5624
|
-
timeoutMs = config.timeoutMs;
|
|
5625
|
-
examples = config.examples;
|
|
5626
|
-
execute(params) {
|
|
5627
|
-
return config.execute(params);
|
|
5628
|
-
}
|
|
5629
|
-
}
|
|
5630
|
-
return new DynamicGadget();
|
|
5631
|
-
}
|
|
5632
|
-
|
|
5633
|
-
// src/index.ts
|
|
6072
|
+
init_create_gadget();
|
|
6073
|
+
init_output_viewer();
|
|
5634
6074
|
init_exceptions();
|
|
5635
6075
|
init_executor();
|
|
6076
|
+
init_gadget();
|
|
5636
6077
|
init_parser();
|
|
5637
6078
|
init_registry();
|
|
5638
6079
|
|
|
5639
6080
|
// src/gadgets/typed-gadget.ts
|
|
6081
|
+
init_gadget();
|
|
5640
6082
|
function Gadget(config) {
|
|
5641
6083
|
class GadgetBase extends BaseGadget {
|
|
5642
6084
|
description = config.description;
|
|
@@ -6356,6 +6798,9 @@ function createMockClient(options) {
|
|
|
6356
6798
|
defaultProvider: "mock"
|
|
6357
6799
|
});
|
|
6358
6800
|
}
|
|
6801
|
+
|
|
6802
|
+
// src/testing/mock-gadget.ts
|
|
6803
|
+
init_gadget();
|
|
6359
6804
|
// Annotate the CommonJS export names for ESM import in node:
|
|
6360
6805
|
0 && (module.exports = {
|
|
6361
6806
|
AgentBuilder,
|
|
@@ -6366,6 +6811,7 @@ function createMockClient(options) {
|
|
|
6366
6811
|
DEFAULT_PROMPTS,
|
|
6367
6812
|
Gadget,
|
|
6368
6813
|
GadgetExecutor,
|
|
6814
|
+
GadgetOutputStore,
|
|
6369
6815
|
GadgetRegistry,
|
|
6370
6816
|
GeminiGenerativeProvider,
|
|
6371
6817
|
HookPresets,
|
|
@@ -6386,6 +6832,7 @@ function createMockClient(options) {
|
|
|
6386
6832
|
complete,
|
|
6387
6833
|
createAnthropicProviderFromEnv,
|
|
6388
6834
|
createGadget,
|
|
6835
|
+
createGadgetOutputViewer,
|
|
6389
6836
|
createGeminiProviderFromEnv,
|
|
6390
6837
|
createLogger,
|
|
6391
6838
|
createMockAdapter,
|