@chatpanel/gateway 0.1.2 → 0.1.3

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@chatpanel/gateway",
3
- "version": "0.1.2",
3
+ "version": "0.1.3",
4
4
  "description": "Local privacy gateway — redacts PII out of OpenAI/Anthropic API traffic before it reaches a model, then restores it in the reply. Point opencode, codex, aider, Claude Code, etc. at it.",
5
5
  "type": "module",
6
6
  "bin": {
package/src/config.js CHANGED
@@ -7,6 +7,7 @@
7
7
 
8
8
  import { readFileSync, existsSync } from 'node:fs';
9
9
  import { join } from 'node:path';
10
+ import os from 'node:os';
10
11
 
11
12
  const DEFAULTS = {
12
13
  host: '127.0.0.1',
@@ -100,7 +101,9 @@ function deepMerge(base, over) {
100
101
  export function loadConfig(env = process.env) {
101
102
  let cfg = DEFAULTS;
102
103
 
103
- const path = env.CHATPANEL_GATEWAY_CONFIG || join(process.cwd(), 'gateway.config.json');
104
+ // Writable per-user location by default (NOT cwd — a login service runs with
105
+ // cwd "/", which is read-only). Same path persistConfig() writes to.
106
+ const path = env.CHATPANEL_GATEWAY_CONFIG || join(os.homedir(), '.chatpanel', 'gateway.config.json');
104
107
  if (existsSync(path)) {
105
108
  try {
106
109
  cfg = deepMerge(cfg, JSON.parse(readFileSync(path, 'utf8')));
@@ -2,15 +2,19 @@
2
2
  // configure it live over the localhost API (GET/POST /config). The gateway stays
3
3
  // authoritative — the extension is just a UI client.
4
4
 
5
- import { writeFileSync } from 'node:fs';
6
- import { join } from 'node:path';
5
+ import { writeFileSync, mkdirSync } from 'node:fs';
6
+ import { join, dirname } from 'node:path';
7
+ import os from 'node:os';
7
8
 
9
+ // Default to a writable per-user location, NOT process.cwd(): when the gateway
10
+ // runs as a login service its cwd is "/" (read-only → EROFS on save).
8
11
  export function configPath(env = process.env) {
9
- return env.CHATPANEL_GATEWAY_CONFIG || join(process.cwd(), 'gateway.config.json');
12
+ return env.CHATPANEL_GATEWAY_CONFIG || join(os.homedir(), '.chatpanel', 'gateway.config.json');
10
13
  }
11
14
 
12
15
  // Persist the user-editable subset (not derived runtime state).
13
16
  export function persistConfig(cfg, path = configPath()) {
17
+ mkdirSync(dirname(path), { recursive: true });
14
18
  const out = {
15
19
  host: cfg.host, port: cfg.port, backend: cfg.backend,
16
20
  bridge: cfg.bridge, upstreams: cfg.upstreams, redaction: cfg.redaction,
package/src/server.js CHANGED
@@ -31,7 +31,7 @@ import * as openai from './openai.js';
31
31
  import * as responses from './responses.js';
32
32
  import * as anthropic from './anthropic.js';
33
33
 
34
- export const VERSION = '0.1.2';
34
+ export const VERSION = '0.1.3';
35
35
 
36
36
  const KNOWN_AGENTS = new Set(['codex', 'claude', 'opencode', 'pi', 'kiro', 'antigravity']);
37
37