@miller-tech/uap 1.172.6 → 1.172.8
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/.tsbuildinfo +1 -1
- package/dist/models/openai-compat-client.d.ts.map +1 -1
- package/dist/models/openai-compat-client.js +56 -27
- package/dist/models/openai-compat-client.js.map +1 -1
- package/package.json +1 -1
- package/src/policies/enforcers/__pycache__/_common.cpython-312.pyc +0 -0
- package/src/policies/enforcers/enforcement_infra_protect.py +47 -0
- package/templates/hooks/__pycache__/deliver_autoroute.cpython-312.pyc +0 -0
- package/tools/agents/scripts/__pycache__/toolcall_path_normalizer.cpython-312.pyc +0 -0
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"openai-compat-client.d.ts","sourceRoot":"","sources":["../../src/models/openai-compat-client.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;
|
|
1
|
+
{"version":3,"file":"openai-compat-client.d.ts","sourceRoot":"","sources":["../../src/models/openai-compat-client.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAOH,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AAC9C,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAEjD,MAAM,WAAW,yBAAyB;IACxC,oHAAoH;IACpH,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB,uEAAuE;IACvE,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AA6BD;;;;;;;;GAQG;AACH,wBAAgB,eAAe,CAAC,GAAG,EAAE,GAAG,GAAG,OAAO,CAEjD;AAED;;;;;;;;;;;;GAYG;AACH,wBAAgB,wBAAwB,CACtC,KAAK,EAAE;IAAE,YAAY,CAAC,EAAE,MAAM,CAAA;CAAE,EAChC,GAAG,EAAE,GAAG,GACP,MAAM,GAAG,SAAS,CAYpB;AAmGD,qBAAa,kBAAmB,YAAW,WAAW;IACpD,OAAO,CAAC,QAAQ,CAAC,eAAe,CAAS;IACzC,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAS;gBAEvB,OAAO,GAAE,yBAA8B;IAQnD;;;;;;OAMG;IACG,QAAQ,CACZ,KAAK,EAAE,WAAW,EAClB,MAAM,EAAE,MAAM,EACd,OAAO,CAAC,EAAE;QAAE,SAAS,CAAC,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,MAAM,CAAC;QAAC,WAAW,CAAC,EAAE,MAAM,CAAC;QAAC,YAAY,CAAC,EAAE,OAAO,CAAA;KAAE,GAC/F,OAAO,CAAC;QAAE,OAAO,EAAE,MAAM,CAAC;QAAC,UAAU,EAAE;YAAE,KAAK,EAAE,MAAM,CAAC;YAAC,MAAM,EAAE,MAAM,CAAA;SAAE,CAAC;QAAC,SAAS,EAAE,MAAM,CAAA;KAAE,CAAC;YAgBnF,QAAQ;CAyEvB"}
|
|
@@ -7,6 +7,7 @@
|
|
|
7
7
|
* endpoints.
|
|
8
8
|
*/
|
|
9
9
|
import { existsSync, readFileSync } from 'node:fs';
|
|
10
|
+
import { homedir } from 'node:os';
|
|
10
11
|
import { dirname, join } from 'node:path';
|
|
11
12
|
import { fetchModelWithRetry, modelHttpTimeoutMs } from './long-fetch.js';
|
|
12
13
|
const DEFAULT_TIMEOUT_MS = modelHttpTimeoutMs();
|
|
@@ -90,40 +91,68 @@ export function resolveRequestCredential(model, url) {
|
|
|
90
91
|
* token recovered here can only ever travel to the local proxy.
|
|
91
92
|
*/
|
|
92
93
|
let cachedProxyToken = null;
|
|
94
|
+
/** PROXY_AUTH_TOKEN out of one systemd-style EnvironmentFile, or undefined. */
|
|
95
|
+
function readProxyTokenFrom(file) {
|
|
96
|
+
if (!existsSync(file))
|
|
97
|
+
return undefined;
|
|
98
|
+
for (const line of readFileSync(file, 'utf8').split('\n')) {
|
|
99
|
+
const trimmed = line.trim();
|
|
100
|
+
if (!trimmed || trimmed.startsWith('#'))
|
|
101
|
+
continue;
|
|
102
|
+
// systemd EnvironmentFile semantics: KEY=<rest of line>. No shell
|
|
103
|
+
// word-splitting, and no quote handling beyond a wrapping pair.
|
|
104
|
+
const eq = trimmed.indexOf('=');
|
|
105
|
+
if (eq < 0 || trimmed.slice(0, eq).trim() !== 'PROXY_AUTH_TOKEN')
|
|
106
|
+
continue;
|
|
107
|
+
const value = trimmed
|
|
108
|
+
.slice(eq + 1)
|
|
109
|
+
.trim()
|
|
110
|
+
.replace(/^(['"])([\s\S]*)\1$/, '$2');
|
|
111
|
+
if (value)
|
|
112
|
+
return value;
|
|
113
|
+
}
|
|
114
|
+
return undefined;
|
|
115
|
+
}
|
|
116
|
+
/**
|
|
117
|
+
* Every place the token may live, in priority order.
|
|
118
|
+
*
|
|
119
|
+
* Walking up from cwd is not enough on its own. `uap setup` writes a
|
|
120
|
+
* `.uap/proxy.env` into EVERY project, but only the install that generated the
|
|
121
|
+
* secret carries PROXY_AUTH_TOKEN — so an agent working in an unrelated project
|
|
122
|
+
* finds a proxy.env, finds no token in it, and (previously) stopped there and
|
|
123
|
+
* sent an unauthenticated request. That is the deliver 401: the file existed,
|
|
124
|
+
* it simply wasn't the file with the secret.
|
|
125
|
+
*
|
|
126
|
+
* So: never stop at the first file, only at the first file that actually has the
|
|
127
|
+
* key, and fall back to the user-level config where the token is installed once
|
|
128
|
+
* per machine rather than once per project.
|
|
129
|
+
*/
|
|
130
|
+
function* proxyEnvCandidates() {
|
|
131
|
+
let dir = process.cwd();
|
|
132
|
+
// The MCP server's cwd is wherever the client launched it, often a
|
|
133
|
+
// subdirectory of the project rather than its root.
|
|
134
|
+
for (let depth = 0; depth < 12; depth++) {
|
|
135
|
+
yield join(dir, '.uap', 'proxy.env');
|
|
136
|
+
const parent = dirname(dir);
|
|
137
|
+
if (parent === dir)
|
|
138
|
+
break;
|
|
139
|
+
dir = parent;
|
|
140
|
+
}
|
|
141
|
+
const home = homedir();
|
|
142
|
+
yield join(process.env.XDG_CONFIG_HOME || join(home, '.config'), 'uap', 'proxy.env');
|
|
143
|
+
yield join(home, '.uap', 'proxy.env');
|
|
144
|
+
}
|
|
93
145
|
function proxyTokenFromFile() {
|
|
94
146
|
if (cachedProxyToken !== null)
|
|
95
147
|
return cachedProxyToken;
|
|
96
148
|
cachedProxyToken = undefined;
|
|
97
149
|
try {
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
const candidate = join(dir, '.uap', 'proxy.env');
|
|
103
|
-
if (existsSync(candidate)) {
|
|
104
|
-
for (const line of readFileSync(candidate, 'utf8').split('\n')) {
|
|
105
|
-
const trimmed = line.trim();
|
|
106
|
-
if (!trimmed || trimmed.startsWith('#'))
|
|
107
|
-
continue;
|
|
108
|
-
// systemd EnvironmentFile semantics: KEY=<rest of line>. No shell
|
|
109
|
-
// word-splitting, and no quote handling beyond a wrapping pair.
|
|
110
|
-
const eq = trimmed.indexOf('=');
|
|
111
|
-
if (eq < 0 || trimmed.slice(0, eq).trim() !== 'PROXY_AUTH_TOKEN')
|
|
112
|
-
continue;
|
|
113
|
-
const value = trimmed
|
|
114
|
-
.slice(eq + 1)
|
|
115
|
-
.trim()
|
|
116
|
-
.replace(/^(['"])([\s\S]*)\1$/, '$2');
|
|
117
|
-
if (value)
|
|
118
|
-
cachedProxyToken = value;
|
|
119
|
-
break;
|
|
120
|
-
}
|
|
150
|
+
for (const candidate of proxyEnvCandidates()) {
|
|
151
|
+
const token = readProxyTokenFrom(candidate);
|
|
152
|
+
if (token) {
|
|
153
|
+
cachedProxyToken = token;
|
|
121
154
|
break;
|
|
122
155
|
}
|
|
123
|
-
const parent = dirname(dir);
|
|
124
|
-
if (parent === dir)
|
|
125
|
-
break;
|
|
126
|
-
dir = parent;
|
|
127
156
|
}
|
|
128
157
|
}
|
|
129
158
|
catch {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"openai-compat-client.js","sourceRoot":"","sources":["../../src/models/openai-compat-client.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,UAAU,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;AACnD,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AAE1C,OAAO,EAAE,mBAAmB,EAAE,kBAAkB,EAAE,MAAM,iBAAiB,CAAC;AAiB1E,MAAM,kBAAkB,GAAG,kBAAkB,EAAE,CAAC;AAEhD,MAAM,WAAW,GAAG,6CAA6C,CAAC;AAClE,gFAAgF;AAChF,2EAA2E;AAC3E,wEAAwE;AACxE,2EAA2E;AAC3E,iFAAiF;AACjF,MAAM,OAAO,GAAG,8CAA8C,CAAC;AAE/D,SAAS,aAAa,CAAC,QAAgB;IACrC,MAAM,CAAC,GAAG,OAAO,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;IACjC,IAAI,CAAC,CAAC;QAAE,OAAO,KAAK,CAAC;IACrB,MAAM,CAAC,CAAC,EAAE,CAAC,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC5C,IAAI,CAAC,CAAC,EAAE,CAAC,EAAE,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,GAAG,GAAG,CAAC;QAAE,OAAO,KAAK,CAAC;IAC1E,IAAI,CAAC,KAAK,EAAE;QAAE,OAAO,IAAI,CAAC;IAC1B,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK,GAAG;QAAE,OAAO,IAAI,CAAC;IACxC,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,IAAI,EAAE,IAAI,CAAC,IAAI,EAAE;QAAE,OAAO,IAAI,CAAC;IACjD,OAAO,KAAK,CAAC;AACf,CAAC;AAED;;;;;;;;GAQG;AACH,MAAM,UAAU,eAAe,CAAC,GAAQ;IACtC,OAAO,WAAW,CAAC,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,IAAI,aAAa,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC;AACvE,CAAC;AAED;;;;;;;;;;;;GAYG;AACH,MAAM,UAAU,wBAAwB,CACtC,KAAgC,EAChC,GAAQ;IAER,MAAM,QAAQ,GAAG,KAAK,CAAC,YAAY,CAAC,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;IAClF,IAAI,QAAQ,EAAE,CAAC;QACb,IAAI,GAAG,CAAC,QAAQ,KAAK,QAAQ,IAAI,CAAC,eAAe,CAAC,GAAG,CAAC,EAAE,CAAC;YACvD,MAAM,IAAI,KAAK,CACb,oBAAoB,KAAK,CAAC,YAAY,SAAS,GAAG,CAAC,QAAQ,wBAAwB,GAAG,CAAC,QAAQ,eAAe,CAC/G,CAAC;QACJ,CAAC;QACD,OAAO,QAAQ,CAAC;IAClB,CAAC;IACD,wEAAwE;IACxE,OAAO,eAAe,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,gBAAgB,IAAI,kBAAkB,EAAE,CAAC,CAAC,CAAC,SAAS,CAAC;AACjG,CAAC;AAED;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,IAAI,gBAAgB,GAA8B,IAAI,CAAC;AAEvD,SAAS,kBAAkB;
|
|
1
|
+
{"version":3,"file":"openai-compat-client.js","sourceRoot":"","sources":["../../src/models/openai-compat-client.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
Binary file
|
|
@@ -98,6 +98,48 @@ REASON = (
|
|
|
98
98
|
)
|
|
99
99
|
|
|
100
100
|
|
|
101
|
+
# Scripts invoked by the command, e.g. `bash deploy.sh`, `sh ./x.sh`, `./x.sh`,
|
|
102
|
+
# `source x.sh`. Every rule above reads the command TEXT, so moving a
|
|
103
|
+
# service-restart of the inference stack one level down -- into a file -- slipped
|
|
104
|
+
# past all of them. Not theoretical: it was used during this project's own
|
|
105
|
+
# sessions to cycle the stack while the gate reported nothing to block.
|
|
106
|
+
_SCRIPT_INVOCATION_RE = re.compile(
|
|
107
|
+
r"(?:^|[|;&]|\bsudo\b|\benv\b\s)\s*"
|
|
108
|
+
r"(?:(?:ba|z|k|da)?sh\s+|source\s+|\.\s+)?"
|
|
109
|
+
r"((?:\./|/|~/|\.\./)[^\s;|&<>()'\"]+|[\w./-]+\.(?:sh|bash|zsh))"
|
|
110
|
+
)
|
|
111
|
+
# Only small local files are worth reading; the cap keeps this off the hot path.
|
|
112
|
+
_MAX_SCRIPT_BYTES = 256 * 1024
|
|
113
|
+
|
|
114
|
+
|
|
115
|
+
def _referenced_script_bodies(cmd: str, limit: int = 4) -> list[tuple[str, str]]:
|
|
116
|
+
"""(path, contents) for scripts this command would execute.
|
|
117
|
+
|
|
118
|
+
Best-effort and deliberately shallow: one level, at most `limit` files, and
|
|
119
|
+
any read error is skipped. A miss must degrade to today's behaviour
|
|
120
|
+
(text-only scanning), never to an exception that takes the whole gate down.
|
|
121
|
+
"""
|
|
122
|
+
found: list[tuple[str, str]] = []
|
|
123
|
+
seen: set[str] = set()
|
|
124
|
+
for m in _SCRIPT_INVOCATION_RE.finditer(cmd):
|
|
125
|
+
raw = m.group(1)
|
|
126
|
+
if raw in seen:
|
|
127
|
+
continue
|
|
128
|
+
seen.add(raw)
|
|
129
|
+
try:
|
|
130
|
+
p = Path(raw).expanduser()
|
|
131
|
+
if not p.is_absolute():
|
|
132
|
+
p = Path.cwd() / p
|
|
133
|
+
if not p.is_file() or p.stat().st_size > _MAX_SCRIPT_BYTES:
|
|
134
|
+
continue
|
|
135
|
+
found.append((str(p), p.read_text(errors="replace")))
|
|
136
|
+
except Exception: # noqa: BLE001 - unreadable/oddly-named file: skip it
|
|
137
|
+
continue
|
|
138
|
+
if len(found) >= limit:
|
|
139
|
+
break
|
|
140
|
+
return found
|
|
141
|
+
|
|
142
|
+
|
|
101
143
|
def main() -> None:
|
|
102
144
|
operation, args = parse_cli()
|
|
103
145
|
if operation not in BASH_OPS:
|
|
@@ -108,6 +150,11 @@ def main() -> None:
|
|
|
108
150
|
for rule in RULES:
|
|
109
151
|
if rule.search(cmd):
|
|
110
152
|
emit(False, REASON)
|
|
153
|
+
# Same rules, applied to the body of any script the command would run.
|
|
154
|
+
for path, body in _referenced_script_bodies(cmd):
|
|
155
|
+
for rule in RULES:
|
|
156
|
+
if rule.search(body):
|
|
157
|
+
emit(False, f"{REASON} (matched inside the invoked script {path})")
|
|
111
158
|
emit(True, "no infra-destructive pattern")
|
|
112
159
|
|
|
113
160
|
|
|
Binary file
|