import { test } from "node:test"; import assert from "node:assert/strict"; import { estimateCost } from "../src/tools/models.js"; import { byId, fixtureCatalog } from "./helpers.js"; const items = fixtureCatalog(); test("image, transcription, speech — явный отказ, а не ноль", () => { for (const id of [ "bytedance-seed/seedream-4.5", "black-forest-labs/flux-3-image", "openai/whisper-1", "elevenlabs/eleven-flash-v2", ]) { const r = estimateCost(byId(items, id), { prompt_tokens: 1000, completion_tokens: 0 }); assert.equal(r.ok, false, id); if (!r.ok) assert.match(r.error, /нет цены за токен — тарификация по факту, оценка невозможна/); } }); test("text-модель: рубли без кэша, USD с ценой кэш-чтения", () => { const ds = byId(items, "deepseek/deepseek-v4-flash"); // ₽: 1_000_000 × 10.38881086 / 1e6 = 10.38881086 // 500_000 × 20.77762173 / 1e6 = 10.388810865 // итого 20.777621725 → 20.78 // $: (1_000_000 − 400_000) × 0.0000001289925 = 0.0773955 // 400_000 × 0.0000000257985 = 0.0103194 // 500_000 × 0.000000257985 = 0.1289925 // итого 0.2167074 const r = estimateCost(ds, { prompt_tokens: 1_000_000, completion_tokens: 500_000, cached_tokens: 400_000 }); assert.ok(r.ok); assert.equal(r.cost_rub, "20.777621725"); assert.equal(r.cost_rub_rounded, "20.78"); assert.equal(r.cost_usd, "0.2167074"); assert.match(r.basis, /без учёта скидки за кэш/); assert.match(r.basis, /цене кэш-чтения/); const noCache = estimateCost(ds, { prompt_tokens: 1_000_000, completion_tokens: 500_000 }); assert.ok(noCache.ok); // $: 0.1289925 + 0.1289925 = 0.257985 assert.equal(noCache.cost_usd, "0.257985"); assert.equal(noCache.cost_rub, "20.777621725"); }); test("модель без объявленной цены кэша считает кэш по полной цене и говорит об этом", () => { const qwen = byId(items, "qwen/qwen3-coder-30b-a3b-instruct"); // $: 1000 × 0.000000099225 = 0.000099225 (кэш по полной цене) const r = estimateCost(qwen, { prompt_tokens: 1000, cached_tokens: 500 }); assert.ok(r.ok); assert.equal(r.cost_usd, "0.000099225"); assert.match(r.basis, /не объявляет цену кэш-чтения/); }); test("decision: выход не тарифицируется", () => { const jev = byId(items, "typesafe/jev-1.13.0"); // 2_000_000 × 4.79483578 / 1e6 = 9.58967156; выход бесплатен. const r = estimateCost(jev, { prompt_tokens: 2_000_000, completion_tokens: 10 }); assert.ok(r.ok); assert.equal(r.cost_rub, "9.58967156"); assert.match(r.basis, /выход decision-модели не тарифицируется/); }); test("кэш больше промпта — ошибка", () => { const r = estimateCost(byId(items, "deepseek/deepseek-v4-flash"), { prompt_tokens: 10, cached_tokens: 11 }); assert.equal(r.ok, false); });