fluxflow-cli 2.11.7 → 2.12.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.
Files changed (2) hide show
  1. package/dist/fluxflow.js +93 -9
  2. package/package.json +2 -2
package/dist/fluxflow.js CHANGED
@@ -749,6 +749,7 @@ import os2 from "os";
749
749
  var wrapText, formatTokens, truncatePath, parsePatchPairs, applyPatches, generateHighFidelityDiff;
750
750
  var init_text = __esm({
751
751
  "src/utils/text.js"() {
752
+ init_paths();
752
753
  wrapText = (text, width) => {
753
754
  if (!text) return "";
754
755
  const ansiRegex = /\x1B\[[0-?]*[ -/]*[@-~]/g;
@@ -812,10 +813,11 @@ var init_text = __esm({
812
813
  return num.toString();
813
814
  };
814
815
  truncatePath = (p, maxLength = 40) => {
815
- p = p.replace(os2.homedir(), "~");
816
+ let data_dir = DATA_DIR.replaceAll("\\\\", "\\");
817
+ p = p.replace(os2.homedir(), "~").replace(data_dir, "FluxFlow").replaceAll("\\", "/");
816
818
  if (!p || p.length <= maxLength) return p;
817
819
  const half = Math.floor((maxLength - 3) / 2);
818
- return p.substring(0, half) + "..." + p.substring(p.length - half);
820
+ return p.substring(0, half) + "..." + p.substring(p.length - half).replaceAll("\\", "/");
819
821
  };
820
822
  parsePatchPairs = (args) => {
821
823
  const patchPairs = [];
@@ -3372,11 +3374,11 @@ var thinking_prompts_default;
3372
3374
  var init_thinking_prompts = __esm({
3373
3375
  "src/data/thinking_prompts.json"() {
3374
3376
  thinking_prompts_default = {
3375
- xHigh: "EFFORT LEVEL: HIGH\nThink in a continuous, relentless analytical monologue. Engage in adversarial self interrogation that treats every assumption as hostile until proven:\nDeconstruct requirements into atomic invariants. Trace every implicit dependency, side effect, and state mutation. Map the entire dependency graph and identify circular dependencies or tight coupling before they manifest\nEvaluate algorithmic complexity (time/space) for every operation. Consider memory models, cache locality, and allocation patterns. For concurrent systems, reason through race conditions, deadlocks, and memory ordering\nFormulate solutions by comparing multiple architectural approaches. Explicitly evaluate trade offs, monolithic vs modular, eager vs lazy, mutable vs immutable, sync vs async. Choose based on measured criteria, not intuition\nMentally execute the solution at multiple scales. What breaks at 10x load? 100x? What happens under resource exhaustion? Trace error propagation paths through every layer\nActively attempt to falsify your own logic. Steel man the opposite approach. Search for, off by one errors, integer overflow, null/undefined propagation, unhandled promises, resource leaks, SQL injection vectors, XSS vulnerabilities, CSRF holes, timing attacks, and privilege escalation paths\nReason about observability, what metrics matter? Where are the logging gaps? How will this be debugged in production at 3am?\nConsider future evolution, what changes will this architecture resist vs accommodate? Where are the extension points? What will break when requirements inevitably change?\nMap out implementation with surgical precision, exact file structure, module boundaries, interface contracts, error types, and test strategies before writing a single line\nRULES:\n- Ruthlessly question every architectural choice. Default to skepticism\n- Think in terms of invariants, contracts, and failure modes, not just happy paths\n- Verify ALL imports and system stability, AVOID ANY Syntax errors, re-read TOOL RESULTS/files to verify\n- MANDATORY THINKING: Full reasoning required for ALL requests/greetings (verify context, check for hidden complexity)",
3376
- High: "EFFORT LEVEL: HIGH\nThink in a rigorous, technically grounded monologue within <think>...</think>. Treat this as a design review where every decision must be justified:\nBreak the objective into verifiable steps with clear success criteria. Identify the critical path and potential bottlenecks\nMentally compile and execute your approach. Check for: missing imports, undefined behavior, type mismatches, unhandled errors, and resource cleanup. Trace data flow from input to output, noting transformations\nRecognize design patterns and anti patterns. If you see God objects, tight coupling, or premature optimization, call it out and refactor mentally before committing\nEvaluate performance characteristics. Will this scale? Are there O(n\xB2) operations hiding in innocent looking code? Where are the allocation hotspots?\nConsider the error surface, what can fail and how? Design error handling that preserves invariants and provides actionable feedback\nReview your architecture for, separation of concerns, single responsibility, dependency inversion, and interface segregation. Ensure clean abstractions with minimal coupling\nRULES:\n- NO HEADINGS/MARKERS/LISTS\n- Continuous analytical flow\n- Verify correctness through first principles reasoning, not pattern matching\n- Actively search for ways your solution could fail or degrade\n- Verify ALL imports and system stability, AVOID ANY Syntax errors, re-read TOOL RESULTS/files to verify\n- MANDATORY THINKING: Full technical verification for all tasks/greetings",
3377
+ xHigh: "EFFORT LEVEL: HIGH\nThink in a continuous, relentless analytical monologue. Engage in adversarial self interrogation that treats every assumption as hostile until proven:\nDeconstruct requirements into atomic invariants. Trace every implicit dependency, side effect, and state mutation. Map the entire dependency graph and identify circular dependencies or tight coupling before they manifest\nEvaluate algorithmic complexity (time/space) for every operation. Consider memory models, cache locality, and allocation patterns. For concurrent systems, reason through race conditions, deadlocks, and memory ordering\nFormulate solutions by comparing multiple architectural approaches. Explicitly evaluate trade offs, monolithic vs modular, eager vs lazy, mutable vs immutable, sync vs async. Choose based on measured criteria, not intuition\nMentally execute the solution at multiple scales. What breaks at 10x load? 100x? Resource exhaustion? Trace error propagation paths through every layer\nActively attempt to falsify your own logic. Steel man the opposite approach\nReason about observability & vulnarability\nConsider future evolution, what changes will this architecture resist vs accommodate? Where are the extension points? What will break when requirements inevitably change?\nMap out implementation with surgical precision, exact file structure, module boundaries, interface contracts, error types, and test strategies before writing\nRULES:\n- Ruthlessly question every architectural choice. Default to skepticism\n- Think in terms of invariants, contracts, and failure modes, not just happy paths\n- Verify ALL imports and system stability, AVOID errors\n- MANDATORY THINKING: Full reasoning required for ALL requests/greetings",
3378
+ High: "EFFORT LEVEL: HIGH\nThink in a rigorous, technically grounded monologue within <think>...</think>\nBreak the objective into verifiable steps with clear success criteria. Identify the critical path and potential bottlenecks\nMentally compile and execute your approach. Check for: missing imports, undefined behavior, type mismatches, unhandled errors, and resource cleanup. Trace data flow from input to output, noting transformations\nRecognize design patterns and anti patterns. If you see God objects, tight coupling, or premature optimization, call it out and refactor mentally before committing\nEvaluate performance characteristics. Will this scale? Are there O(n\xB2) operations hiding in innocent looking code? Where are the allocation hotspots?\nConsider the error surface, what can fail and how? Design error handling that preserves invariants and provides actionable feedback\nReview your architecture for, separation of concerns, single responsibility, dependency inversion, and interface segregation. Ensure clean abstractions with minimal coupling\nRULES:\n- NO HEADINGS/MARKERS/LISTS\n- Continuous analytical flow\n- Verify correctness through first principles reasoning, not pattern matching\n- Actively search for ways your solution could fail or degrade\n- Verify ALL imports and system stability, AVOID ANY Syntax errors, re-read TOOL RESULTS/files to verify\n- MANDATORY THINKING: Full technical verification for all tasks/greetings",
3377
3379
  Medium: "EFFORT LEVEL: MEDIUM\nThink in a focused, technically-aware monologue within <think>...</think>\nIdentify the most direct path that satisfies requirements without over-engineering\nQuickly scan for obvious issues, missing error handling, incorrect input assumptions, forgotten edge cases, or missing dependencies\nVerify the solution is appropriately modular with cohesive changes\nOutline the concrete changes, which files, which functions, what the key logic looks like\nRULES:\n- NO HEADINGS/MARKERS/LISTS\n- Clean logical stream\n- Efficient but deliberate. Focus energy on actionable implementation details\n- Verify ALL imports and system stability, AVOID ANY Syntax errors, re-read TOOL RESULTS/files to verify\n- MANDATORY THINKING: Brief verification for technical tasks/greetings",
3378
3380
  Minimal: "EFFORT LEVEL: LOW\nThink in a quick, focused monologue within <think>...</think>. Just verify the basics:\nConfirm what the user wants and whether it's straightforward or has hidden complexity\nIdentify the specific tool, file, or action needed\nCheck for any obvious correctness issues before acting\nRULES:\n- NO HEADINGS/MARKERS/LISTS\n- Few lines of clear thought\n- Just enough thinking to avoid obvious mistakes\n- Verify ALL imports and system stability, AVOID ANY Syntax errors, re-read TOOL RESULTS/files to verify\n- Suitable for simple requests/greetings",
3379
- Off: "EFFORT LEVEL: INSTANT\nNo thinking. Immediate response\nRULES:\n- Verify ALL imports and system stability, AVOID ANY Syntax errors, re-read TOOL RESULTS/files to verify"
3381
+ Off: "EFFORT LEVEL: LOWEST\nNo thinking. Immediate response\nRULES:\n- Verify ALL imports and system stability, AVOID ANY Syntax errors, re-read TOOL RESULTS/files to verify"
3380
3382
  };
3381
3383
  }
3382
3384
  });
@@ -7785,7 +7787,7 @@ Provide a consolidated summary of the entire session.`;
7785
7787
  }
7786
7788
  };
7787
7789
  getAIStream = async function* (modelName, history, settings, steeringCallback, versionFluxflow2) {
7788
- const { profile, thinkingLevel, mode, janitorModel, chatId, systemSettings, sessionStats, aiProvider = "Google", apiTier } = settings;
7790
+ const { profile, thinkingLevel, mode, janitorModel, chatId, isPlayground, systemSettings, sessionStats, aiProvider = "Google", apiTier } = settings;
7789
7791
  const isMultiModal = isModelMultimodal(modelName);
7790
7792
  if (!client && aiProvider === "Google") throw new Error("AI not initialized");
7791
7793
  const isMemoryEnabled = systemSettings?.memory !== false;
@@ -8388,7 +8390,7 @@ ${boxBottom}` };
8388
8390
  taggedContextStr = "[TAGGED CONTEXT]\n" + taggedContextBlocks.join("\n\n") + "\n[/TAGGED CONTEXT]\n";
8389
8391
  }
8390
8392
  const firstUserMsg = `[SYSTEM METADATA (PRIORITY: DYNAMIC), Chat Context >> Metadata] Time: ${dateTimeStr}
8391
- CWD: ${process.cwd()}${cwdMismatch ? ` (WARNING: CWD Mismatch! Previous Path: ${lastCwd})` : ""}
8393
+ CWD: ${process.cwd()}${isPlayground ? " [PLAYGROUND MODE]" : ""}${cwdMismatch ? ` (WARNING: CWD Mismatch! Previous Path: ${lastCwd})` : ""}
8392
8394
  **DIRECTORY STRUCTURE**
8393
8395
  ${dirStructure}${memoryPrompt}${ideBlock}
8394
8396
  ${activeSummaryBlock}${thinkingLevel !== "Fast" && thinkingLevel !== "xHigh" && aiProvider === "Google" ? `${modelName.toLowerCase().startsWith("gemma") ? "[SYSTEM] **STRICTLY FOLLOW THINKING POLICY AS CRITICAL PRIORITY. DO NOT START A RESPONSE WITHOUT <think> ... </think>** [/SYSTEM]\n" : ""}` : ""}${taggedContextStr}[USER] ${cleanAgentText.trim()} [/USER]`.trim();
@@ -11252,6 +11254,8 @@ function App({ args = [] }) {
11252
11254
  } else if ((arg === "--resume" || arg === "-r") && args[i + 1]) {
11253
11255
  parsed.resume = args[i + 1];
11254
11256
  i++;
11257
+ } else if (arg === "--playground") {
11258
+ parsed.playground = true;
11255
11259
  }
11256
11260
  }
11257
11261
  return parsed;
@@ -11408,7 +11412,8 @@ function App({ args = [] }) {
11408
11412
  const [monthlyUsage, setMonthlyUsage] = useState11(null);
11409
11413
  const [customPeriodUsage, setCustomPeriodUsage] = useState11(null);
11410
11414
  const [statsMode, setStatsMode] = useState11("daily");
11411
- const [chatId, setChatId] = useState11(generateChatId());
11415
+ const PLAYGROUND_CHAT_ID = "flow-playground";
11416
+ const [chatId, setChatId] = useState11(args.includes("--playground") ? PLAYGROUND_CHAT_ID : generateChatId());
11412
11417
  useEffect8(() => {
11413
11418
  const nextTokens = sessionTotalTokens - chatTokenStartRef.current;
11414
11419
  setChatTokens(nextTokens);
@@ -11438,6 +11443,8 @@ function App({ args = [] }) {
11438
11443
  const isSecondRender = useRef3(true);
11439
11444
  const isThirdRender = useRef3(true);
11440
11445
  const prevProviderRef = useRef3(aiProvider);
11446
+ const originalAllowExternalAccessRef = useRef3(false);
11447
+ const originalMemoryRef = useRef3(true);
11441
11448
  useEffect8(() => {
11442
11449
  if (prevProviderRef.current !== aiProvider) {
11443
11450
  prevProviderRef.current = aiProvider;
@@ -11896,6 +11903,8 @@ function App({ args = [] }) {
11896
11903
  });
11897
11904
  }
11898
11905
  const saved = await loadSettings();
11906
+ originalAllowExternalAccessRef.current = saved.systemSettings?.allowExternalAccess ?? false;
11907
+ originalMemoryRef.current = saved.systemSettings?.memory ?? true;
11899
11908
  if (parsedArgs.mode) {
11900
11909
  setMode(parsedArgs.mode);
11901
11910
  } else {
@@ -11973,6 +11982,10 @@ function App({ args = [] }) {
11973
11982
  } else if (parsedArgs.externalAccess === "off") {
11974
11983
  freshSettings.allowExternalAccess = false;
11975
11984
  }
11985
+ if (parsedArgs.playground) {
11986
+ freshSettings.allowExternalAccess = false;
11987
+ freshSettings.memory = false;
11988
+ }
11976
11989
  setSystemSettings(freshSettings);
11977
11990
  setProfileData(saved.profileData);
11978
11991
  setImageSettings(saved.imageSettings || { keyType: "Default", quality: "Low-High", apiKey: "" });
@@ -11988,6 +12001,12 @@ function App({ args = [] }) {
11988
12001
  cleanupOldHistory(saved.systemSettings.autoDeleteHistory);
11989
12002
  }
11990
12003
  cleanupOldLogs(LOGS_DIR);
12004
+ if (!parsedArgs.playground) {
12005
+ deleteChat(PLAYGROUND_CHAT_ID).catch(() => {
12006
+ });
12007
+ fs22.remove(path20.join(DATA_DIR, "playground")).catch(() => {
12008
+ });
12009
+ }
11991
12010
  performVersionCheck(false, freshSettings);
11992
12011
  await initUsage();
11993
12012
  await RevertManager.recoverCrashedTransaction();
@@ -12016,6 +12035,43 @@ function App({ args = [] }) {
12016
12035
  setMessages((prev) => [...prev, { id: "sys-err-" + Date.now(), role: "system", text: `ERROR: Chat session [${id}] not found. Started new session.`, isMeta: true }]);
12017
12036
  }
12018
12037
  }
12038
+ if (parsedArgs.playground) {
12039
+ const playgroundDir = path20.join(DATA_DIR, "playground");
12040
+ try {
12041
+ fs22.ensureDirSync(playgroundDir);
12042
+ process.chdir(playgroundDir);
12043
+ } catch (e) {
12044
+ }
12045
+ const playgroundHistory = await loadHistory();
12046
+ if (playgroundHistory[PLAYGROUND_CHAT_ID]) {
12047
+ const resumedMsgs = [...playgroundHistory[PLAYGROUND_CHAT_ID].messages];
12048
+ if (!resumedMsgs[0]?.isLogo) {
12049
+ resumedMsgs.unshift({ id: "logo-" + Date.now(), role: "system", isLogo: true, isMeta: true });
12050
+ }
12051
+ setMessages(resumedMsgs);
12052
+ setMessages((prev) => {
12053
+ const newMsgs = [...prev, {
12054
+ id: "playground-" + Date.now(),
12055
+ role: "system",
12056
+ text: `[PLAYGROUND] Session restored. CWD locked to: ${playgroundDir}`,
12057
+ isMeta: true
12058
+ }];
12059
+ setCompletedIndex(newMsgs.length);
12060
+ return newMsgs;
12061
+ });
12062
+ } else {
12063
+ setMessages((prev) => {
12064
+ const newMsgs = [...prev, {
12065
+ id: "playground-" + Date.now(),
12066
+ role: "system",
12067
+ text: `[PLAYGROUND] Mode active. CWD locked to: FluxFlow/playground`,
12068
+ isMeta: true
12069
+ }];
12070
+ setCompletedIndex(newMsgs.length);
12071
+ return newMsgs;
12072
+ });
12073
+ }
12074
+ }
12019
12075
  const detectedIde = getIDEName();
12020
12076
  const isIDE = !["Terminal", "Windows Terminal"].includes(detectedIde);
12021
12077
  if (isIDE) {
@@ -12063,13 +12119,21 @@ function App({ args = [] }) {
12063
12119
  useEffect8(() => {
12064
12120
  if (!isInitializing) {
12065
12121
  const modelToSave = parsedArgs.model && activeModel === parsedArgs.model ? persistedModelRef.current : activeModel;
12122
+ let settingsToSave = systemSettings;
12123
+ if (parsedArgs.playground) {
12124
+ settingsToSave = {
12125
+ ...systemSettings,
12126
+ allowExternalAccess: originalAllowExternalAccessRef.current,
12127
+ memory: originalMemoryRef.current
12128
+ };
12129
+ }
12066
12130
  saveSettings({
12067
12131
  mode,
12068
12132
  thinkingLevel,
12069
12133
  aiProvider,
12070
12134
  activeModel: modelToSave || activeModel,
12071
12135
  showFullThinking,
12072
- systemSettings,
12136
+ systemSettings: settingsToSave,
12073
12137
  profileData,
12074
12138
  imageSettings,
12075
12139
  apiTier
@@ -12529,6 +12593,13 @@ ${cleanText}`, color: "magenta" }];
12529
12593
  { id: "logo-" + Date.now(), role: "system", isLogo: true, isMeta: true }
12530
12594
  ]);
12531
12595
  setCompletedIndex(1);
12596
+ if (parsedArgs.playground) {
12597
+ parsedArgs.playground = false;
12598
+ deleteChat(PLAYGROUND_CHAT_ID).catch(() => {
12599
+ });
12600
+ fs22.remove(path20.join(DATA_DIR, "playground")).catch(() => {
12601
+ });
12602
+ }
12532
12603
  setChatId(generateChatId());
12533
12604
  setSessionStats({ tokens: 0 });
12534
12605
  setIsExpanded(false);
@@ -13203,6 +13274,7 @@ ${timestamp}` };
13203
13274
  janitorModel,
13204
13275
  sessionStats,
13205
13276
  chatId,
13277
+ isPlayground: !!parsedArgs.playground,
13206
13278
  aiProvider,
13207
13279
  apiKey,
13208
13280
  apiTier,
@@ -14936,6 +15008,7 @@ if (isBundled && !process.execArgv.some((arg) => arg.includes("max-old-space-siz
14936
15008
  -v, --version Show installed version
14937
15009
  --help Show this help menu
14938
15010
  --help commands Show available /commands
15011
+ --playground Launch in Playground mode (fixed session, CWD: DATA_DIR/playground)
14939
15012
  --update check Check for new updates
14940
15013
  --update check latest Show the latest version available on npm
14941
15014
  --update latest Update the app to the latest version`);
@@ -15136,5 +15209,16 @@ if (isBundled && !process.execArgv.some((arg) => arg.includes("max-old-space-siz
15136
15209
  process.stdout.write("\x1B]0;FluxFlow\x07");
15137
15210
  process.stdout.write("\x1B]633;P;TerminalTitle=FluxFlow\x07");
15138
15211
  }
15212
+ if (args.includes("--playground")) {
15213
+ const { DATA_DIR: DATA_DIR2 } = await Promise.resolve().then(() => (init_paths(), paths_exports));
15214
+ const pathMod = await import("path");
15215
+ const fsMod = await import("fs-extra");
15216
+ const playgroundDir = pathMod.default.join(DATA_DIR2, "playground");
15217
+ try {
15218
+ fsMod.default.ensureDirSync(playgroundDir);
15219
+ process.chdir(playgroundDir);
15220
+ } catch (e) {
15221
+ }
15222
+ }
15139
15223
  render(/* @__PURE__ */ React15.createElement(App2, { args: process.argv.slice(2) }), { exitOnCtrlC: false });
15140
15224
  }
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "fluxflow-cli",
3
- "version": "2.11.7",
4
- "date": "2026-06-23",
3
+ "version": "2.12.1",
4
+ "date": "2026-06-24",
5
5
  "description": "A high-fidelity agentic terminal assistant for the Flux Era.",
6
6
  "keywords": [
7
7
  "ai",