tokmon 0.28.3 → 0.28.4

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.
@@ -168,6 +168,21 @@ function reclaimDeadLock(opts = {}) {
168
168
  return false;
169
169
  }
170
170
  }
171
+ function reclaimUnhealthyLock(expected, opts = {}, minimumAgeMs = 0) {
172
+ const path = lockfilePath(opts);
173
+ try {
174
+ const before = lstatSync(path);
175
+ if (!before.isFile()) return false;
176
+ const current = readLock(opts);
177
+ if (!current || current.ownerId !== expected.ownerId || current.pid !== expected.pid || current.startedAt !== expected.startedAt || current.state !== "ready" || Date.now() - current.startedAt < minimumAgeMs) return false;
178
+ const after = lstatSync(path);
179
+ if (after.dev !== before.dev || after.ino !== before.ino) return false;
180
+ unlinkSync(path);
181
+ return true;
182
+ } catch {
183
+ return false;
184
+ }
185
+ }
171
186
  function reclaimAbandonedLock(opts = {}, graceMs = 1e4) {
172
187
  const path = lockfilePath(opts);
173
188
  try {
@@ -271,6 +286,7 @@ export {
271
286
  writeLock,
272
287
  unlinkLock,
273
288
  reclaimDeadLock,
289
+ reclaimUnhealthyLock,
274
290
  reclaimAbandonedLock,
275
291
  isAlive,
276
292
  verifyLock,
@@ -3,7 +3,7 @@ import {
3
3
  readLock,
4
4
  retireIncompatibleCliOwner,
5
5
  verifyLock
6
- } from "./chunk-USKOQIE3.js";
6
+ } from "./chunk-5B3XCEMC.js";
7
7
  import {
8
8
  daemonChannelFromWire,
9
9
  resolveDaemonChannel
@@ -1,8 +1,8 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
3
  attachOrSpawn
4
- } from "./chunk-P5JN5DDX.js";
5
- import "./chunk-USKOQIE3.js";
4
+ } from "./chunk-FLANGRI6.js";
5
+ import "./chunk-5B3XCEMC.js";
6
6
  import "./chunk-UYPDMVW5.js";
7
7
  import {
8
8
  createDaemonRpcClient
package/dist/cli.js CHANGED
@@ -41,7 +41,7 @@ function validateServeArgs(serveArgs) {
41
41
  }
42
42
  async function main() {
43
43
  if (subcommand && ["usage", "models", "query", "providers", "snapshot", "config"].includes(subcommand)) {
44
- const { runQueryCommand } = await import("./cli-command-MD3RJRP4.js");
44
+ const { runQueryCommand } = await import("./cli-command-I4GRR3MF.js");
45
45
  try {
46
46
  const output = await runQueryCommand(
47
47
  subcommand,
@@ -60,14 +60,14 @@ Run tokmon ${subcommand} --help for usage.
60
60
  return;
61
61
  }
62
62
  if (subcommand === "__daemon") {
63
- const { runDaemon } = await import("./daemon-EMOA36WB.js");
63
+ const { runDaemon } = await import("./daemon-ZXV3V5CS.js");
64
64
  await runDaemon(args.slice(1), { foreground: false });
65
65
  process.exitCode ??= 0;
66
66
  return;
67
67
  }
68
68
  if (subcommand === "serve" || subcommand === "web") {
69
69
  validateServeArgs(args.slice(1));
70
- const { runDaemon } = await import("./daemon-EMOA36WB.js");
70
+ const { runDaemon } = await import("./daemon-ZXV3V5CS.js");
71
71
  await runDaemon(args.slice(1), { foreground: true });
72
72
  process.exitCode ??= 0;
73
73
  return;
@@ -117,7 +117,7 @@ Run tokmon ${subcommand} --help for usage.
117
117
  }
118
118
  const { loadConfig } = await import("./config-3DGZ47F7.js");
119
119
  const { resolveGlyphs, setGlyphs } = await import("./glyphs-NKCSZLGO.js");
120
- const { attachOrSpawn } = await import("./daemon-handle-JHE5MKMI.js");
120
+ const { attachOrSpawn } = await import("./daemon-handle-G4OGPFR3.js");
121
121
  const config = await loadConfig();
122
122
  setGlyphs(resolveGlyphs({
123
123
  flag: asciiFlag,
@@ -7,11 +7,12 @@ import {
7
7
  readLock,
8
8
  reclaimAbandonedLock,
9
9
  reclaimDeadLock,
10
+ reclaimUnhealthyLock,
10
11
  retireIncompatibleCliOwner,
11
12
  unlinkLock,
12
13
  verifyLock,
13
14
  writeLock
14
- } from "./chunk-USKOQIE3.js";
15
+ } from "./chunk-5B3XCEMC.js";
15
16
  import {
16
17
  appVersion,
17
18
  startWebServer
@@ -91,6 +92,12 @@ async function discoverOwner(opts, protocolVersion) {
91
92
  if (!current && reclaimAbandonedLock(opts)) current = readLock(opts);
92
93
  const live = await verifyLock(current, protocolVersion);
93
94
  if (live) return live;
95
+ if (current?.state === "ready" && current.protocolVersion === protocolVersion && isAlive(current.pid)) {
96
+ const winner = await waitForOwner(opts, protocolVersion);
97
+ if (winner) return winner;
98
+ if (reclaimUnhealthyLock(current, opts)) return null;
99
+ current = readLock(opts);
100
+ }
94
101
  if (current?.state === "starting" && current.protocolVersion === protocolVersion && isAlive(current.pid)) {
95
102
  const winner = await waitForOwner(opts, protocolVersion);
96
103
  if (winner) return winner;
@@ -1,8 +1,8 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
3
  attachOrSpawn
4
- } from "./chunk-P5JN5DDX.js";
5
- import "./chunk-USKOQIE3.js";
4
+ } from "./chunk-FLANGRI6.js";
5
+ import "./chunk-5B3XCEMC.js";
6
6
  import "./chunk-UYPDMVW5.js";
7
7
  import "./chunk-JZSZEHVD.js";
8
8
  import "./chunk-HNWEJ6MS.js";
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "tokmon",
3
- "version": "0.28.3",
3
+ "version": "0.28.4",
4
4
  "description": "Terminal + web dashboard for Claude Code, Codex, Cursor, Grok, opencode, pi, Copilot, Gemini & more — usage, limits, and costs",
5
5
  "type": "module",
6
6
  "bin": {