@teith/openclaw-runware-provider 0.3.4 → 0.3.6

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.
@@ -1,78 +1,55 @@
1
1
  /**
2
2
  * Emits `openclaw.cost.usd` OpenTelemetry counter for runware completions.
3
3
  *
4
- * Why this file exists
5
- * --------------------
6
- * OpenClaw 2026.6.1 has two cost-computation paths with different data
7
- * sources:
4
+ * In openclaw 2026.6.x, session transcripts live as
5
+ * `~/.openclaw/agents/<agentId>/sessions/<sessionId>.trajectory.jsonl`
6
+ * with this per-entry shape:
8
7
  *
9
- * Completion path (works) — openai-completions runtime calls
10
- * `calculateCost(model, usage)` with the live `model` object returned
11
- * by this plugin's `catalog.run`. `model.cost` is populated from
12
- * `/v1/models`. Result is written into transcript JSONL as
13
- * `usage.cost`. Usage UI reads from there.
8
+ * {
9
+ * "traceSchema": "openclaw-trajectory", "schemaVersion": 1,
10
+ * "traceId": "...", "type": "model.completed",
11
+ * "sessionKey": "agent:main:<channel>[:<frag>]",
12
+ * "provider": "runware", "modelId": "qwen35-397b-a17b-fp8",
13
+ * "data": {
14
+ * "usage": { "input", "output", "cacheRead", "total" },
15
+ * "promptCache": { "lastCallUsage": { "cacheWrite" } }
16
+ * }
17
+ * }
14
18
  *
15
- * Diagnostic path (broken)`agent-runner` emits `model.usage`
16
- * diagnostic events with `costUsd = estimateUsageCost({ usage, cost:
17
- * resolveModelCostConfig(provider, model, config) })`. That resolver
18
- * reads ONLY from:
19
- * `models.json` cost index
20
- * `openclaw.json` `models.providers.*.models[].cost`
21
- * `cachedPricing` Map (seeded from manifest `modelCatalog` and
22
- * upstream OpenRouter/LiteLLM catalogs)
23
- * None of those carry runware pricing — pricing flows through the
24
- * plugin's runtime `catalog.run`, which is invisible to this resolver.
25
- * So `costUsd` is undefined, the diagnostics-otel handler's
26
- * `if (evt.costUsd) costCounter.add(...)` guard is falsy, and the
27
- * `openclaw_cost_usd_total` counter stays at zero.
19
+ * Transcripts DO NOT carry the dollar cost openclaw's Usage UI multiplies
20
+ * tokens by the live `model.cost` from the plugin's ProviderShape at render
21
+ * time. The diagnostic-path counter `openclaw.cost.usd` tries to do the
22
+ * same thing through `resolveModelCostConfig(...)`, which reads from a
23
+ * cache that's never seeded for runware (cache only accepts manifest
24
+ * `modelCatalog` rows + openclaw.json + OpenRouter/LiteLLM catalogs;
25
+ * runtime `catalog.run` results don't reach it). Result: counter stays at
26
+ * zero even though everything else works.
28
27
  *
29
- * What this file does
30
- * -------------------
31
- * Tails session transcripts (`~/.openclaw/agents/<id>/sessions/*.jsonl`),
32
- * which already contain `usage.cost.total` because the completion path
33
- * filled them in. Parses new entries on a 2s tick, filters to
34
- * `provider === "runware"`, and writes to the same global OTel counter
35
- * `openclaw.cost.usd` that diagnostics-otel tried (and failed) to write
36
- * to. The OTel API stores its MeterProvider on a globalThis symbol slot
37
- * so plugin-side `getMeter(...).createCounter("openclaw.cost.usd", ...)`
38
- * shares the MeterProvider that diagnostics-otel registered at gateway
39
- * start. Counter writes from both sides land on the same
40
- * `(name, attributes)` time series in OTLP Prometheus → GMP.
28
+ * This module fills that gap from inside the plugin. We:
29
+ * 1. Maintain a per-modelId pricing snapshot (input/output/cacheRead/
30
+ * cacheWrite per-million-token USD) refreshed every 30s from the
31
+ * same `fetchModels()` cache that feeds catalog.run. So pricing is
32
+ * genuinely real-time, no static manifest field, no build step.
33
+ * 2. Tail every `*.trajectory.jsonl` under `~/.openclaw/agents/<id>/sessions/`
34
+ * on a 2s interval, filtering to `type === "model.completed"`. The
35
+ * sibling `trace.artifacts` event duplicates the same usage data, so
36
+ * filtering by type prevents double-counting.
37
+ * 3. Compute USD with openclaw's own formula:
38
+ * cost = (cost_per_1M * tokens) / 1_000_000
39
+ * 4. Write to the global OTel counter `openclaw.cost.usd` with
40
+ * attributes (`openclaw.provider`, `openclaw.model`, `openclaw.channel`)
41
+ * that match what diagnostics-otel uses for `openclaw.tokens` —
42
+ * same labels → same Prometheus time series.
41
43
  *
42
- * Why polling and not a hook
43
- * --------------------------
44
- * `llm_output` and `agent_end` carry usage, but openclaw blocks them for
45
- * non-bundled plugins unless `plugins.entries.<id>.hooks
46
- * .allowConversationAccess: true` is set in openclaw.json — i.e. in the
47
- * manager. `model_call_ended` is bundled-accessible but only carries
48
- * sanitized metadata (no usage). `wrapStreamFn` is a provider-runtime
49
- * hook on `registerProvider` but `register(api)` is not invoked for
50
- * external plugins in 2026.5.x and behavior is unverified in 2026.6.1.
51
- * Tailing the transcript file is the one path that does not depend on
52
- * any of those (the transcripts are written by the completion path
53
- * regardless of hooks).
44
+ * Anchors at file size on first sighting, so only entries written after
45
+ * gateway start count (no replay of historical transcripts on every
46
+ * restart). Survives plugin hot-reload via globalThis state.
54
47
  *
55
- * Double-counting safety
56
- * ----------------------
57
- * On startup the poller takes the current size of every transcript
58
- * file as the initial offset existing entries are assumed already
59
- * accounted for by whatever was running before. Only bytes appended
60
- * after startup emit metrics. Gateway restart resets all offsets, which
61
- * is the correct behavior for a process-scoped counter (Prometheus
62
- * `rate()` handles counter resets).
63
- *
64
- * If openclaw eventually fixes the diagnostic path so that
65
- * `evt.costUsd` is populated for runware, both writers will increment
66
- * the same series and the metric will double for runware. At that point
67
- * delete this module. (We do not attempt to detect that case at runtime
68
- * because diagnostics-otel does not expose its emit-or-skip decision to
69
- * other plugins.)
70
- */
71
- /**
72
- * Idempotent. Safe to call from multiple plugin entry files; only the
73
- * first call starts the interval, subsequent calls return immediately.
74
- * Survives openclaw plugin hot-reload because state lives on
75
- * `globalThis`.
48
+ * Polling instead of a runtime hook because openclaw blocks `llm_output`
49
+ * and `agent_end` for non-bundled plugins unless
50
+ * `plugins.entries.<id>.hooks.allowConversationAccess: true` is set in
51
+ * openclaw.json i.e. the manager. The trajectory file is written
52
+ * unconditionally and is plugin-readable, so no config flag needed.
76
53
  */
