@solongate/proxy 0.81.18 → 0.81.19

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/index.js CHANGED
@@ -7090,145 +7090,34 @@ var init_api_client = __esm({
7090
7090
  });
7091
7091
 
7092
7092
  // src/tui/notify.ts
7093
- import { spawn, execFileSync as execFileSync2 } from "child_process";
7094
- import { writeFileSync as writeFileSync3, existsSync as existsSync4 } from "fs";
7095
- import { join as join6 } from "path";
7096
- import { tmpdir as tmpdir2 } from "os";
7097
- function captureFocusTarget() {
7093
+ import { spawn } from "child_process";
7094
+ function desktopNotify(title, msg) {
7098
7095
  try {
7099
7096
  if (process.platform === "linux") {
7100
- focusToken = (process.env.WINDOWID || "").trim() || null;
7101
- if (!focusToken) {
7102
- try {
7103
- focusToken = execFileSync2("xdotool", ["getactivewindow"], { encoding: "utf-8", timeout: 1500, stdio: ["ignore", "pipe", "ignore"] }).trim() || null;
7104
- } catch {
7105
- focusToken = null;
7106
- }
7107
- }
7097
+ const p = spawn("notify-send", ["-a", "SolonGate", title, msg], { stdio: "ignore", detached: true });
7098
+ p.on("error", () => {
7099
+ });
7100
+ p.unref();
7108
7101
  } else if (process.platform === "win32") {
7109
- const ps = `Add-Type -Name W -Namespace N -MemberDefinition '[DllImport("user32.dll")]public static extern System.IntPtr GetForegroundWindow();' | Out-Null; [N.W]::GetForegroundWindow().ToInt64()`;
7110
- try {
7111
- focusToken = execFileSync2("powershell", ["-NoProfile", "-NonInteractive", "-Command", ps], { encoding: "utf-8", timeout: 4e3, stdio: ["ignore", "pipe", "ignore"] }).trim() || null;
7112
- } catch {
7113
- focusToken = null;
7114
- }
7102
+ const q = (s) => s.replace(/'/g, "''");
7103
+ const ps = `Add-Type -AssemblyName System.Windows.Forms;Add-Type -AssemblyName System.Drawing;$n=New-Object System.Windows.Forms.NotifyIcon;$n.Icon=[System.Drawing.SystemIcons]::Information;$n.Visible=$true;$n.ShowBalloonTip(6000,'${q(title)}','${q(msg)}',[System.Windows.Forms.ToolTipIcon]::Warning);Start-Sleep -Milliseconds 6500;$n.Dispose()`;
7104
+ const p = spawn("powershell", ["-NoProfile", "-NonInteractive", "-Command", ps], { stdio: "ignore", detached: true, windowsHide: true });
7105
+ p.on("error", () => {
7106
+ });
7107
+ p.unref();
7108
+ } else if (process.platform === "darwin") {
7109
+ const esc = (s) => s.replace(/"/g, '\\"');
7110
+ const p = spawn("osascript", ["-e", `display notification "${esc(msg)}" with title "${esc(title)}"`], { stdio: "ignore", detached: true });
7111
+ p.on("error", () => {
7112
+ });
7113
+ p.unref();
7115
7114
  }
7116
7115
  } catch {
7117
- focusToken = null;
7118
- }
7119
- }
7120
- function desktopNotify(title, msg) {
7121
- try {
7122
- if (process.platform === "linux") linuxNotify(title, msg);
7123
- else if (process.platform === "win32") winNotify(title, msg);
7124
- else if (process.platform === "darwin") macNotify(title, msg);
7125
- } catch {
7126
- }
7127
- }
7128
- function linuxNotify(title, msg) {
7129
- let p;
7130
- try {
7131
- p = spawn("notify-send", ["--wait", "--action=default=Open", "-a", "SolonGate", title, msg], { stdio: ["ignore", "pipe", "ignore"] });
7132
- } catch {
7133
- return;
7134
7116
  }
7135
- p.on("error", () => {
7136
- });
7137
- p.stdout?.on("data", (d) => {
7138
- if (String(d).trim() === "default") raiseLinuxWindow();
7139
- });
7140
- p.unref();
7141
7117
  }
7142
- function raiseLinuxWindow() {
7143
- try {
7144
- process.stdout.write("\x1B[5t");
7145
- } catch {
7146
- }
7147
- if (!focusToken) return;
7148
- try {
7149
- const x = spawn("xdotool", ["windowactivate", focusToken], { stdio: "ignore" });
7150
- x.on("error", () => {
7151
- try {
7152
- const hex = "0x" + Number(focusToken).toString(16);
7153
- const w = spawn("wmctrl", ["-ia", hex], { stdio: "ignore" });
7154
- w.on("error", () => {
7155
- });
7156
- w.unref();
7157
- } catch {
7158
- }
7159
- });
7160
- x.unref();
7161
- } catch {
7162
- }
7163
- }
7164
- function ensureWinScript() {
7165
- if (winScriptPath && existsSync4(winScriptPath)) return winScriptPath;
7166
- const p = join6(tmpdir2(), "solongate-toast.ps1");
7167
- const script = [
7168
- "param([string]$Title,[string]$Msg,[string]$Hwnd)",
7169
- "Add-Type -AssemblyName System.Windows.Forms",
7170
- "Add-Type -AssemblyName System.Drawing",
7171
- `Add-Type -Name Win -Namespace Sg -MemberDefinition '[DllImport("user32.dll")]public static extern bool SetForegroundWindow(System.IntPtr h);[DllImport("user32.dll")]public static extern bool ShowWindow(System.IntPtr h,int c);'`,
7172
- "$ni=New-Object System.Windows.Forms.NotifyIcon",
7173
- "$ni.Icon=[System.Drawing.SystemIcons]::Information",
7174
- "$ni.Visible=$true",
7175
- "$script:clicked=$false",
7176
- "$ni.add_BalloonTipClicked({$script:clicked=$true})",
7177
- "$ni.ShowBalloonTip(8000,$Title,$Msg,[System.Windows.Forms.ToolTipIcon]::Warning)",
7178
- "$sw=[System.Diagnostics.Stopwatch]::StartNew()",
7179
- "while($sw.Elapsed.TotalSeconds -lt 9 -and -not $script:clicked){[System.Windows.Forms.Application]::DoEvents();Start-Sleep -Milliseconds 100}",
7180
- "if($script:clicked -and $Hwnd){try{$h=[System.IntPtr][int64]$Hwnd;[Sg.Win]::ShowWindow($h,9)|Out-Null;[Sg.Win]::SetForegroundWindow($h)|Out-Null}catch{}}",
7181
- "$ni.Visible=$false;$ni.Dispose()"
7182
- ].join("\n");
7183
- try {
7184
- writeFileSync3(p, script);
7185
- winScriptPath = p;
7186
- return p;
7187
- } catch {
7188
- return null;
7189
- }
7190
- }
7191
- function winNotify(title, msg) {
7192
- const script = ensureWinScript();
7193
- if (!script) return;
7194
- try {
7195
- const p = spawn("powershell", ["-NoProfile", "-NonInteractive", "-ExecutionPolicy", "Bypass", "-File", script, "-Title", title, "-Msg", msg, "-Hwnd", focusToken || ""], { stdio: "ignore", detached: true, windowsHide: true });
7196
- p.on("error", () => {
7197
- });
7198
- p.unref();
7199
- } catch {
7200
- }
7201
- }
7202
- function macBundleId() {
7203
- const prog = (process.env.TERM_PROGRAM || "").toLowerCase();
7204
- if (prog.includes("iterm")) return "com.googlecode.iterm2";
7205
- if (prog.includes("apple_terminal")) return "com.apple.Terminal";
7206
- if (prog.includes("vscode")) return "com.microsoft.VSCode";
7207
- return "com.apple.Terminal";
7208
- }
7209
- function macNotify(title, msg) {
7210
- try {
7211
- const p = spawn("terminal-notifier", ["-title", title, "-message", msg, "-activate", macBundleId(), "-sender", macBundleId()], { stdio: "ignore", detached: true });
7212
- p.on("error", () => {
7213
- try {
7214
- const esc = (s) => s.replace(/"/g, '\\"');
7215
- const a = spawn("osascript", ["-e", `display notification "${esc(msg)}" with title "${esc(title)}"`], { stdio: "ignore", detached: true });
7216
- a.on("error", () => {
7217
- });
7218
- a.unref();
7219
- } catch {
7220
- }
7221
- });
7222
- p.unref();
7223
- } catch {
7224
- }
7225
- }
7226
- var focusToken, winScriptPath;
7227
7118
  var init_notify = __esm({
7228
7119
  "src/tui/notify.ts"() {
7229
7120
  "use strict";
7230
- focusToken = null;
7231
- winScriptPath = null;
7232
7121
  }
7233
7122
  });
7234
7123
 
@@ -7280,9 +7169,9 @@ var init_hooks = __esm({
7280
7169
  // src/tui/panels/Live.tsx
7281
7170
  import { Box as Box2, Text as Text2, useInput } from "ink";
7282
7171
  import TextInput from "ink-text-input";
7283
- import { closeSync, mkdirSync as mkdirSync3, openSync, readSync, statSync, writeFileSync as writeFileSync4 } from "fs";
7172
+ import { closeSync, mkdirSync as mkdirSync3, openSync, readSync, statSync, writeFileSync as writeFileSync3 } from "fs";
7284
7173
  import { homedir as homedir4 } from "os";
7285
- import { join as join7 } from "path";
7174
+ import { join as join6 } from "path";
7286
7175
  import { useCallback as useCallback2, useEffect as useEffect2, useRef as useRef2, useState as useState2 } from "react";
7287
7176
  import { Fragment as Fragment2, jsx as jsx2, jsxs as jsxs2 } from "react/jsx-runtime";
7288
7177
  function tailLines(file, maxBytes = 131072) {
@@ -7811,10 +7700,10 @@ function LivePanel({ active: active2 }) {
7811
7700
  else if (input === "x") toggleSignal("dlp");
7812
7701
  else if (input === "r") toggleSignal("ratelimit");
7813
7702
  else if (input === "e") {
7814
- const file = join7(homedir4(), ".solongate", "live-export.jsonl");
7703
+ const file = join6(homedir4(), ".solongate", "live-export.jsonl");
7815
7704
  try {
7816
- mkdirSync3(join7(homedir4(), ".solongate"), { recursive: true });
7817
- writeFileSync4(file, visibleDesc.map((x) => JSON.stringify(x)).join("\n") + "\n");
7705
+ mkdirSync3(join6(homedir4(), ".solongate"), { recursive: true });
7706
+ writeFileSync3(file, visibleDesc.map((x) => JSON.stringify(x)).join("\n") + "\n");
7818
7707
  setActionMsg({ text: `\u2713 exported ${visibleDesc.length} lines \u2192 ${file}`, level: "ok", until: Date.now() + 6e3 });
7819
7708
  } catch (err2) {
7820
7709
  setActionMsg({ text: "\u2717 export failed: " + (err2 instanceof Error ? err2.message : String(err2)), level: "bad", until: Date.now() + 6e3 });
@@ -8081,8 +7970,8 @@ var init_Live = __esm({
8081
7970
  SPIN = ["\u280B", "\u2819", "\u2839", "\u2838", "\u283C", "\u2834", "\u2826", "\u2827", "\u2807", "\u280F"];
8082
7971
  BG = "#12234f";
8083
7972
  DIM_FLOOR = "#233457";
8084
- LOCAL_LOG = join7(homedir4(), ".solongate", "local-logs", "solongate-audit.jsonl");
8085
- RING = join7(process.cwd(), ".solongate", ".eval-ring.jsonl");
7973
+ LOCAL_LOG = join6(homedir4(), ".solongate", "local-logs", "solongate-audit.jsonl");
7974
+ RING = join6(process.cwd(), ".solongate", ".eval-ring.jsonl");
8086
7975
  hhmmss = (ts) => {
8087
7976
  const d = new Date(ts);
8088
7977
  return Number.isNaN(d.getTime()) ? "--:--:--" : d.toTimeString().slice(0, 8);
@@ -9298,7 +9187,6 @@ async function launchTui() {
9298
9187
  process.stderr.write("Not logged in. Run `solongate login` first.\n");
9299
9188
  return;
9300
9189
  }
9301
- captureFocusTarget();
9302
9190
  process.stdout.write("\x1B[?1049h\x1B[H");
9303
9191
  try {
9304
9192
  const { waitUntilExit } = render(/* @__PURE__ */ jsx10(App, {}));
@@ -9312,7 +9200,6 @@ var init_tui = __esm({
9312
9200
  "use strict";
9313
9201
  init_App();
9314
9202
  init_client();
9315
- init_notify();
9316
9203
  }
9317
9204
  });
9318
9205
 
@@ -10004,9 +9891,9 @@ var init_agents2 = __esm({
10004
9891
  });
10005
9892
 
10006
9893
  // src/commands/doctor.ts
10007
- import { existsSync as existsSync5, statSync as statSync2 } from "fs";
9894
+ import { existsSync as existsSync4, statSync as statSync2 } from "fs";
10008
9895
  import { homedir as homedir5 } from "os";
10009
- import { join as join8 } from "path";
9896
+ import { join as join7 } from "path";
10010
9897
  async function run6(argv) {
10011
9898
  const { flags } = parse(argv);
10012
9899
  const json = flagBool(flags, "json");
@@ -10036,7 +9923,7 @@ async function run6(argv) {
10036
9923
  } catch {
10037
9924
  }
10038
9925
  }
10039
- if (existsSync5(LOCAL_LOG2)) {
9926
+ if (existsSync4(LOCAL_LOG2)) {
10040
9927
  const st = statSync2(LOCAL_LOG2);
10041
9928
  const ageMin = (Date.now() - st.mtimeMs) / 6e4;
10042
9929
  checks.push({ name: "local logs", ok: true, detail: `on \xB7 ${(st.size / 1024).toFixed(0)}KB \xB7 last write ${ageMin < 1 ? "just now" : Math.round(ageMin) + "m ago"}` });
@@ -10066,14 +9953,14 @@ var init_doctor = __esm({
10066
9953
  init_api_client();
10067
9954
  init_format();
10068
9955
  init_args();
10069
- LOCAL_LOG2 = join8(homedir5(), ".solongate", "local-logs", "solongate-audit.jsonl");
9956
+ LOCAL_LOG2 = join7(homedir5(), ".solongate", "local-logs", "solongate-audit.jsonl");
10070
9957
  }
10071
9958
  });
10072
9959
 
10073
9960
  // src/commands/watch.ts
10074
- import { closeSync as closeSync2, existsSync as existsSync6, openSync as openSync2, readSync as readSync2, statSync as statSync3 } from "fs";
9961
+ import { closeSync as closeSync2, existsSync as existsSync5, openSync as openSync2, readSync as readSync2, statSync as statSync3 } from "fs";
10075
9962
  import { homedir as homedir6 } from "os";
10076
- import { join as join9 } from "path";
9963
+ import { join as join8 } from "path";
10077
9964
  function tailLocal(file, maxBytes = 131072) {
10078
9965
  try {
10079
9966
  const size = statSync3(file).size;
@@ -10117,7 +10004,7 @@ async function run7(argv) {
10117
10004
  for (const r of rows) if (keep(r)) print(r, json);
10118
10005
  };
10119
10006
  const pollLocal = () => {
10120
- if (cloudOnly || !existsSync6(LOCAL_LOG3)) return;
10007
+ if (cloudOnly || !existsSync5(LOCAL_LOG3)) return;
10121
10008
  const rows = [];
10122
10009
  for (const line of tailLocal(LOCAL_LOG3)) {
10123
10010
  try {
@@ -10180,7 +10067,7 @@ var init_watch = __esm({
10180
10067
  init_cli_utils();
10181
10068
  init_args();
10182
10069
  init_format();
10183
- LOCAL_LOG3 = join9(homedir6(), ".solongate", "local-logs", "solongate-audit.jsonl");
10070
+ LOCAL_LOG3 = join8(homedir6(), ".solongate", "local-logs", "solongate-audit.jsonl");
10184
10071
  trunc = (s, n) => s.length <= n ? s : s.slice(0, n - 1) + "\u2026";
10185
10072
  time = (ms) => new Date(ms).toTimeString().slice(0, 8);
10186
10073
  }
@@ -10482,32 +10369,32 @@ __export(global_install_exports, {
10482
10369
  runGlobalRestore: () => runGlobalRestore,
10483
10370
  unlockProtected: () => unlockProtected
10484
10371
  });
10485
- import { readFileSync as readFileSync7, writeFileSync as writeFileSync5, existsSync as existsSync7, mkdirSync as mkdirSync4 } from "fs";
10486
- import { resolve as resolve4, join as join10, dirname } from "path";
10372
+ import { readFileSync as readFileSync7, writeFileSync as writeFileSync4, existsSync as existsSync6, mkdirSync as mkdirSync4 } from "fs";
10373
+ import { resolve as resolve4, join as join9, dirname } from "path";
10487
10374
  import { homedir as homedir7 } from "os";
10488
10375
  import { fileURLToPath } from "url";
10489
10376
  import { createInterface } from "readline";
10490
- import { execFileSync as execFileSync3 } from "child_process";
10377
+ import { execFileSync as execFileSync2 } from "child_process";
10491
10378
  function lockFile(file) {
10492
- if (!existsSync7(file)) return;
10379
+ if (!existsSync6(file)) return;
10493
10380
  try {
10494
10381
  if (process.platform === "win32") {
10495
10382
  try {
10496
- execFileSync3("icacls", [file, "/deny", "*S-1-1-0:(WD,AD,DC,DE)"], { stdio: "ignore" });
10383
+ execFileSync2("icacls", [file, "/deny", "*S-1-1-0:(WD,AD,DC,DE)"], { stdio: "ignore" });
10497
10384
  } catch {
10498
10385
  }
10499
10386
  try {
10500
- execFileSync3("attrib", ["+R", file], { stdio: "ignore" });
10387
+ execFileSync2("attrib", ["+R", file], { stdio: "ignore" });
10501
10388
  } catch {
10502
10389
  }
10503
10390
  } else if (process.platform === "darwin") {
10504
10391
  try {
10505
- execFileSync3("chflags", ["uchg", file], { stdio: "ignore" });
10392
+ execFileSync2("chflags", ["uchg", file], { stdio: "ignore" });
10506
10393
  } catch {
10507
10394
  }
10508
10395
  } else {
10509
10396
  try {
10510
- execFileSync3("chattr", ["+i", file], { stdio: "ignore" });
10397
+ execFileSync2("chattr", ["+i", file], { stdio: "ignore" });
10511
10398
  } catch {
10512
10399
  }
10513
10400
  }
@@ -10515,29 +10402,29 @@ function lockFile(file) {
10515
10402
  }
10516
10403
  }
10517
10404
  function unlockFile(file) {
10518
- if (!existsSync7(file)) return;
10405
+ if (!existsSync6(file)) return;
10519
10406
  try {
10520
10407
  if (process.platform === "win32") {
10521
10408
  try {
10522
- execFileSync3("icacls", [file, "/remove:d", "*S-1-1-0"], { stdio: "ignore" });
10409
+ execFileSync2("icacls", [file, "/remove:d", "*S-1-1-0"], { stdio: "ignore" });
10523
10410
  } catch {
10524
10411
  }
10525
10412
  try {
10526
- execFileSync3("icacls", [file, "/reset"], { stdio: "ignore" });
10413
+ execFileSync2("icacls", [file, "/reset"], { stdio: "ignore" });
10527
10414
  } catch {
10528
10415
  }
10529
10416
  try {
10530
- execFileSync3("attrib", ["-R", file], { stdio: "ignore" });
10417
+ execFileSync2("attrib", ["-R", file], { stdio: "ignore" });
10531
10418
  } catch {
10532
10419
  }
10533
10420
  } else if (process.platform === "darwin") {
10534
10421
  try {
10535
- execFileSync3("chflags", ["nouchg", file], { stdio: "ignore" });
10422
+ execFileSync2("chflags", ["nouchg", file], { stdio: "ignore" });
10536
10423
  } catch {
10537
10424
  }
10538
10425
  } else {
10539
10426
  try {
10540
- execFileSync3("chattr", ["-i", file], { stdio: "ignore" });
10427
+ execFileSync2("chattr", ["-i", file], { stdio: "ignore" });
10541
10428
  } catch {
10542
10429
  }
10543
10430
  }
@@ -10547,10 +10434,10 @@ function unlockFile(file) {
10547
10434
  function protectedTargets() {
10548
10435
  const p = globalPaths();
10549
10436
  return [
10550
- join10(p.hooksDir, "guard.mjs"),
10551
- join10(p.hooksDir, "audit.mjs"),
10552
- join10(p.hooksDir, "stop.mjs"),
10553
- join10(p.hooksDir, "shield.mjs"),
10437
+ join9(p.hooksDir, "guard.mjs"),
10438
+ join9(p.hooksDir, "audit.mjs"),
10439
+ join9(p.hooksDir, "stop.mjs"),
10440
+ join9(p.hooksDir, "shield.mjs"),
10554
10441
  p.configPath,
10555
10442
  p.settingsPath
10556
10443
  ];
@@ -10563,25 +10450,25 @@ function unlockProtected() {
10563
10450
  }
10564
10451
  function globalPaths() {
10565
10452
  const home = homedir7();
10566
- const sgDir = join10(home, ".solongate");
10567
- const hooksDir = join10(sgDir, "hooks");
10568
- const claudeDir = join10(home, ".claude");
10453
+ const sgDir = join9(home, ".solongate");
10454
+ const hooksDir = join9(sgDir, "hooks");
10455
+ const claudeDir = join9(home, ".claude");
10569
10456
  return {
10570
10457
  home,
10571
10458
  sgDir,
10572
10459
  hooksDir,
10573
10460
  claudeDir,
10574
- settingsPath: join10(claudeDir, "settings.json"),
10575
- backupPath: join10(claudeDir, "settings.solongate.bak"),
10576
- configPath: join10(sgDir, "cloud-guard.json")
10461
+ settingsPath: join9(claudeDir, "settings.json"),
10462
+ backupPath: join9(claudeDir, "settings.solongate.bak"),
10463
+ configPath: join9(sgDir, "cloud-guard.json")
10577
10464
  };
10578
10465
  }
10579
10466
  function readHook(filename) {
10580
- return readFileSync7(join10(HOOKS_DIR, filename), "utf-8");
10467
+ return readFileSync7(join9(HOOKS_DIR, filename), "utf-8");
10581
10468
  }
10582
10469
  function readGuard() {
10583
- const bundled = join10(HOOKS_DIR, "guard.bundled.mjs");
10584
- return existsSync7(bundled) ? readFileSync7(bundled, "utf-8") : readHook("guard.mjs");
10470
+ const bundled = join9(HOOKS_DIR, "guard.bundled.mjs");
10471
+ return existsSync6(bundled) ? readFileSync7(bundled, "utf-8") : readHook("guard.mjs");
10585
10472
  }
10586
10473
  function ask(question) {
10587
10474
  const rl = createInterface({ input: process.stdin, output: process.stderr });
@@ -10594,14 +10481,14 @@ function runGlobalRestore() {
10594
10481
  const p = globalPaths();
10595
10482
  unlockProtected();
10596
10483
  removeClaudeShim();
10597
- if (existsSync7(p.backupPath)) {
10598
- writeFileSync5(p.settingsPath, readFileSync7(p.backupPath, "utf-8"));
10484
+ if (existsSync6(p.backupPath)) {
10485
+ writeFileSync4(p.settingsPath, readFileSync7(p.backupPath, "utf-8"));
10599
10486
  console.log(` Restored ${p.settingsPath} from backup.`);
10600
- } else if (existsSync7(p.settingsPath)) {
10487
+ } else if (existsSync6(p.settingsPath)) {
10601
10488
  try {
10602
10489
  const s = JSON.parse(readFileSync7(p.settingsPath, "utf-8"));
10603
10490
  delete s.hooks;
10604
- writeFileSync5(p.settingsPath, JSON.stringify(s, null, 2) + "\n");
10491
+ writeFileSync4(p.settingsPath, JSON.stringify(s, null, 2) + "\n");
10605
10492
  console.log(` Removed SolonGate hooks from ${p.settingsPath}.`);
10606
10493
  } catch {
10607
10494
  }
@@ -10616,7 +10503,7 @@ function escapeRe(s) {
10616
10503
  function resolveRealClaude() {
10617
10504
  try {
10618
10505
  const finder = process.platform === "win32" ? "where" : "which";
10619
- const out2 = execFileSync3(finder, ["claude"], { encoding: "utf-8" }).split(/\r?\n/).map((s) => s.trim()).filter(Boolean);
10506
+ const out2 = execFileSync2(finder, ["claude"], { encoding: "utf-8" }).split(/\r?\n/).map((s) => s.trim()).filter(Boolean);
10620
10507
  if (process.platform === "win32") {
10621
10508
  const low = (s) => s.toLowerCase();
10622
10509
  return out2.find((l) => low(l).endsWith(".cmd")) || out2.find((l) => low(l).endsWith(".exe")) || out2.find((l) => low(l).endsWith(".bat")) || out2[0] || null;
@@ -10629,24 +10516,24 @@ function resolveRealClaude() {
10629
10516
  function shimTargets() {
10630
10517
  if (process.platform === "win32") {
10631
10518
  try {
10632
- const prof = execFileSync3("powershell", ["-NoProfile", "-Command", "$PROFILE.CurrentUserAllHosts"], { encoding: "utf-8" }).trim();
10519
+ const prof = execFileSync2("powershell", ["-NoProfile", "-Command", "$PROFILE.CurrentUserAllHosts"], { encoding: "utf-8" }).trim();
10633
10520
  return prof ? [prof] : [];
10634
10521
  } catch {
10635
10522
  return [];
10636
10523
  }
10637
10524
  }
10638
- return [".bashrc", ".zshrc", ".profile"].map((f) => join10(homedir7(), f)).filter((f) => existsSync7(f));
10525
+ return [".bashrc", ".zshrc", ".profile"].map((f) => join9(homedir7(), f)).filter((f) => existsSync6(f));
10639
10526
  }
10640
10527
  function writeShimBlock(file, block2) {
10641
10528
  const re = new RegExp(escapeRe(SHIM_BEGIN) + "[\\s\\S]*?" + escapeRe(SHIM_END) + "\\r?\\n?", "g");
10642
- let content = existsSync7(file) ? readFileSync7(file, "utf-8") : "";
10529
+ let content = existsSync6(file) ? readFileSync7(file, "utf-8") : "";
10643
10530
  content = content.replace(re, "");
10644
10531
  if (block2) {
10645
10532
  if (content.length && !content.endsWith("\n")) content += "\n";
10646
10533
  content += block2 + "\n";
10647
10534
  }
10648
10535
  mkdirSync4(dirname(file), { recursive: true });
10649
- writeFileSync5(file, content);
10536
+ writeFileSync4(file, content);
10650
10537
  }
10651
10538
  function installClaudeShim(shieldPath) {
10652
10539
  const real = resolveRealClaude();
@@ -10700,19 +10587,19 @@ async function runGlobalInstall(opts = {}) {
10700
10587
  mkdirSync4(p.hooksDir, { recursive: true });
10701
10588
  mkdirSync4(p.claudeDir, { recursive: true });
10702
10589
  unlockProtected();
10703
- writeFileSync5(join10(p.hooksDir, "guard.mjs"), readGuard());
10704
- writeFileSync5(join10(p.hooksDir, "audit.mjs"), readHook("audit.mjs"));
10705
- writeFileSync5(join10(p.hooksDir, "stop.mjs"), readHook("stop.mjs"));
10706
- writeFileSync5(join10(p.hooksDir, "shield.mjs"), readHook("shield.mjs"));
10590
+ writeFileSync4(join9(p.hooksDir, "guard.mjs"), readGuard());
10591
+ writeFileSync4(join9(p.hooksDir, "audit.mjs"), readHook("audit.mjs"));
10592
+ writeFileSync4(join9(p.hooksDir, "stop.mjs"), readHook("stop.mjs"));
10593
+ writeFileSync4(join9(p.hooksDir, "shield.mjs"), readHook("shield.mjs"));
10707
10594
  console.log(` Installed hooks \u2192 ${p.hooksDir}`);
10708
- installClaudeShim(join10(p.hooksDir, "shield.mjs"));
10709
- writeFileSync5(p.configPath, JSON.stringify({ apiKey, apiUrl }, null, 2) + "\n");
10595
+ installClaudeShim(join9(p.hooksDir, "shield.mjs"));
10596
+ writeFileSync4(p.configPath, JSON.stringify({ apiKey, apiUrl }, null, 2) + "\n");
10710
10597
  console.log(` Wrote ${p.configPath}`);
10711
10598
  let existing = {};
10712
- if (existsSync7(p.settingsPath)) {
10599
+ if (existsSync6(p.settingsPath)) {
10713
10600
  const raw = readFileSync7(p.settingsPath, "utf-8");
10714
- if (!existsSync7(p.backupPath)) {
10715
- writeFileSync5(p.backupPath, raw);
10601
+ if (!existsSync6(p.backupPath)) {
10602
+ writeFileSync4(p.backupPath, raw);
10716
10603
  console.log(` Backed up existing settings \u2192 ${p.backupPath}`);
10717
10604
  }
10718
10605
  try {
@@ -10721,9 +10608,9 @@ async function runGlobalInstall(opts = {}) {
10721
10608
  existing = {};
10722
10609
  }
10723
10610
  }
10724
- const guardAbs = join10(p.hooksDir, "guard.mjs").replace(/\\/g, "/");
10725
- const auditAbs = join10(p.hooksDir, "audit.mjs").replace(/\\/g, "/");
10726
- const stopAbs = join10(p.hooksDir, "stop.mjs").replace(/\\/g, "/");
10611
+ const guardAbs = join9(p.hooksDir, "guard.mjs").replace(/\\/g, "/");
10612
+ const auditAbs = join9(p.hooksDir, "audit.mjs").replace(/\\/g, "/");
10613
+ const stopAbs = join9(p.hooksDir, "stop.mjs").replace(/\\/g, "/");
10727
10614
  const nodeBin = process.execPath.replace(/\\/g, "/");
10728
10615
  const call = process.platform === "win32" ? "& " : "";
10729
10616
  const hookCmd = (script) => `${call}"${nodeBin}" "${script}" claude-code "Claude Code"`;
@@ -10735,7 +10622,7 @@ async function runGlobalInstall(opts = {}) {
10735
10622
  Stop: [{ matcher: "", hooks: [{ type: "command", command: hookCmd(stopAbs) }] }]
10736
10623
  }
10737
10624
  };
10738
- writeFileSync5(p.settingsPath, JSON.stringify(merged, null, 2) + "\n");
10625
+ writeFileSync4(p.settingsPath, JSON.stringify(merged, null, 2) + "\n");
10739
10626
  console.log(` Registered global hooks \u2192 ${p.settingsPath}`);
10740
10627
  if (process.env["SOLONGATE_OS_LOCK"] === "1") {
10741
10628
  lockProtected();
@@ -10915,7 +10802,7 @@ import { createServer, request as httpRequest } from "http";
10915
10802
  import { request as httpsRequest } from "https";
10916
10803
  import { spawn as spawn3 } from "child_process";
10917
10804
  import { URL as URL2 } from "url";
10918
- import { readFileSync as readFileSync8, existsSync as existsSync8, readdirSync, statSync as statSync4 } from "fs";
10805
+ import { readFileSync as readFileSync8, existsSync as existsSync7, readdirSync, statSync as statSync4 } from "fs";
10919
10806
  import { resolve as resolve5 } from "path";
10920
10807
  import { homedir as homedir8 } from "os";
10921
10808
  function findCacheFile() {
@@ -10923,7 +10810,7 @@ function findCacheFile() {
10923
10810
  const envSel = process.env.SOLONGATE_AGENT_ID;
10924
10811
  if (envSel) {
10925
10812
  const f = resolve5(dir, ".policy-cache-" + envSel.replace(/[^a-zA-Z0-9_-]/g, "_") + ".json");
10926
- if (existsSync8(f)) return f;
10813
+ if (existsSync7(f)) return f;
10927
10814
  }
10928
10815
  let best = null, bestTs = -1;
10929
10816
  try {
@@ -10944,7 +10831,7 @@ function findCacheFile() {
10944
10831
  function loadCfg() {
10945
10832
  try {
10946
10833
  const f = findCacheFile();
10947
- if (f && existsSync8(f)) {
10834
+ if (f && existsSync7(f)) {
10948
10835
  const c2 = JSON.parse(readFileSync8(f, "utf-8"));
10949
10836
  const d = c2?.security?.dlpRedact;
10950
10837
  const g = c2?.security?.ghost;
@@ -11234,7 +11121,7 @@ __export(logs_server_exports, {
11234
11121
  });
11235
11122
  import { createServer as createServer2 } from "http";
11236
11123
  import { readFileSync as readFileSync9, statSync as statSync5 } from "fs";
11237
- import { resolve as resolve6, join as join11, isAbsolute } from "path";
11124
+ import { resolve as resolve6, join as join10, isAbsolute } from "path";
11238
11125
  import { homedir as homedir9 } from "os";
11239
11126
  import { readdirSync as readdirSync2 } from "fs";
11240
11127
  function allowedOrigins() {
@@ -11260,7 +11147,7 @@ async function findLogDir() {
11260
11147
  const files = readdirSync2(base).filter((f) => f.startsWith(".policy-cache-") && f.endsWith(".json"));
11261
11148
  for (const f of files) {
11262
11149
  try {
11263
- const c2 = JSON.parse(readFileSync9(join11(base, f), "utf-8"));
11150
+ const c2 = JSON.parse(readFileSync9(join10(base, f), "utf-8"));
11264
11151
  const p = c2?.security?.localLogs?.path;
11265
11152
  if (typeof p === "string" && p.trim()) return { dir: resolveLocalLogDir(p), configured: p };
11266
11153
  } catch {
@@ -11269,7 +11156,7 @@ async function findLogDir() {
11269
11156
  } catch {
11270
11157
  }
11271
11158
  try {
11272
- const cfgRaw = readFileSync9(join11(base, "cloud-guard.json"), "utf-8");
11159
+ const cfgRaw = readFileSync9(join10(base, "cloud-guard.json"), "utf-8");
11273
11160
  const { apiKey, apiUrl } = JSON.parse(cfgRaw);
11274
11161
  if (apiKey) {
11275
11162
  const url = `${apiUrl || "https://api.solongate.com"}/api/v1/policies/active`;
@@ -11298,7 +11185,7 @@ function setCors(req, res) {
11298
11185
  }
11299
11186
  function fileInfo(dir) {
11300
11187
  if (!dir) return { file: null, exists: false, size: 0, mtimeMs: 0 };
11301
- const file = join11(dir, LOG_FILENAME);
11188
+ const file = join10(dir, LOG_FILENAME);
11302
11189
  try {
11303
11190
  const st = statSync5(file);
11304
11191
  return { file, exists: true, size: st.size, mtimeMs: st.mtimeMs };
@@ -11411,7 +11298,7 @@ var init_logs_server = __esm({
11411
11298
 
11412
11299
  // src/inject.ts
11413
11300
  var inject_exports = {};
11414
- import { readFileSync as readFileSync10, writeFileSync as writeFileSync6, existsSync as existsSync9, copyFileSync } from "fs";
11301
+ import { readFileSync as readFileSync10, writeFileSync as writeFileSync5, existsSync as existsSync8, copyFileSync } from "fs";
11415
11302
  import { resolve as resolve7 } from "path";
11416
11303
  import { execSync } from "child_process";
11417
11304
  function parseInjectArgs(argv) {
@@ -11469,7 +11356,7 @@ WHAT IT DOES
11469
11356
  `);
11470
11357
  }
11471
11358
  function detectProject() {
11472
- if (!existsSync9(resolve7("package.json"))) return false;
11359
+ if (!existsSync8(resolve7("package.json"))) return false;
11473
11360
  try {
11474
11361
  const pkg = JSON.parse(readFileSync10(resolve7("package.json"), "utf-8"));
11475
11362
  const allDeps = { ...pkg.dependencies, ...pkg.devDependencies };
@@ -11485,13 +11372,13 @@ function findTsEntryFile() {
11485
11372
  const binPath = typeof pkg.bin === "string" ? pkg.bin : Object.values(pkg.bin)[0];
11486
11373
  if (typeof binPath === "string") {
11487
11374
  const srcPath = binPath.replace(/^\.\/dist\//, "./src/").replace(/\.js$/, ".ts");
11488
- if (existsSync9(resolve7(srcPath))) return resolve7(srcPath);
11489
- if (existsSync9(resolve7(binPath))) return resolve7(binPath);
11375
+ if (existsSync8(resolve7(srcPath))) return resolve7(srcPath);
11376
+ if (existsSync8(resolve7(binPath))) return resolve7(binPath);
11490
11377
  }
11491
11378
  }
11492
11379
  if (pkg.main) {
11493
11380
  const srcPath = pkg.main.replace(/^\.\/dist\//, "./src/").replace(/\.js$/, ".ts");
11494
- if (existsSync9(resolve7(srcPath))) return resolve7(srcPath);
11381
+ if (existsSync8(resolve7(srcPath))) return resolve7(srcPath);
11495
11382
  }
11496
11383
  } catch {
11497
11384
  }
@@ -11505,7 +11392,7 @@ function findTsEntryFile() {
11505
11392
  ];
11506
11393
  for (const c2 of candidates) {
11507
11394
  const full = resolve7(c2);
11508
- if (existsSync9(full)) {
11395
+ if (existsSync8(full)) {
11509
11396
  try {
11510
11397
  const content = readFileSync10(full, "utf-8");
11511
11398
  if (content.includes("McpServer") || content.includes("McpServer")) {
@@ -11516,13 +11403,13 @@ function findTsEntryFile() {
11516
11403
  }
11517
11404
  }
11518
11405
  for (const c2 of candidates) {
11519
- if (existsSync9(resolve7(c2))) return resolve7(c2);
11406
+ if (existsSync8(resolve7(c2))) return resolve7(c2);
11520
11407
  }
11521
11408
  return null;
11522
11409
  }
11523
11410
  function detectPackageManager() {
11524
- if (existsSync9(resolve7("pnpm-lock.yaml"))) return "pnpm";
11525
- if (existsSync9(resolve7("yarn.lock"))) return "yarn";
11411
+ if (existsSync8(resolve7("pnpm-lock.yaml"))) return "pnpm";
11412
+ if (existsSync8(resolve7("yarn.lock"))) return "yarn";
11526
11413
  return "npm";
11527
11414
  }
11528
11415
  function installSdk() {
@@ -11665,7 +11552,7 @@ async function main2() {
11665
11552
  }
11666
11553
  log3(" Language: TypeScript");
11667
11554
  const entryFile = opts.file ? resolve7(opts.file) : findTsEntryFile();
11668
- if (!entryFile || !existsSync9(entryFile)) {
11555
+ if (!entryFile || !existsSync8(entryFile)) {
11669
11556
  log3(` Could not find entry file.${opts.file ? ` File not found: ${opts.file}` : ""}`);
11670
11557
  log3("");
11671
11558
  log3(" Specify it manually: --file <path>");
@@ -11678,7 +11565,7 @@ async function main2() {
11678
11565
  log3("");
11679
11566
  const backupPath = entryFile + ".solongate-backup";
11680
11567
  if (opts.restore) {
11681
- if (!existsSync9(backupPath)) {
11568
+ if (!existsSync8(backupPath)) {
11682
11569
  log3(" No backup found. Nothing to restore.");
11683
11570
  process.exit(1);
11684
11571
  }
@@ -11714,12 +11601,12 @@ async function main2() {
11714
11601
  log3(" To apply: npx @solongate/proxy inject");
11715
11602
  process.exit(0);
11716
11603
  }
11717
- if (!existsSync9(backupPath)) {
11604
+ if (!existsSync8(backupPath)) {
11718
11605
  copyFileSync(entryFile, backupPath);
11719
11606
  log3("");
11720
11607
  log3(` Backup: ${backupPath}`);
11721
11608
  }
11722
- writeFileSync6(entryFile, result.modified);
11609
+ writeFileSync5(entryFile, result.modified);
11723
11610
  log3("");
11724
11611
  log3(" \u250C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2510");
11725
11612
  log3(" \u2502 SolonGate SDK injected successfully! \u2502");
@@ -11748,8 +11635,8 @@ var init_inject = __esm({
11748
11635
 
11749
11636
  // src/create.ts
11750
11637
  var create_exports = {};
11751
- import { mkdirSync as mkdirSync5, writeFileSync as writeFileSync7, existsSync as existsSync10 } from "fs";
11752
- import { resolve as resolve8, join as join12 } from "path";
11638
+ import { mkdirSync as mkdirSync5, writeFileSync as writeFileSync6, existsSync as existsSync9 } from "fs";
11639
+ import { resolve as resolve8, join as join11 } from "path";
11753
11640
  import { execSync as execSync2 } from "child_process";
11754
11641
  function withSpinner(message, fn) {
11755
11642
  const frames = ["\u28FE", "\u28FD", "\u28FB", "\u28BF", "\u287F", "\u28DF", "\u28EF", "\u28F7"];
@@ -11828,8 +11715,8 @@ EXAMPLES
11828
11715
  `);
11829
11716
  }
11830
11717
  function createProject(dir, name, _policy) {
11831
- writeFileSync7(
11832
- join12(dir, "package.json"),
11718
+ writeFileSync6(
11719
+ join11(dir, "package.json"),
11833
11720
  JSON.stringify(
11834
11721
  {
11835
11722
  name,
@@ -11858,8 +11745,8 @@ function createProject(dir, name, _policy) {
11858
11745
  2
11859
11746
  ) + "\n"
11860
11747
  );
11861
- writeFileSync7(
11862
- join12(dir, "tsconfig.json"),
11748
+ writeFileSync6(
11749
+ join11(dir, "tsconfig.json"),
11863
11750
  JSON.stringify(
11864
11751
  {
11865
11752
  compilerOptions: {
@@ -11879,9 +11766,9 @@ function createProject(dir, name, _policy) {
11879
11766
  2
11880
11767
  ) + "\n"
11881
11768
  );
11882
- mkdirSync5(join12(dir, "src"), { recursive: true });
11883
- writeFileSync7(
11884
- join12(dir, "src", "index.ts"),
11769
+ mkdirSync5(join11(dir, "src"), { recursive: true });
11770
+ writeFileSync6(
11771
+ join11(dir, "src", "index.ts"),
11885
11772
  `#!/usr/bin/env node
11886
11773
 
11887
11774
  console.log = (...args: unknown[]) => {
@@ -11922,8 +11809,8 @@ console.log('');
11922
11809
  console.log('Press Ctrl+C to stop.');
11923
11810
  `
11924
11811
  );
11925
- writeFileSync7(
11926
- join12(dir, ".mcp.json"),
11812
+ writeFileSync6(
11813
+ join11(dir, ".mcp.json"),
11927
11814
  JSON.stringify(
11928
11815
  {
11929
11816
  mcpServers: {
@@ -11940,13 +11827,13 @@ console.log('Press Ctrl+C to stop.');
11940
11827
  2
11941
11828
  ) + "\n"
11942
11829
  );
11943
- writeFileSync7(
11944
- join12(dir, ".env"),
11830
+ writeFileSync6(
11831
+ join11(dir, ".env"),
11945
11832
  `SOLONGATE_API_KEY=sg_live_YOUR_KEY_HERE
11946
11833
  `
11947
11834
  );
11948
- writeFileSync7(
11949
- join12(dir, ".gitignore"),
11835
+ writeFileSync6(
11836
+ join11(dir, ".gitignore"),
11950
11837
  `node_modules/
11951
11838
  dist/
11952
11839
  *.solongate-backup
@@ -11960,7 +11847,7 @@ async function main3() {
11960
11847
  const opts = parseCreateArgs(process.argv);
11961
11848
  const dir = resolve8(opts.name);
11962
11849
  printBanner("Create MCP Server");
11963
- if (existsSync10(dir)) {
11850
+ if (existsSync9(dir)) {
11964
11851
  log3(` ${c.red}Error:${c.reset} Directory "${opts.name}" already exists.`);
11965
11852
  process.exit(1);
11966
11853
  }
@@ -12039,12 +11926,12 @@ var init_create = __esm({
12039
11926
 
12040
11927
  // src/pull-push.ts
12041
11928
  var pull_push_exports = {};
12042
- import { readFileSync as readFileSync11, writeFileSync as writeFileSync8, existsSync as existsSync11 } from "fs";
11929
+ import { readFileSync as readFileSync11, writeFileSync as writeFileSync7, existsSync as existsSync10 } from "fs";
12043
11930
  import { resolve as resolve9 } from "path";
12044
11931
  function loadEnv() {
12045
11932
  if (process.env.SOLONGATE_API_KEY) return;
12046
11933
  const envPath = resolve9(".env");
12047
- if (!existsSync11(envPath)) return;
11934
+ if (!existsSync10(envPath)) return;
12048
11935
  try {
12049
11936
  const content = readFileSync11(envPath, "utf-8");
12050
11937
  for (const line of content.split("\n")) {
@@ -12234,7 +12121,7 @@ async function pull(apiKey, file, policyId) {
12234
12121
  const policy = await fetchCloudPolicy(apiKey, API_URL, policyId);
12235
12122
  const { id: _id, ...policyWithoutId } = policy;
12236
12123
  const json = JSON.stringify(policyWithoutId, null, 2) + "\n";
12237
- writeFileSync8(file, json, "utf-8");
12124
+ writeFileSync7(file, json, "utf-8");
12238
12125
  log5("");
12239
12126
  log5(green2(" Saved to: ") + file);
12240
12127
  log5(` ${dim2("Name:")} ${policy.name}`);
@@ -12246,7 +12133,7 @@ async function pull(apiKey, file, policyId) {
12246
12133
  log5("");
12247
12134
  }
12248
12135
  async function push(apiKey, file, policyId) {
12249
- if (!existsSync11(file)) {
12136
+ if (!existsSync10(file)) {
12250
12137
  log5(red2(`ERROR: File not found: ${file}`));
12251
12138
  process.exit(1);
12252
12139
  }
package/dist/tui/index.js CHANGED
@@ -150,9 +150,9 @@ function KeyHints({ hints }) {
150
150
  // src/tui/panels/Live.tsx
151
151
  import { Box as Box2, Text as Text2, useInput } from "ink";
152
152
  import TextInput from "ink-text-input";
153
- import { closeSync, mkdirSync, openSync, readSync, statSync, writeFileSync as writeFileSync2 } from "fs";
153
+ import { closeSync, mkdirSync, openSync, readSync, statSync, writeFileSync } from "fs";
154
154
  import { homedir as homedir3 } from "os";
155
- import { join as join4 } from "path";
155
+ import { join as join3 } from "path";
156
156
  import { useCallback as useCallback2, useEffect as useEffect2, useRef as useRef2, useState as useState2 } from "react";
157
157
 
158
158
  // src/api-client/client.ts
@@ -489,138 +489,28 @@ function list4() {
489
489
  var api = { policies: policies_exports, settings: settings_exports, stats: stats_exports, audit: audit_exports, agents: agents_exports, keys: keys_exports, mcp: mcp_exports };
490
490
 
491
491
  // src/tui/notify.ts
492
- import { spawn, execFileSync } from "child_process";
493
- import { writeFileSync, existsSync as existsSync2 } from "fs";
494
- import { join as join3 } from "path";
495
- import { tmpdir } from "os";
496
- var focusToken = null;
497
- function captureFocusTarget() {
492
+ import { spawn } from "child_process";
493
+ function desktopNotify(title, msg) {
498
494
  try {
499
495
  if (process.platform === "linux") {
500
- focusToken = (process.env.WINDOWID || "").trim() || null;
501
- if (!focusToken) {
502
- try {
503
- focusToken = execFileSync("xdotool", ["getactivewindow"], { encoding: "utf-8", timeout: 1500, stdio: ["ignore", "pipe", "ignore"] }).trim() || null;
504
- } catch {
505
- focusToken = null;
506
- }
507
- }
496
+ const p = spawn("notify-send", ["-a", "SolonGate", title, msg], { stdio: "ignore", detached: true });
497
+ p.on("error", () => {
498
+ });
499
+ p.unref();
508
500
  } else if (process.platform === "win32") {
509
- const ps = `Add-Type -Name W -Namespace N -MemberDefinition '[DllImport("user32.dll")]public static extern System.IntPtr GetForegroundWindow();' | Out-Null; [N.W]::GetForegroundWindow().ToInt64()`;
510
- try {
511
- focusToken = execFileSync("powershell", ["-NoProfile", "-NonInteractive", "-Command", ps], { encoding: "utf-8", timeout: 4e3, stdio: ["ignore", "pipe", "ignore"] }).trim() || null;
512
- } catch {
513
- focusToken = null;
514
- }
501
+ const q = (s) => s.replace(/'/g, "''");
502
+ const ps = `Add-Type -AssemblyName System.Windows.Forms;Add-Type -AssemblyName System.Drawing;$n=New-Object System.Windows.Forms.NotifyIcon;$n.Icon=[System.Drawing.SystemIcons]::Information;$n.Visible=$true;$n.ShowBalloonTip(6000,'${q(title)}','${q(msg)}',[System.Windows.Forms.ToolTipIcon]::Warning);Start-Sleep -Milliseconds 6500;$n.Dispose()`;
503
+ const p = spawn("powershell", ["-NoProfile", "-NonInteractive", "-Command", ps], { stdio: "ignore", detached: true, windowsHide: true });
504
+ p.on("error", () => {
505
+ });
506
+ p.unref();
507
+ } else if (process.platform === "darwin") {
508
+ const esc = (s) => s.replace(/"/g, '\\"');
509
+ const p = spawn("osascript", ["-e", `display notification "${esc(msg)}" with title "${esc(title)}"`], { stdio: "ignore", detached: true });
510
+ p.on("error", () => {
511
+ });
512
+ p.unref();
515
513
  }
516
- } catch {
517
- focusToken = null;
518
- }
519
- }
520
- function desktopNotify(title, msg) {
521
- try {
522
- if (process.platform === "linux") linuxNotify(title, msg);
523
- else if (process.platform === "win32") winNotify(title, msg);
524
- else if (process.platform === "darwin") macNotify(title, msg);
525
- } catch {
526
- }
527
- }
528
- function linuxNotify(title, msg) {
529
- let p;
530
- try {
531
- p = spawn("notify-send", ["--wait", "--action=default=Open", "-a", "SolonGate", title, msg], { stdio: ["ignore", "pipe", "ignore"] });
532
- } catch {
533
- return;
534
- }
535
- p.on("error", () => {
536
- });
537
- p.stdout?.on("data", (d) => {
538
- if (String(d).trim() === "default") raiseLinuxWindow();
539
- });
540
- p.unref();
541
- }
542
- function raiseLinuxWindow() {
543
- try {
544
- process.stdout.write("\x1B[5t");
545
- } catch {
546
- }
547
- if (!focusToken) return;
548
- try {
549
- const x = spawn("xdotool", ["windowactivate", focusToken], { stdio: "ignore" });
550
- x.on("error", () => {
551
- try {
552
- const hex = "0x" + Number(focusToken).toString(16);
553
- const w = spawn("wmctrl", ["-ia", hex], { stdio: "ignore" });
554
- w.on("error", () => {
555
- });
556
- w.unref();
557
- } catch {
558
- }
559
- });
560
- x.unref();
561
- } catch {
562
- }
563
- }
564
- var winScriptPath = null;
565
- function ensureWinScript() {
566
- if (winScriptPath && existsSync2(winScriptPath)) return winScriptPath;
567
- const p = join3(tmpdir(), "solongate-toast.ps1");
568
- const script = [
569
- "param([string]$Title,[string]$Msg,[string]$Hwnd)",
570
- "Add-Type -AssemblyName System.Windows.Forms",
571
- "Add-Type -AssemblyName System.Drawing",
572
- `Add-Type -Name Win -Namespace Sg -MemberDefinition '[DllImport("user32.dll")]public static extern bool SetForegroundWindow(System.IntPtr h);[DllImport("user32.dll")]public static extern bool ShowWindow(System.IntPtr h,int c);'`,
573
- "$ni=New-Object System.Windows.Forms.NotifyIcon",
574
- "$ni.Icon=[System.Drawing.SystemIcons]::Information",
575
- "$ni.Visible=$true",
576
- "$script:clicked=$false",
577
- "$ni.add_BalloonTipClicked({$script:clicked=$true})",
578
- "$ni.ShowBalloonTip(8000,$Title,$Msg,[System.Windows.Forms.ToolTipIcon]::Warning)",
579
- "$sw=[System.Diagnostics.Stopwatch]::StartNew()",
580
- "while($sw.Elapsed.TotalSeconds -lt 9 -and -not $script:clicked){[System.Windows.Forms.Application]::DoEvents();Start-Sleep -Milliseconds 100}",
581
- "if($script:clicked -and $Hwnd){try{$h=[System.IntPtr][int64]$Hwnd;[Sg.Win]::ShowWindow($h,9)|Out-Null;[Sg.Win]::SetForegroundWindow($h)|Out-Null}catch{}}",
582
- "$ni.Visible=$false;$ni.Dispose()"
583
- ].join("\n");
584
- try {
585
- writeFileSync(p, script);
586
- winScriptPath = p;
587
- return p;
588
- } catch {
589
- return null;
590
- }
591
- }
592
- function winNotify(title, msg) {
593
- const script = ensureWinScript();
594
- if (!script) return;
595
- try {
596
- const p = spawn("powershell", ["-NoProfile", "-NonInteractive", "-ExecutionPolicy", "Bypass", "-File", script, "-Title", title, "-Msg", msg, "-Hwnd", focusToken || ""], { stdio: "ignore", detached: true, windowsHide: true });
597
- p.on("error", () => {
598
- });
599
- p.unref();
600
- } catch {
601
- }
602
- }
603
- function macBundleId() {
604
- const prog = (process.env.TERM_PROGRAM || "").toLowerCase();
605
- if (prog.includes("iterm")) return "com.googlecode.iterm2";
606
- if (prog.includes("apple_terminal")) return "com.apple.Terminal";
607
- if (prog.includes("vscode")) return "com.microsoft.VSCode";
608
- return "com.apple.Terminal";
609
- }
610
- function macNotify(title, msg) {
611
- try {
612
- const p = spawn("terminal-notifier", ["-title", title, "-message", msg, "-activate", macBundleId(), "-sender", macBundleId()], { stdio: "ignore", detached: true });
613
- p.on("error", () => {
614
- try {
615
- const esc = (s) => s.replace(/"/g, '\\"');
616
- const a = spawn("osascript", ["-e", `display notification "${esc(msg)}" with title "${esc(title)}"`], { stdio: "ignore", detached: true });
617
- a.on("error", () => {
618
- });
619
- a.unref();
620
- } catch {
621
- }
622
- });
623
- p.unref();
624
514
  } catch {
625
515
  }
626
516
  }
@@ -671,8 +561,8 @@ var CONFIG = loadConfig();
671
561
  var SPIN = ["\u280B", "\u2819", "\u2839", "\u2838", "\u283C", "\u2834", "\u2826", "\u2827", "\u2807", "\u280F"];
672
562
  var BG = "#12234f";
673
563
  var DIM_FLOOR = "#233457";
674
- var LOCAL_LOG = join4(homedir3(), ".solongate", "local-logs", "solongate-audit.jsonl");
675
- var RING = join4(process.cwd(), ".solongate", ".eval-ring.jsonl");
564
+ var LOCAL_LOG = join3(homedir3(), ".solongate", "local-logs", "solongate-audit.jsonl");
565
+ var RING = join3(process.cwd(), ".solongate", ".eval-ring.jsonl");
676
566
  var hhmmss = (ts) => {
677
567
  const d = new Date(ts);
678
568
  return Number.isNaN(d.getTime()) ? "--:--:--" : d.toTimeString().slice(0, 8);
@@ -1215,10 +1105,10 @@ function LivePanel({ active: active2 }) {
1215
1105
  else if (input === "x") toggleSignal("dlp");
1216
1106
  else if (input === "r") toggleSignal("ratelimit");
1217
1107
  else if (input === "e") {
1218
- const file = join4(homedir3(), ".solongate", "live-export.jsonl");
1108
+ const file = join3(homedir3(), ".solongate", "live-export.jsonl");
1219
1109
  try {
1220
- mkdirSync(join4(homedir3(), ".solongate"), { recursive: true });
1221
- writeFileSync2(file, visibleDesc.map((x) => JSON.stringify(x)).join("\n") + "\n");
1110
+ mkdirSync(join3(homedir3(), ".solongate"), { recursive: true });
1111
+ writeFileSync(file, visibleDesc.map((x) => JSON.stringify(x)).join("\n") + "\n");
1222
1112
  setActionMsg({ text: `\u2713 exported ${visibleDesc.length} lines \u2192 ${file}`, level: "ok", until: Date.now() + 6e3 });
1223
1113
  } catch (err) {
1224
1114
  setActionMsg({ text: "\u2717 export failed: " + (err instanceof Error ? err.message : String(err)), level: "bad", until: Date.now() + 6e3 });
@@ -2587,7 +2477,6 @@ async function launchTui() {
2587
2477
  process.stderr.write("Not logged in. Run `solongate login` first.\n");
2588
2478
  return;
2589
2479
  }
2590
- captureFocusTarget();
2591
2480
  process.stdout.write("\x1B[?1049h\x1B[H");
2592
2481
  try {
2593
2482
  const { waitUntilExit } = render(/* @__PURE__ */ jsx10(App, {}));
@@ -1,4 +1,2 @@
1
- /** Capture the current terminal window once, at TUI startup. Cheap + best-effort. */
2
- export declare function captureFocusTarget(): void;
3
- /** Fire a desktop toast; clicking it raises the dataroom terminal. */
1
+ /** Fire a plain desktop toast. No-op-safe: missing tools just mean no toast. */
4
2
  export declare function desktopNotify(title: string, msg: string): void;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@solongate/proxy",
3
- "version": "0.81.18",
3
+ "version": "0.81.19",
4
4
  "description": "AI tool security proxy: protect any AI tool server with customizable policies, path/command constraints, rate limiting, and audit logging. No code changes required.",
5
5
  "type": "module",
6
6
  "bin": {