@askalf/dario 5.4.22 → 5.4.24

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/README.md CHANGED
@@ -18,7 +18,9 @@
18
18
 
19
19
  <p><strong>One local endpoint. Every AI tool you own. The subscription you already pay for.</strong></p>
20
20
 
21
- <sub><code>npm i -g @askalf/dario</code> · <strong>0</strong> runtime deps · <a href="https://www.npmjs.com/package/@askalf/dario">SLSA-attested</a> every release · nothing phones home · ~22k lines you can read in a weekend · independent, unofficial, third-party (<a href="DISCLAIMER.md">DISCLAIMER.md</a>)</sub>
21
+ <sub><code>npm i -g @askalf/dario</code> · <strong>0</strong> runtime deps · <a href="https://www.npmjs.com/package/@askalf/dario">SLSA-attested</a> every release · nothing phones home · ~24k lines you can read in a weekend · independent, unofficial, third-party (<a href="DISCLAIMER.md">DISCLAIMER.md</a>)</sub>
22
+
23
+ <sub>Part of <a href="#own-your-stack"><strong>Own Your Stack</strong></a> — 12 open tools for owning your AI infra: <a href="https://github.com/askalf/truecopy">truecopy</a> · <a href="https://github.com/askalf/strongroom">strongroom</a> · <a href="https://github.com/askalf/fieldpass">fieldpass</a> · <a href="https://github.com/askalf/plumbline">plumbline</a> · <a href="#own-your-stack">full family ↓</a></sub>
22
24
 
23
25
  </div>
24
26
 
@@ -353,6 +355,7 @@ dario is the routing layer of **[Own Your Stack](https://github.com/askalf)**
353
355
  - **[strongroom](https://github.com/askalf/strongroom)** — own your agent secrets
354
356
  - **[cordon](https://github.com/askalf/cordon)** — own your prompts
355
357
  - **[fieldpass](https://github.com/askalf/fieldpass)** — own your agent browser
358
+ - **[plumbline](https://github.com/askalf/plumbline)** — own your agent oversight
356
359
  - **[amnesia](https://github.com/askalf/amnesia)** — own your search
357
360
  - **[askalf](https://askalf.org)** — own your operation: the AI operation that runs Sprayberry Labs
358
361
 
package/dist/doctor.js CHANGED
@@ -20,6 +20,7 @@ import { CC_TEMPLATE, resolveSystemPrompt, } from './cc-template.js';
20
20
  import { describeTemplate, detectDrift, checkCCCompat, findInstalledCC, SUPPORTED_CC_RANGE, CURRENT_SCHEMA_VERSION, compareVersions, } from './live-fingerprint.js';
21
21
  import { detectCCOAuthConfig } from './cc-oauth-detect.js';
22
22
  import { runAuthorizeProbe } from './cc-authorize-probe.js';
23
+ import { MIGRATED_LOGIN_ALIAS } from './accounts.js';
23
24
  const __dirname = dirname(fileURLToPath(import.meta.url));
24
25
  /**
25
26
  * Format a epoch timestamp reset time relative to the current time.
@@ -109,6 +110,7 @@ export function checkIdentityDrift(input) {
109
110
  }
110
111
  const aligned = [];
111
112
  const drifted = [];
113
+ const driftedAliases = [];
112
114
  for (const acc of poolAccounts) {
113
115
  const deviceMatch = acc.deviceId === live.deviceId;
114
116
  const acctMatch = acc.accountUuid === live.accountUuid;
@@ -118,6 +120,7 @@ export function checkIdentityDrift(input) {
118
120
  else {
119
121
  const which = !deviceMatch && !acctMatch ? 'both' : !deviceMatch ? 'deviceId' : 'accountUuid';
120
122
  drifted.push(`${acc.alias} (${which})`);
123
+ driftedAliases.push(acc.alias);
121
124
  }
122
125
  }
123
126
  if (drifted.length === 0) {
@@ -127,10 +130,30 @@ export function checkIdentityDrift(input) {
127
130
  detail: `${aligned.length}/${poolAccounts.length} pool account${poolAccounts.length === 1 ? '' : 's'} match ~/.claude.json (userID=${shortId(live.deviceId)})`,
128
131
  }];
129
132
  }
133
+ // The remedy is deliberately NOT `accounts add <alias>`. That command
134
+ // exits 1 on an alias that already exists ("Remove it first"), and its
135
+ // default path runs a full OAuth browser flow rather than re-snapshotting
136
+ // — so naming it here walked every drifted user into a dead end. The two
137
+ // alias kinds genuinely need different commands: the reserved login alias
138
+ // is back-filled from whatever credentials are current, so removing it is
139
+ // enough (it re-materializes on the next `dario login` / `dario proxy`),
140
+ // while a user-added alias has to be removed and re-added, which re-runs
141
+ // OAuth for that account by design.
142
+ const loginDrifted = driftedAliases.includes(MIGRATED_LOGIN_ALIAS);
143
+ const otherDrifted = driftedAliases.filter((a) => a !== MIGRATED_LOGIN_ALIAS);
144
+ const fixes = [];
145
+ if (loginDrifted) {
146
+ fixes.push(`\`dario accounts remove ${MIGRATED_LOGIN_ALIAS}\` — it re-materializes from your ` +
147
+ `current credentials on the next \`dario login\` / \`dario proxy\``);
148
+ }
149
+ if (otherDrifted.length > 0) {
150
+ fixes.push(`\`dario accounts remove <alias>\` then \`dario accounts add <alias>\` to re-snapshot` +
151
+ `${otherDrifted.length === 1 ? '' : ' (for each of them)'} — the add re-runs OAuth for that account`);
152
+ }
130
153
  return [{
131
154
  status: 'warn',
132
155
  label: 'Identity',
133
- detail: `${drifted.length}/${poolAccounts.length} pool account${poolAccounts.length === 1 ? '' : 's'} drifted from ~/.claude.json (live userID=${shortId(live.deviceId)}): ${drifted.join('; ')} — re-run \`dario accounts add <alias>\` to refresh the stored snapshot, or non-Haiku requests on the drifted account(s) will 401`,
156
+ detail: `${drifted.length}/${poolAccounts.length} pool account${poolAccounts.length === 1 ? '' : 's'} drifted from ~/.claude.json (live userID=${shortId(live.deviceId)}): ${drifted.join('; ')} — non-Haiku requests on the drifted account(s) will 401. Fix: ${fixes.join('; ')}`,
134
157
  }];
135
158
  }
136
159
  /**
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@askalf/dario",
3
- "version": "5.4.22",
3
+ "version": "5.4.24",
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": {