@askalf/dario 5.4.20 → 5.4.22
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/live-fingerprint.d.ts +2 -0
- package/dist/live-fingerprint.js +35 -4
- package/dist/proxy.js +17 -5
- package/package.json +1 -1
|
@@ -286,6 +286,8 @@ export declare function findInstalledCC(): {
|
|
|
286
286
|
path: string | null;
|
|
287
287
|
version: string | null;
|
|
288
288
|
};
|
|
289
|
+
/** Test-only: drop the resolved-binary memo. */
|
|
290
|
+
export declare function _resetClaudeBinCacheForTest(): void;
|
|
289
291
|
export declare function enumerateClaudeCandidates(): string[];
|
|
290
292
|
/**
|
|
291
293
|
* Given a captured /v1/messages request body, pull out the fields that
|
package/dist/live-fingerprint.js
CHANGED
|
@@ -341,10 +341,20 @@ function quarantineCorruptCache(reason) {
|
|
|
341
341
|
* other's partial writes. Exposed for tests via `_atomicWriteJsonForTest`.
|
|
342
342
|
*/
|
|
343
343
|
function atomicWriteJson(targetPath, data) {
|
|
344
|
-
|
|
344
|
+
// 0700: whichever code path creates ~/.dario first decides that directory's
|
|
345
|
+
// permissions, and this one runs at startup, before any credential write.
|
|
346
|
+
// Without a mode it lands 755 on Linux, which makes every non-0600 file inside
|
|
347
|
+
// world-readable. The credential paths already create their dirs 0700; this was
|
|
348
|
+
// the one that could get there first and did not.
|
|
349
|
+
mkdirSync(dirname(targetPath), { recursive: true, mode: 0o700 });
|
|
345
350
|
const tmp = `${targetPath}.${process.pid}.tmp`;
|
|
346
351
|
try {
|
|
347
|
-
|
|
352
|
+
// 0600: this file holds the UNSCRUBBED live capture. Verified on the Linux
|
|
353
|
+
// deployment to contain `# Environment` (cwd, OS, platform) and `gitStatus:`
|
|
354
|
+
// (branch, modified files, recent commits); structurally it can also carry
|
|
355
|
+
// `# claudeMd`, `# userEmail` and `# auto memory` — the scrub list exists
|
|
356
|
+
// because CC emits them. Credentials beside it are 0600; this was 0644.
|
|
357
|
+
writeFileSync(tmp, JSON.stringify(data, null, 2), { mode: 0o600 });
|
|
348
358
|
renameSync(tmp, targetPath);
|
|
349
359
|
}
|
|
350
360
|
catch (err) {
|
|
@@ -587,11 +597,32 @@ export function findInstalledCC() {
|
|
|
587
597
|
const version = path ? probeInstalledCCVersion() : null;
|
|
588
598
|
return { path, version };
|
|
589
599
|
}
|
|
600
|
+
// Resolving the binary means enumerating candidates and, when there is more
|
|
601
|
+
// than one, SPAWNING each to compare versions. That is a subprocess per
|
|
602
|
+
// candidate per call, and there are four call sites (refresh, capture,
|
|
603
|
+
// findInstalledCC, drift). Profiling a proxy start showed ~720ms of blocking
|
|
604
|
+
// spawnSync, over half of a ~1270ms startup, from repeating this and the
|
|
605
|
+
// version probe. The installed binary cannot change mid-process, so resolve
|
|
606
|
+
// once. Keyed on the override so a test flipping DARIO_CLAUDE_BIN is not served
|
|
607
|
+
// a stale answer.
|
|
608
|
+
let _claudeBinCache = null;
|
|
609
|
+
/** Test-only: drop the resolved-binary memo. */
|
|
610
|
+
export function _resetClaudeBinCacheForTest() {
|
|
611
|
+
_claudeBinCache = null;
|
|
612
|
+
}
|
|
590
613
|
function findClaudeBinary() {
|
|
591
614
|
// Honor an explicit override first — useful for tests and for users on
|
|
592
615
|
// non-standard installs.
|
|
593
|
-
|
|
594
|
-
|
|
616
|
+
const override = process.env.DARIO_CLAUDE_BIN;
|
|
617
|
+
if (override)
|
|
618
|
+
return override;
|
|
619
|
+
if (_claudeBinCache && _claudeBinCache.key === '')
|
|
620
|
+
return _claudeBinCache.value;
|
|
621
|
+
const resolved = resolveClaudeBinaryUncached();
|
|
622
|
+
_claudeBinCache = { key: '', value: resolved };
|
|
623
|
+
return resolved;
|
|
624
|
+
}
|
|
625
|
+
function resolveClaudeBinaryUncached() {
|
|
595
626
|
const candidates = enumerateClaudeCandidates();
|
|
596
627
|
if (candidates.length === 0)
|
|
597
628
|
return null;
|
package/dist/proxy.js
CHANGED
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
import { createServer } from 'node:http';
|
|
2
2
|
import { randomUUID, randomBytes, timingSafeEqual, createHash } from 'node:crypto';
|
|
3
|
-
import { execSync } from 'node:child_process';
|
|
4
3
|
import { readFileSync, readdirSync, createWriteStream } from 'node:fs';
|
|
5
4
|
import { join } from 'node:path';
|
|
6
5
|
import { homedir } from 'node:os';
|
|
@@ -11,7 +10,7 @@ import { buildHealthResponse, derivePoolStatus, shouldDiscloseHealthInternals }
|
|
|
11
10
|
import { darioVersion } from './version.js';
|
|
12
11
|
import { buildCCRequest, applyCcPromptCaching, parseEffortSuffix, reverseMapResponse, createStreamingReverseMapper, orderHeadersForOutbound, overlayTemplateHeaderValues, forwardClientCCIdentityHeaders, isMcpToolName, CC_TEMPLATE, effectiveCacheControl, withForced1hBeta } from './cc-template.js';
|
|
13
12
|
import { stampCch, hasCchSeed } from './cch.js';
|
|
14
|
-
import { describeTemplate, detectDrift, checkCCCompat } from './live-fingerprint.js';
|
|
13
|
+
import { describeTemplate, detectDrift, checkCCCompat, probeInstalledCCVersion } from './live-fingerprint.js';
|
|
15
14
|
import { AccountPool, computeStickyKey, parseRateLimits, modelFamily, isInAuthCooldown, authCooldownMs, reconcilePoolAccounts, resolvePoolStrategy } from './pool.js';
|
|
16
15
|
import { Analytics, billingBucketFromClaim, formatUsageLogLine, SUBSCRIPTION_CLAIMS } from './analytics.js';
|
|
17
16
|
import { OverageGuard, buildHaltErrorBody } from './overage-guard.js';
|
|
@@ -118,8 +117,15 @@ export function buildBillingTag(cliVersion, cch) {
|
|
|
118
117
|
function detectCliVersion() {
|
|
119
118
|
const templateVersion = CC_TEMPLATE._version || '2.1.100';
|
|
120
119
|
try {
|
|
121
|
-
|
|
122
|
-
|
|
120
|
+
// Was its own execSync('claude --version'), which made this the THIRD
|
|
121
|
+
// synchronous spawn of a 259 MB binary during startup for one version
|
|
122
|
+
// string — findClaudeBinary probes candidates, probeInstalledCCVersion
|
|
123
|
+
// probes the winner, and this probed again. probeInstalledCCVersion is
|
|
124
|
+
// memoised per process and resolves the binary properly (honours
|
|
125
|
+
// DARIO_CLAUDE_BIN, picks the newest candidate) rather than trusting
|
|
126
|
+
// whatever bare `claude` the shell finds, so reusing it is both cheaper and
|
|
127
|
+
// more correct.
|
|
128
|
+
return probeInstalledCCVersion() ?? templateVersion;
|
|
123
129
|
}
|
|
124
130
|
catch {
|
|
125
131
|
return templateVersion;
|
|
@@ -1082,7 +1088,13 @@ export async function startProxy(opts = {}) {
|
|
|
1082
1088
|
let logFileStream = null;
|
|
1083
1089
|
if (logFilePath) {
|
|
1084
1090
|
try {
|
|
1085
|
-
|
|
1091
|
+
// 0600 to match everything else dario writes. Records are redacted metadata
|
|
1092
|
+
// rather than bodies (writeLogLine runs redactSecrets; -vv bodies go to
|
|
1093
|
+
// stdout), so this is defence-in-depth — but it still shows which account
|
|
1094
|
+
// served which request and when, and 0644 contradicted the convention every
|
|
1095
|
+
// credential path here follows. Mode applies to CREATION only, so an
|
|
1096
|
+
// existing log keeps its own mode, which is right for append.
|
|
1097
|
+
logFileStream = createWriteStream(logFilePath, { flags: 'a', mode: 0o600 });
|
|
1086
1098
|
logFileStream.on('error', (err) => {
|
|
1087
1099
|
console.error(`[dario] log-file write error: ${err.message} (logging disabled)`);
|
|
1088
1100
|
logFileStream = null;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@askalf/dario",
|
|
3
|
-
"version": "5.4.
|
|
3
|
+
"version": "5.4.22",
|
|
4
4
|
"description": "Use your Claude Pro/Max subscription in any tool — Cursor, Cline, Aider, the Agent SDK, your scripts — at subscription pricing, not per-token API bills. One local Anthropic + OpenAI-compatible endpoint.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"bin": {
|