@poe-platform/safe-bash 0.1.819 → 0.1.820

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.
@@ -99,6 +99,80 @@ async function pluginsCommand(args, output, diagnostic, step, signal, load) {
99
99
  return 0;
100
100
  }
101
101
 
102
+ // packages/safe-bash-command-llm/src/chat-options.ts
103
+ var chatOptions = [
104
+ "-h",
105
+ "--help",
106
+ "--td",
107
+ "--tools-debug",
108
+ "--ta",
109
+ "--tools-approve",
110
+ "--no-stream",
111
+ "--functions",
112
+ "-T",
113
+ "--tool",
114
+ "--cl",
115
+ "--chain-limit",
116
+ "-f",
117
+ "--fragment",
118
+ "--sf",
119
+ "--system-fragment",
120
+ "-m",
121
+ "--model",
122
+ "-s",
123
+ "--system",
124
+ "-o",
125
+ "--option",
126
+ "-t",
127
+ "--template",
128
+ "-p",
129
+ "--param",
130
+ "--key"
131
+ ];
132
+ async function chatOptionSuggestion(value, step) {
133
+ if (!value.startsWith("--")) return "";
134
+ const options = chatOptions.filter((option) => option.startsWith("--"));
135
+ const cutoff = 0.6;
136
+ const maximum = Math.floor(Math.max(...options.map((option) => option.length)) * (2 / cutoff - 1));
137
+ const input = [];
138
+ for (const char of value) {
139
+ await step();
140
+ input.push(char);
141
+ if (input.length > maximum) return "";
142
+ }
143
+ const matches = [];
144
+ for (const option of options) {
145
+ if (2 * Math.min(option.length, input.length) / (option.length + input.length) < cutoff) continue;
146
+ const pending = [[0, option.length, 0, input.length]];
147
+ let matched = 0;
148
+ while (pending.length) {
149
+ const [aStart, aEnd, bStart, bEnd] = pending.pop();
150
+ let bestA = aStart, bestB = bStart, size = 0;
151
+ for (let a = aStart; a < aEnd; a++) {
152
+ await step();
153
+ for (let b = bStart; b < bEnd; b++) {
154
+ let length = 0;
155
+ while (a + length < aEnd && b + length < bEnd && option[a + length] === input[b + length]) length++;
156
+ if (length > size) {
157
+ bestA = a;
158
+ bestB = b;
159
+ size = length;
160
+ }
161
+ }
162
+ }
163
+ if (!size) continue;
164
+ matched += size;
165
+ if (aStart < bestA && bStart < bestB) pending.push([aStart, bestA, bStart, bestB]);
166
+ if (bestA + size < aEnd && bestB + size < bEnd) pending.push([bestA + size, aEnd, bestB + size, bEnd]);
167
+ }
168
+ const score = 2 * matched / (option.length + input.length);
169
+ if (score >= cutoff) matches.push({ option, score });
170
+ }
171
+ matches.sort((left, right) => right.score - left.score || (left.option < right.option ? 1 : left.option > right.option ? -1 : 0));
172
+ const suggestions = matches.slice(0, 3).map((match) => match.option).sort();
173
+ return !suggestions.length ? "" : suggestions.length === 1 ? ` Did you mean ${suggestions[0]}?` : ` (Possible options: ${suggestions.join(", ")})`;
174
+ }
175
+
102
176
  // packages/safe-bash-command-llm/src/chat-help.ts
103
177
  var chatHelp = "Usage: llm chat [OPTIONS]\n\n Hold an ongoing chat with a model.\n\nOptions:\n -s, --system TEXT System prompt to use\n -m, --model TEXT Model to use\n -f, --fragment TEXT Fragment (alias, URL, hash or file path) to\n add to the prompt\n --sf, --system-fragment TEXT Fragment to add to system prompt\n -t, --template TEXT Template to use\n -p, --param <TEXT TEXT>... Parameters for template\n -o, --option <TEXT TEXT>... key/value options for the model\n --no-stream Do not stream output\n --key TEXT API key to use\n -T, --tool TEXT Name of a tool to make available to the model\n --functions TEXT Python code block or file path defining\n functions to register as tools\n --td, --tools-debug Show full details of tool executions\n --ta, --tools-approve Manually approve every tool execution\n --cl, --chain-limit INTEGER How many chained tool responses to allow,\n default 5, set 0 for unlimited\n -h, --help Show this message and exit.\n";
104
178
 