77
54
  export declare function startCostMetricPoller(opts?: {
78
55
  openclawHome?: string;
@@ -1 +1 @@
1
- {"version":3,"file":"cost-metric.d.ts","sourceRoot":"","sources":["../src/cost-metric.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAqEG;AAgDH;;;;;GAKG;AACH,wBAAgB,qBAAqB,CAAC,IAAI,CAAC,EAAE;IAC3C,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB,GAAG,IAAI,CAiCP"}
1
+ {"version":3,"file":"cost-metric.d.ts","sourceRoot":"","sources":["../src/cost-metric.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAoDG;AA0EH,wBAAgB,qBAAqB,CAAC,IAAI,CAAC,EAAE;IAC3C,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB,GAAG,IAAI,CAiCP"}
@@ -1,82 +1,69 @@
1
1
  /**
2
2
  * Emits `openclaw.cost.usd` OpenTelemetry counter for runware completions.
3
3
  *
4
- * Why this file exists
5
- * --------------------
6
- * OpenClaw 2026.6.1 has two cost-computation paths with different data
7
- * sources:
4
+ * In openclaw 2026.6.x, session transcripts live as
5
+ * `~/.openclaw/agents/<agentId>/sessions/<sessionId>.trajectory.jsonl`
6
+ * with this per-entry shape:
8
7
  *
9
- * Completion path (works) — openai-completions runtime calls
10
- * `calculateCost(model, usage)` with the live `model` object returned
11
- * by this plugin's `catalog.run`. `model.cost` is populated from
12
- * `/v1/models`. Result is written into transcript JSONL as
13
- * `usage.cost`. Usage UI reads from there.
8
+ * {
9
+ * "traceSchema": "openclaw-trajectory", "schemaVersion": 1,
10
+ * "traceId": "...", "type": "model.completed",
11
+ * "sessionKey": "agent:main:<channel>[:<frag>]",
12
+ * "provider": "runware", "modelId": "qwen35-397b-a17b-fp8",
13
+ * "data": {
14
+ * "usage": { "input", "output", "cacheRead", "total" },
15
+ * "promptCache": { "lastCallUsage": { "cacheWrite" } }
16
+ * }
17
+ * }
14
18
  *
15
- * Diagnostic path (broken)`agent-runner` emits `model.usage`
16
- * diagnostic events with `costUsd = estimateUsageCost({ usage, cost:
17
- * resolveModelCostConfig(provider, model, config) })`. That resolver
18
- * reads ONLY from:
19
- * `models.json` cost index
20
- * `openclaw.json` `models.providers.*.models[].cost`
21
- * `cachedPricing` Map (seeded from manifest `modelCatalog` and
22
- * upstream OpenRouter/LiteLLM catalogs)
23
- * None of those carry runware pricing — pricing flows through the
24
- * plugin's runtime `catalog.run`, which is invisible to this resolver.
25
- * So `costUsd` is undefined, the diagnostics-otel handler's
26
- * `if (evt.costUsd) costCounter.add(...)` guard is falsy, and the
27
- * `openclaw_cost_usd_total` counter stays at zero.
19
+ * Transcripts DO NOT carry the dollar cost openclaw's Usage UI multiplies
20
+ * tokens by the live `model.cost` from the plugin's ProviderShape at render
21
+ * time. The diagnostic-path counter `openclaw.cost.usd` tries to do the
22
+ * same thing through `resolveModelCostConfig(...)`, which reads from a
23
+ * cache that's never seeded for runware (cache only accepts manifest
24
+ * `modelCatalog` rows + openclaw.json + OpenRouter/LiteLLM catalogs;
25
+ * runtime `catalog.run` results don't reach it). Result: counter stays at
26
+ * zero even though everything else works.
28
27
  *
29
- * What this file does
30
- * -------------------
31
- * Tails session transcripts (`~/.openclaw/agents/<id>/sessions/*.jsonl`),
32
- * which already contain `usage.cost.total` because the completion path
33
- * filled them in. Parses new entries on a 2s tick, filters to
34
- * `provider === "runware"`, and writes to the same global OTel counter
35
- * `openclaw.cost.usd` that diagnostics-otel tried (and failed) to write
36
- * to. The OTel API stores its MeterProvider on a globalThis symbol slot
37
- * so plugin-side `getMeter(...).createCounter("openclaw.cost.usd", ...)`
38
- * shares the MeterProvider that diagnostics-otel registered at gateway
39
- * start. Counter writes from both sides land on the same
40
- * `(name, attributes)` time series in OTLP Prometheus → GMP.
28
+ * This module fills that gap from inside the plugin. We:
29
+ * 1. Maintain a per-modelId pricing snapshot (input/output/cacheRead/
30
+ * cacheWrite per-million-token USD) refreshed every 30s from the
31
+ * same `fetchModels()` cache that feeds catalog.run. So pricing is
32
+ * genuinely real-time, no static manifest field, no build step.
33
+ * 2. Tail every `*.trajectory.jsonl` under `~/.openclaw/agents/<id>/sessions/`
34
+ * on a 2s interval, filtering to `type === "model.completed"`. The
35
+ * sibling `trace.artifacts` event duplicates the same usage data, so
36
+ * filtering by type prevents double-counting.
37
+ * 3. Compute USD with openclaw's own formula:
38
+ * cost = (cost_per_1M * tokens) / 1_000_000
39
+ * 4. Write to the global OTel counter `openclaw.cost.usd` with
40
+ * attributes (`openclaw.provider`, `openclaw.model`, `openclaw.channel`)
41
+ * that match what diagnostics-otel uses for `openclaw.tokens` —
42
+ * same labels → same Prometheus time series.
41
43
  *
42
- * Why polling and not a hook
43
- * --------------------------
44
- * `llm_output` and `agent_end` carry usage, but openclaw blocks them for
45
- * non-bundled plugins unless `plugins.entries.<id>.hooks
46
- * .allowConversationAccess: true` is set in openclaw.json — i.e. in the
47
- * manager. `model_call_ended` is bundled-accessible but only carries
48
- * sanitized metadata (no usage). `wrapStreamFn` is a provider-runtime
49
- * hook on `registerProvider` but `register(api)` is not invoked for
50
- * external plugins in 2026.5.x and behavior is unverified in 2026.6.1.
51
- * Tailing the transcript file is the one path that does not depend on
52
- * any of those (the transcripts are written by the completion path
53
- * regardless of hooks).
44
+ * Anchors at file size on first sighting, so only entries written after
45
+ * gateway start count (no replay of historical transcripts on every
46
+ * restart). Survives plugin hot-reload via globalThis state.
54
47
  *
55
- * Double-counting safety
56
- * ----------------------
57
- * On startup the poller takes the current size of every transcript
58
- * file as the initial offset existing entries are assumed already
59
- * accounted for by whatever was running before. Only bytes appended
60
- * after startup emit metrics. Gateway restart resets all offsets, which
61
- * is the correct behavior for a process-scoped counter (Prometheus
62
- * `rate()` handles counter resets).
63
- *
64
- * If openclaw eventually fixes the diagnostic path so that
65
- * `evt.costUsd` is populated for runware, both writers will increment
66
- * the same series and the metric will double for runware. At that point
67
- * delete this module. (We do not attempt to detect that case at runtime
68
- * because diagnostics-otel does not expose its emit-or-skip decision to
69
- * other plugins.)
48
+ * Polling instead of a runtime hook because openclaw blocks `llm_output`
49
+ * and `agent_end` for non-bundled plugins unless
50
+ * `plugins.entries.<id>.hooks.allowConversationAccess: true` is set in
51
+ * openclaw.json i.e. the manager. The trajectory file is written
52
+ * unconditionally and is plugin-readable, so no config flag needed.
70
53
  */
71
54
  import { createReadStream } from "node:fs";
72
55
  import { readdir, stat } from "node:fs/promises";
73
56
  import { homedir } from "node:os";
74
57
  import { join } from "node:path";
58
+ import { fetchModels } from "./catalog.js";
59
+ import { resolveApiKey, resolveBaseUrl } from "./models.js";
75
60
  const GLOBAL_KEY = "__runware_openclaw_cost_metric__";
76
61
  const POLL_INTERVAL_MS = 2000;
62
+ const PRICING_REFRESH_MS = 30_000;
77
63
  const RUNWARE_PROVIDER = "runware";
78
64
  const METER_NAME = "runware-openclaw-provider";
79
65
  const METRIC_NAME = "openclaw.cost.usd";
66
+ const TARGET_ENTRY_TYPE = "model.completed";
80
67
  function loadState() {
81
68
  const g = globalThis;
82
69
  const existing = g[GLOBAL_KEY];
@@ -89,16 +76,17 @@ function loadState() {
89
76
  emittedAny: false,
90
77
  fileStates: new Map(),
91
78
  intervalHandle: null,
79
+ pricingByModelId: new Map(),
80
+ lastPricingFetchAt: 0,
81
+ pricingFetchInFlight: null,
82
+ pricingLoadedLogged: false,
83
+ warnedMissingPricing: new Set(),
84
+ warnedNoApiKey: false,
85
+ warnedPricingFetchFailed: false,
92
86
  };
93
87
  g[GLOBAL_KEY] = fresh;
94
88
  return fresh;
95
89
  }
96
- /**
97
- * Idempotent. Safe to call from multiple plugin entry files; only the
98
- * first call starts the interval, subsequent calls return immediately.
99
- * Survives openclaw plugin hot-reload because state lives on
100
- * `globalThis`.
101
- */
102
90
  export function startCostMetricPoller(opts) {
103
91
  const state = loadState();
104
92
  if (state.initialized)
@@ -128,10 +116,6 @@ export function startCostMetricPoller(opts) {
128
116
  console.log(`[runware-cost-metric] started, intervalMs=${intervalMs} openclawHome=${openclawHome}`);
129
117
  }
130
118
  async function initCounter() {
131
- // Dynamic import so a missing @opentelemetry/api doesn't break the
132
- // plugin entry. Typed structurally — we don't import OTel types
133
- // statically because verbatimModuleSyntax disallows type-only imports
134
- // here without `import type`, and the dynamic shape is all we need.
135
119
  const otel = (await import("@opentelemetry/api"));
136
120
  const meter = otel.metrics.getMeter(METER_NAME);
137
121
  return meter.createCounter(METRIC_NAME, {
@@ -139,6 +123,59 @@ async function initCounter() {
139
123
  unit: "USD",
140
124
  });
141
125
  }
126
+ async function refreshPricingIfStale(state) {
127
+ if (state.pricingFetchInFlight) {
128
+ await state.pricingFetchInFlight;
129
+ return;
130
+ }
131
+ const now = Date.now();
132
+ if (state.pricingByModelId.size > 0 &&
133
+ now - state.lastPricingFetchAt < PRICING_REFRESH_MS) {
134
+ return;
135
+ }
136
+ const apiKey = resolveApiKey({ env: process.env });
137
+ if (!apiKey) {
138
+ if (!state.warnedNoApiKey) {
139
+ state.warnedNoApiKey = true;
140
+ console.warn("[runware-cost-metric] RUNWARE_API_KEY not in env, pricing unavailable");
141
+ }
142
+ return;
143
+ }
144
+ state.warnedNoApiKey = false;
145
+ const baseUrl = resolveBaseUrl(process.env);
146
+ state.pricingFetchInFlight = (async () => {
147
+ try {
148
+ const models = await fetchModels(baseUrl, apiKey);
149
+ const next = new Map();
150
+ for (const m of models) {
151
+ next.set(m.id, {
152
+ input: m.inputCost ?? 0,
153
+ output: m.outputCost ?? 0,
154
+ cacheRead: m.cacheReadCost ?? 0,
155
+ cacheWrite: m.cacheWriteCost ?? 0,
156
+ });
157
+ }
158
+ state.pricingByModelId = next;
159
+ state.lastPricingFetchAt = Date.now();
160
+ state.warnedPricingFetchFailed = false;
161
+ if (!state.pricingLoadedLogged) {
162
+ state.pricingLoadedLogged = true;
163
+ const sample = Array.from(next.keys()).slice(0, 3).join(", ");
164
+ console.log(`[runware-cost-metric] loaded pricing for ${next.size} models (e.g. ${sample})`);
165
+ }
166
+ }
167
+ catch (err) {
168
+ if (state.pricingByModelId.size === 0 && !state.warnedPricingFetchFailed) {
169
+ state.warnedPricingFetchFailed = true;
170
+ console.warn("[runware-cost-metric] pricing fetch failed (no cached pricing):", err);
171
+ }
172
+ }
173
+ finally {
174
+ state.pricingFetchInFlight = null;
175
+ }
176
+ })();
177
+ await state.pricingFetchInFlight;
178
+ }
142
179
  async function pollOnce(openclawHome, state) {
143
180
  if (state.counterInit) {
144
181
  await state.counterInit;
@@ -146,6 +183,9 @@ async function pollOnce(openclawHome, state) {
146
183
  }
147
184
  if (!state.counter)
148
185
  return;
186
+ await refreshPricingIfStale(state);
187
+ if (state.pricingByModelId.size === 0)
188
+ return;
149
189
  const agentsDir = join(openclawHome, "agents");
150
190
  let agents;
151
191
  try {
@@ -167,7 +207,7 @@ async function pollSessionsDir(sessionsDir, state) {
167
207
  return;
168
208
  }
169
209
  for (const entry of entries) {
170
- if (!entry.endsWith(".jsonl"))
210
+ if (!entry.endsWith(".trajectory.jsonl"))
171
211
  continue;
172
212
  await pollSessionFile(join(sessionsDir, entry), state);
173
213
  }
@@ -183,21 +223,31 @@ async function pollSessionFile(path, state) {
183
223
  return;
184
224
  }
185
225
  const prev = state.fileStates.get(path);
186
- // First sighting: anchor to current size. Existing content predates
187
- // this poller and is assumed already counted by whatever metric path
188
- // was active before. We only emit for bytes appended after startup.
226
+ // First sighting: read from offset 0. New sessions created after gateway
227
+ // start would otherwise lose their early entries (anchor-on-first-sight
228
+ // skips everything written between session creation and our next tick).
229
+ // Trade-off: gateway restart re-reads existing transcripts once, causing
230
+ // a one-shot counter bump. Prometheus `rate()` and `increase()` handle
231
+ // counter resets idiomatically, and the cost-metric counter is reset on
232
+ // every gateway restart anyway (it lives in process memory).
189
233
  if (!prev) {
234
+ console.log(`[runware-cost-metric] tracking new file: ${path} (size=${info.size})`);
235
+ const chunk = info.size > 0 ? await readBytes(path, 0, info.size) : "";
236
+ const consumed = parseAndEmit(chunk, state);
190
237
  state.fileStates.set(path, {
191
- offset: info.size,
238
+ offset: consumed,
192
239
  inode: info.ino,
193
240
  size: info.size,
194
241
  });
195
242
  return;
196
243
  }
197
- // Rotation or truncation: re-anchor and skip emission for this tick.
244
+ // Rotation / truncation: re-anchor at 0 and read whole file again.
198
245
  if (prev.inode !== info.ino || info.size < prev.size) {
246
+ console.log(`[runware-cost-metric] file rotated/truncated, re-reading: ${path}`);
247
+ const chunk = info.size > 0 ? await readBytes(path, 0, info.size) : "";
248
+ const consumed = parseAndEmit(chunk, state);
199
249
  state.fileStates.set(path, {
200
- offset: info.size,
250
+ offset: consumed,
201
251
  inode: info.ino,
202
252
  size: info.size,
203
253
  });
@@ -237,8 +287,6 @@ function readBytes(path, start, end) {
237
287
  function parseAndEmit(chunk, state) {
238
288
  if (chunk.length === 0)
239
289
  return 0;
240
- // Trailing bytes after the last `\n` are a partial line still being
241
- // flushed by openclaw. Leave them for the next tick.
242
290
  const lastNewline = chunk.lastIndexOf("\n");
243
291
  if (lastNewline === -1)
244
292
  return 0;
@@ -260,75 +308,84 @@ function parseAndEmit(chunk, state) {
260
308
  function emitFromEntry(entry, state) {
261
309
  if (!state.counter || !isRecord(entry))
262
310
  return;
263
- if (readProvider(entry) !== RUNWARE_PROVIDER)
311
+ if (entry.type !== TARGET_ENTRY_TYPE)
312
+ return;
313
+ if (entry.provider !== RUNWARE_PROVIDER) {
314
+ // Different provider (anthropic-direct, openai, etc) — not our metric.
315
+ return;
316
+ }
317
+ if (typeof entry.modelId !== "string" || entry.modelId.length === 0) {
318
+ console.warn(`[runware-cost-metric] model.completed entry missing modelId: ${JSON.stringify(entry).slice(0, 300)}`);
319
+ return;
320
+ }
321
+ const modelId = entry.modelId;
322
+ const data = entry.data;
323
+ if (!isRecord(data))
324
+ return;
325
+ const usage = data.usage;
326
+ if (!isRecord(usage))
327
+ return;
328
+ const cost = state.pricingByModelId.get(modelId);
329
+ if (!cost) {
330
+ if (!state.warnedMissingPricing.has(modelId)) {
331
+ state.warnedMissingPricing.add(modelId);
332
+ console.warn(`[runware-cost-metric] no pricing for model "${modelId}" — skipping cost emit (will retry on next /v1/models refresh)`);
333
+ }
264
334
  return;
265
- const cost = readCostUsd(entry);
266
- if (cost <= 0)
335
+ }
336
+ const input = nonNegNumber(usage.input);
337
+ const output = nonNegNumber(usage.output);
338
+ const cacheRead = nonNegNumber(usage.cacheRead);
339
+ const cacheWrite = readCacheWrite(data);
340
+ const costUsd = (cost.input * input +
341
+ cost.output * output +
342
+ cost.cacheRead * cacheRead +
343
+ cost.cacheWrite * cacheWrite) /
344
+ 1_000_000;
345
+ if (!Number.isFinite(costUsd) || costUsd <= 0)
267
346
  return;
268
347
  const attrs = {
269
348
  "openclaw.provider": RUNWARE_PROVIDER,
270
- "openclaw.model": readModel(entry) ?? "unknown",
349
+ "openclaw.model": modelId,
271
350
  };
272
- const channel = readChannel(entry);
351
+ const channel = parseChannelFromSessionKey(entry.sessionKey);
273
352
  if (channel)
274
353
  attrs["openclaw.channel"] = channel;
275
354
  try {
276
- state.counter.add(cost, attrs);
355
+ state.counter.add(costUsd, attrs);
277
356
  if (!state.emittedAny) {
278
357
  state.emittedAny = true;
279
- console.log(`[runware-cost-metric] first emit: ${cost.toFixed(6)} USD ${JSON.stringify(attrs)}`);
358
+ console.log(`[runware-cost-metric] first emit: ${costUsd.toFixed(6)} USD attrs=${JSON.stringify(attrs)} tokens=${JSON.stringify({ input, output, cacheRead, cacheWrite })}`);
280
359
  }
281
360
  }
282
361
  catch (err) {
283
362
  console.error("[runware-cost-metric] counter.add failed:", err);
284
363
  }
285
364
  }
286
- function isRecord(v) {
287
- return v !== null && typeof v === "object";
365
+ function readCacheWrite(data) {
366
+ const pc = data.promptCache;
367
+ if (!isRecord(pc))
368
+ return 0;
369
+ const lcu = pc.lastCallUsage;
370
+ if (!isRecord(lcu))
371
+ return 0;
372
+ return nonNegNumber(lcu.cacheWrite);
288
373
  }
289
- function readProvider(entry) {
290
- if (typeof entry.provider === "string")
291
- return entry.provider;
292
- const model = entry.model;
293
- if (typeof model === "string") {
294
- const slash = model.indexOf("/");
295
- if (slash > 0)
296
- return model.slice(0, slash);
374
+ function parseChannelFromSessionKey(sessionKey) {
375
+ if (typeof sessionKey !== "string")
376
+ return undefined;
377
+ // "agent:<agentId>:<channel>[:<sessionFragment>]"
378
+ const parts = sessionKey.split(":");
379
+ if (parts.length >= 3 && parts[0] === "agent") {
380
+ const ch = parts[2];
381
+ return typeof ch === "string" && ch.length > 0 ? ch : undefined;
297
382
  }
298
383
  return undefined;
299
384
  }
300
- function readCostUsd(entry) {
301
- const usage = entry.usage;
302
- if (isRecord(usage)) {
303
- const cost = usage.cost;
304
- if (isRecord(cost) &&
305
- typeof cost.total === "number" &&
306
- Number.isFinite(cost.total)) {
307
- return cost.total;
308
- }
309
- if (typeof usage.costUsd === "number" &&
310
- Number.isFinite(usage.costUsd)) {
311
- return usage.costUsd;
312
- }
313
- }
314
- if (typeof entry.costUsd === "number" && Number.isFinite(entry.costUsd)) {
315
- return entry.costUsd;
316
- }
317
- return 0;
318
- }
319
- function readModel(entry) {
320
- if (typeof entry.model === "string")
321
- return entry.model;
322
- if (typeof entry.modelId === "string")
323
- return entry.modelId;
324
- return undefined;
385
+ function isRecord(v) {
386
+ return v !== null && typeof v === "object";
325
387
  }
326
- function readChannel(entry) {
327
- if (typeof entry.channel === "string")
328
- return entry.channel;
329
- const meta = entry.metadata;
330
- if (isRecord(meta) && typeof meta.channel === "string")
331
- return meta.channel;
332
- return undefined;
388
+ function nonNegNumber(v) {
389
+ return typeof v === "number" && Number.isFinite(v) && v >= 0 ? v : 0;
333
390
  }
334
391
  //# sourceMappingURL=cost-metric.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"cost-metric.js","sourceRoot":"","sources":["../src/cost-metric.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"cost-metric.js","sourceRoot":"","sources":["../src/cost-metric.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@teith/openclaw-runware-provider",
3
- "version": "0.3.4",
3
+ "version": "0.3.6",
4
4
  "description": "OpenClaw provider plugin for Runware — unified OpenAI-compatible access to Claude, GPT, Gemini, Qwen, GLM, MiniMax, Kimi, and Gemma.",
5
5
  "license": "MIT",
6
6
  "type": "module",