@@ -2741,10 +2815,10 @@ async function listLlmModels(context, service, tokens, emit, step, maxConfigurat
2741
2815
  var llmReferenceVersion = "0.27.1";
2742
2816
  var LlmPromptUsageError = class extends Error {
2743
2817
  };
2744
- async function parse(length, text, step, chat = false) {
2818
+ async function parse(length, text, step, chat = false, toolsDebugEnv) {
2745
2819
  const parsed = { toolNames: [], functions: [], chainLimit: 5, prompt: "", queries: [], fragments: [], systemFragments: [], params: {}, options: /* @__PURE__ */ Object.create(null), attachments: [] };
2746
2820
  const operands = [];
2747
- let ended = false;
2821
+ let ended = false, chainLimit;
2748
2822
  for (let index = 0; index < length; index++) {
2749
2823
  await step();
2750
2824
  const argument = text(index);
@@ -2767,11 +2841,11 @@ async function parse(length, text, step, chat = false) {
2767
2841
  if (long) break;
2768
2842
  continue;
2769
2843
  }
2770
- if (!["--td", "--tools-debug", "--ta", "--tools-approve", "--no-stream", "--functions", "-T", "--tool", "--cl", "--chain-limit", "-f", "--fragment", "--sf", "--system-fragment", "-m", "--model", "-s", "--system", "-o", "--option", "-t", "--template", "-p", "--param", "--key"].includes(flag))
2844
+ if (!chatOptions.includes(flag))
2771
2845
  throw new LlmPromptUsageError(`Usage: llm chat [OPTIONS]
2772
2846
  Try 'llm chat -h' for help.
2773
2847
 
2774
- Error: No such option: ${flag}`);
2848
+ Error: No such option: ${flag}${await chatOptionSuggestion(flag, step)}`);
2775
2849
  }
2776
2850
  const boolean = ["--async", "--td", "--tools-debug", "--ta", "--tools-approve", "--no-log", "-n", "-x", "--extract", "--xl", "--extract-last", "-u", "--usage", "--no-stream"].includes(flag);
2777
2851
  if (boolean) {
@@ -2794,14 +2868,8 @@ Error: No such option: ${flag}`);
2794
2868
  const value = attached ?? text(++index);
2795
2869
  if (flag === "--functions") parsed.functions.push(value);
2796
2870
  else if (flag === "-T" || flag === "--tool") parsed.toolNames.push(value);
2797
- else if (flag === "--cl" || flag === "--chain-limit") {
2798
- const integer = tokenInteger(value);
2799
- if (integer === void 0) throw new LlmPromptUsageError(`Usage: llm prompt [OPTIONS] [PROMPT]
2800
- Try 'llm prompt --help' for help.
2801
-
2802
- Error: Invalid value for '--cl' / '--chain-limit': '${value}' is not a valid integer.`);
2803
- parsed.chainLimit = BigInt(integer);
2804
- } else if (flag === "-f" || flag === "--fragment") parsed.fragments.push(value);
2871
+ else if (flag === "--cl" || flag === "--chain-limit") chainLimit = value;
2872
+ else if (flag === "-f" || flag === "--fragment") parsed.fragments.push(value);
2805
2873
  else if (flag === "--sf" || flag === "--system-fragment") parsed.systemFragments.push(value);
2806
2874
  else if (flag === "-q" || flag === "--query") parsed.queries.push(value);
2807
2875
  else if (flag === "-t" || flag === "--template") parsed.template = value;
@@ -2819,6 +2887,24 @@ Error: Invalid value for '--cl' / '--chain-limit': '${value}' is not a valid int
2819
2887
  }
2820
2888
  }
2821
2889
  if (parsed.help) return parsed;
2890
+ const usage3 = chat ? "Usage: llm chat [OPTIONS]\nTry 'llm chat -h' for help." : "Usage: llm prompt [OPTIONS] [PROMPT]\nTry 'llm prompt --help' for help.";
2891
+ if (chainLimit !== void 0) {
2892
+ const integer = tokenInteger(chainLimit);
2893
+ if (integer === void 0) throw new LlmPromptUsageError(`${usage3}
2894
+
2895
+ Error: Invalid value for '--cl' / '--chain-limit': '${chainLimit}' is not a valid integer.`);
2896
+ parsed.chainLimit = BigInt(integer);
2897
+ }
2898
+ if (!parsed.toolsDebug && toolsDebugEnv) {
2899
+ const raw = toolsDebugEnv, value = stripPythonWhitespace(raw).toLowerCase();
2900
+ if (["1", "true", "t", "yes", "y", "on"].includes(value)) parsed.toolsDebug = true;
2901
+ else if (!["", "0", "false", "f", "no", "n", "off"].includes(value)) {
2902
+ const detail = chat ? "" : " Recognized values: , 0, 1, f, false, n, no, off, on, t, true, y, yes";
2903
+ throw new LlmPromptUsageError(`${usage3}
2904
+
2905
+ Error: Invalid value for '--td' / '--tools-debug': '${raw}' is not a valid boolean.${detail}`);
2906
+ }
2907
+ }
2822
2908
  if (chat && operands.length) throw new LlmPromptUsageError(`Usage: llm chat [OPTIONS]
2823
2909
  Try 'llm chat -h' for help.
2824
2910
 
@@ -3106,19 +3192,11 @@ async function execute(context, service, limits, templateLoaderOptions, collecti
3106
3192
  }
3107
3193
  const isChat = argumentsValue.args[0] === "chat";
3108
3194
  const promptOffset = argumentsValue.args[0] === "prompt" || isChat ? 1 : 0;
3109
- let args = await parse(argumentsValue.args.length - promptOffset, (index) => argumentText(index + promptOffset), step, isChat);
3195
+ let args = await parse(argumentsValue.args.length - promptOffset, (index) => argumentText(index + promptOffset), step, isChat, context.env.LLM_TOOLS_DEBUG);
3110
3196
  if (args.help) {
3111
3197
  await emitText(chatHelp);
3112
3198
  return { exitCode: 0 };
3113
3199
  }
3114
- if (!args.toolsDebug && context.env.LLM_TOOLS_DEBUG) {
3115
- const raw = context.env.LLM_TOOLS_DEBUG, value = stripPythonWhitespace(raw).toLowerCase();
3116
- if (["1", "true", "t", "yes", "y", "on"].includes(value)) args.toolsDebug = true;
3117
- else if (!["", "0", "false", "f", "no", "n", "off"].includes(value)) throw new LlmPromptUsageError(`Usage: llm prompt [OPTIONS] [PROMPT]
3118
- Try 'llm prompt --help' for help.
3119
-
3120
- Error: Invalid value for '--td' / '--tools-debug': '${raw}' is not a valid boolean. Recognized values: , 0, 1, f, false, n, no, off, on, t, true, y, yes`);
3121
- }
3122
3200
  const configuration = createLlmConfiguration(context, limits?.maxConfigurationBytes, invocationLoaders);
3123
3201
  if (args.model === void 0 && args.queries.length) {
3124
3202
  try {
@@ -3156,6 +3234,10 @@ Error: Invalid value for '--td' / '--tools-debug': '${raw}' is not a valid boole
3156
3234
  try {
3157
3235
  entry = args.save && selected === void 0 ? void 0 : service.resolve(model, args.async && !args.save ? { async: true } : void 0);
3158
3236
  } catch (error) {
3237
+ if (isChat && error instanceof Error && error.message.startsWith("Unknown model: ")) {
3238
+ const missing = selected ?? error.message.slice("Unknown model: ".length);
3239
+ throw new Error(`Error: '${missing}' is not a known model`);
3240
+ }
3159
3241
  if (!args.async || args.save) throw error;
3160
3242
  let detail = "";
3161
3243
  for await (const bytes of pythonRepr(error instanceof Error ? error.message : String(error), signal)) {
@@ -3,7 +3,7 @@ import {
3
3
  createLlmCommands,
4
4
  llmCommands,
5
5
  llmReferenceVersion
6
- } from "../safe-bash/command-chunks/chunk-AC4FFCRL.js";
6
+ } from "../safe-bash/command-chunks/chunk-FVHPDYV5.js";
7
7
  import "../safe-bash/command-chunks/chunk-MCUDSE4H.js";
8
8
  import "../safe-bash/command-chunks/chunk-WOT2YXBT.js";
9
9
  import "../safe-bash/command-chunks/chunk-BZLLQWRK.js";
@@ -43,7 +43,7 @@ import {
43
43
  serializeLlmTokenUsage,
44
44
  streamLlmToolChain,
45
45
  validateLlmTemplateParameters
46
- } from "../safe-bash/command-chunks/chunk-AC4FFCRL.js";
46
+ } from "../safe-bash/command-chunks/chunk-FVHPDYV5.js";
47
47
  import "../safe-bash/command-chunks/chunk-MCUDSE4H.js";
48
48
  import {
49
49
  createLlmConfiguration
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@poe-platform/safe-bash",
3
- "version": "0.1.819",
3
+ "version": "0.1.820",
4
4
  "description": "Extensible virtual shell with pluggable filesystems and streaming commands",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -1407,7 +1407,7 @@
1407
1407
  "access": "public"
1408
1408
  },
1409
1409
  "dependencies": {
1410
- "@poe-platform/safe-fs": "0.1.819",
1410
+ "@poe-platform/safe-fs": "0.1.820",
1411
1411
  "pdf-lib": "1.17.1",
1412
1412
  "@types/node": "^25.2.2",
1413
1413
  "@formatjs/intl-numberformat": "9.4.0",