<div align="center">

# 📊 dsh-usage-stats

**API spend monitoring for DeepSeek Harness: per-request detail, previous-period comparisons, and chart-backed history in one panel.**

*See every token you pay for.*

[![License](https://img.shields.io/badge/license-Apache%202.0-blue.svg)](LICENSE)
[![DSH plugin](https://img.shields.io/badge/dsh-plugin-✅-green)](https://github.com/topics/dsh-plugin)
[![Node](https://img.shields.io/badge/node-%5E22.19%20%7C%7C%20%3E%3D24-brightgreen.svg)](#)

[English](README.md) · [简体中文](README.zh.md) · [Español](README.es.md) · [Português](README.pt.md) · [हिन्दी](README.hi.md)

</div>

---

## Compatibility

| Aspect | Status |
|---|---|
| Harness | DeepSeek Harness `0.1.0-rc.8` |
| Node | `^22.19.0 \|\| >=24.0.0` |
| Surfaces | Host + web client (Settings → Usage tab); the `/usage` command |

## What you get

`dsh-usage-stats` turns the session event stream into a complete spend-monitoring panel:

- **Summary cards** — today / this week / this month / all-time, each with a signed percentage delta against its previous period (yesterday / last week / last month).
- **Per-request conversation detail** — every priced request's start time, turn/step, model, input/output/cache-read/cache-write tokens, cost at the request-time price, and peak badge; durable through restarts via the session projection seam (bounded ring, `requestLog` config).
- **Day / week / month views** — current-vs-previous comparison panels (cost, tokens, calls, peak calls + deltas) with the period's per-day lines.
- **History panel** — a dependency-free daily-cost bar chart (peak-tinted bars, hover details) plus a per-day table (cost / tokens / calls / peak, per-model drill-down), 90 days by default (~a year in the durable layer).
- **Custom range** — any from/to dates: range total, daily chart, per-week lines, per-model breakdown.
- **Pricing** — built-in USD table merged with `config.prices`; **peak-hour pricing** anchored at request start (`peak.hours` windows × `multiplier`, or explicit `peak.prices`); calendar bucketing follows `peak.timezone`.
- **Carbon & latency** — token→carbon bridge (tokens × kWh/token × PUE × regional grid intensity) and per-model latency percentiles.

## Quick start

```sh
# 1. Add the bundle to your profile (tarball channel)
pnpm pack
dsh plugin --profile web add ./dsh-usage-stats-<version>.tgz

# 2. Restart and verify the row
dsh web --restart
dsh --profile web --dump-config | grep -A2 'id: usage'
```

Then type `/usage` in a conversation and open the Settings → Usage tab.

## Install & remove

- **npm channel** (published versions): `dsh plugin --profile web add dsh-usage-stats-alhabor` — npm registry, released from tags.
- **git channel** (latest `main`): `dsh plugin --profile web add "github:PerryLink/dsh-budget#main"` — the `prepare` script builds with production dependencies only.
- **tarball channel**: run `pnpm pack` in this repo, then `dsh plugin --profile web add ./dsh-usage-stats-<version>.tgz`.
- **remove**: `dsh plugin --profile web remove dsh-usage-stats`.

## Configuration

Every key is a Schemastery-validated cordis field (defaults inline in `cordis.patch.yml`).

| Key | Default | Meaning |
|---|---|---|
| `prices` | `{}` | Per-model per-1M-token prices, merged over the built-in USD table |
| `defaultPrice` | `{input: 1.0, output: 3.0}` | Fallback for models absent from both tables |
| `peak.enabled` / `timezone` / `hours` / `weekendOffpeak` / `multiplier` / `prices` | `true` / `Asia/Shanghai` / `[[9,12],[14,18]]` / `true` / `{input:2, output:2, cacheRead:2, cacheWrite:2}` / `{}` | Peak-hour pricing: requests starting inside a window (Mon–Fri only — weekends are all-day off-peak since DeepSeek's 2026-08-23 rule) price through `peak.prices` (or base × `multiplier`); day/month bucketing follows `peak.timezone` |
| `modelAliases` | `{}` | Dated/legacy model ids → canonical pricing id |
| `currency` | `{code: CNY, rate: 1.0, decimals: 2}` | Display currency (amount = computed × rate; for direct CNY pricing set `rate: 1.0` and fill `prices` with CNY rates) |
| `outputLanguage` | `zh` | `/usage` output language: `en` / `zh` |
| `historyDays` | `90` | Days of per-day history kept in the panel snapshot (1..365; the durable layer keeps ~a year per session) |
| `requestLog.enabled` / `size` | `true` / `200` | Per-request detail switch and per-session ring size (10..2000) |
| `carbon.enabled` / `region` / `pue` / `energyKwhPerToken` | `true` / `global` / `1.58` / `0.000007` | Carbon bridge (regions: global, us, eu, china, india, uk, france, iceland) |
| `latency.enabled` / `windowSize` | `true` / `200` | Per-model latency percentiles and their window |
| `refreshIntervalMs` | `5000` | Settings tab polling interval (reserved) |

## Surfaces

| Surface | Kind | Notes |
|---|---|---|
| `/usage` | command | Overview (session/today/yesterday/this week/last week/this month/last month/all-time) |
| `/usage models \| days \| sessions \| week <monday> \| range <from> <to>` | command | Model breakdown / daily history / session list / one week / custom range |
| Settings → Plugins → Usage | settings tab | Summary cards, conversation detail, day/week/month comparisons, custom range, history chart |
| `usage/status`, `usage/range` | Typert Remote | Client channel (the tab consumes these two methods) |

## Permissions & data

- **Permissions**: `session:append` (command audit only), `native-code:none`; no outbound network.
- **Data**: everything shown is a read-only aggregate over official session events; the plugin never appends custom event types to the session log (the rc.8 read path refuses unknown types) — durable state lives entirely in session projections.
- **Fail loud**: invalid prices, timezones, ratios, regions, and bounds fail at mount time.

## Known limits

- Per-request detail is bounded per session (latest 200 by default); older requests live on only in the aggregates.
- Previous-period deltas show "new"/"flat" when the durable history is shorter than one full period.
- Built-in prices drift; override entries with `config.prices`.

## Development

```sh
pnpm install        # node ^22.19 || >=24
pnpm run typecheck  # tsc: src + tests against the local harness checkout
pnpm run typecheck:ci  # tsc against the published 0.1.0-rc.8 types (no paths)
pnpm test           # vitest: 80 tests
pnpm run build      # tsc declarations + tsdown bundles (lib/)
pnpm run verify:self-contained  # dependency specs resolve from the registry
pnpm run verify:artifacts       # built ESM face + typert manifest + client bundle
pnpm pack           # the published tarball
```

## Topics

`dsh`, `dsh-plugin`, `deepseek-harness`, `deepseek`, `cordis`, `budget`, `cost-tracking`, `carbon-footprint`, `latency-benchmark`, `token-usage`

## Contributors

- [@PerryLink](https://github.com/PerryLink) — creator and maintainer: aggregation, budget governance, carbon and latency ports, the Settings tab, and the five-language docs.

## PerryLink DSH Plugin Family

This project is one of the [29 DeepSeek Harness plugins](https://github.com/PerryLink) maintained by [PerryLink](https://github.com/PerryLink). If this one helps you, the others likely will too:

| Plugin | One-liner |
|---|---|
| [dsh-auto-review](https://github.com/PerryLink/dsh-auto-review) | Second-model auto-review on the approval chain, fail-closed by default |
| [dsh-background-agents](https://github.com/PerryLink/dsh-background-agents) | Durable background child agents with a Web UI sidebar, messaging and interrupt |
| **[dsh-budget](https://github.com/PerryLink/dsh-budget)** | Cost governance for DeepSeek Harness: budgets, carbon, and latency in one panel. |
| [dsh-checkpoint-rewind](https://github.com/PerryLink/dsh-checkpoint-rewind) | Claude Code /rewind-equivalent: snapshots, session forks, one-shot restore |
| [dsh-claude-move](https://github.com/PerryLink/dsh-claude-move) | Migrate Claude Code sessions, memory, skills and CLAUDE.md into DSH |
| [dsh-click](https://github.com/PerryLink/dsh-click) | Cross-platform native desktop control for DeepSeek Harness — Windows first. |
| [dsh-composer-history](https://github.com/PerryLink/dsh-composer-history) | Terminal-style input history for the web composer: arrows, Ctrl+R search |
| [dsh-defend](https://github.com/PerryLink/dsh-defend) | Prompt-injection, jailbreak, and secret-leak defense for DeepSeek Harness. |
| [dsh-doublecheck](https://github.com/PerryLink/dsh-doublecheck) | Engineering-discipline guard: requirements grill, test gates, adversary review |
| [dsh-draw](https://github.com/PerryLink/dsh-draw) | Unified static-image generation routing for DeepSeek Harness. |
| [dsh-fast](https://github.com/PerryLink/dsh-fast) | Read-only performance diagnostics for DeepSeek Harness. |
| [dsh-github](https://github.com/PerryLink/dsh-github) | GitHub PR/issues integration for DSH, every write gated by approval |
| [dsh-library](https://github.com/PerryLink/dsh-library) | Local document knowledge base for DeepSeek Harness. |
| [dsh-local-ai](https://github.com/PerryLink/dsh-local-ai) | Local-model (Ollama) integration for DeepSeek Harness. |
| [dsh-lsp-actions](https://github.com/PerryLink/dsh-lsp-actions) | LSP diagnostics, formatting, completion, code actions and rename over language servers |
| [dsh-mask](https://github.com/PerryLink/dsh-mask) | PII masking middleware for DeepSeek Harness — anonymize personal data before it reaches the model, restore it at the display layer. |
| [dsh-mcp-panel](https://github.com/PerryLink/dsh-mcp-panel) | Read-only MCP runtime panel: /mcp command + Settings tab with status, tools and errors |
| [dsh-memento](https://github.com/PerryLink/dsh-memento) | Approval-gated cross-session memory: ctx.memory seam + SQLite + memory tool |
| [dsh-observe](https://github.com/PerryLink/dsh-observe) | OpenTelemetry and Langfuse observability exporter for DeepSeek Harness. |
| [dsh-output-styles](https://github.com/PerryLink/dsh-output-styles) | Claude Code outputStyles-equivalent runtime style switching |
| [dsh-permission-rules](https://github.com/PerryLink/dsh-permission-rules) | Claude Code-style declarative allow/deny/ask permission rules with audit |
| [dsh-plugin-guide](https://github.com/PerryLink/dsh-plugin-guide) | Plugin-development knowledge base as an on-demand agent skill |
| [dsh-score](https://github.com/PerryLink/dsh-score) | Multi-dimensional quality scoring for DeepSeek Harness plugins. |
| [dsh-session-pin](https://github.com/PerryLink/dsh-session-pin) | Pin sessions in the Web sidebar with durable ordering |
| [dsh-session-sync](https://github.com/PerryLink/dsh-session-sync) | Cross-device session sync for DeepSeek Harness — a dedicated git mirror of your session store. |
| [dsh-skill-pack-security](https://github.com/PerryLink/dsh-skill-pack-security) | Security-audit skill pack: secret scan, dependency and supply-chain review |
| [dsh-talk](https://github.com/PerryLink/dsh-talk) | Voice-first session loop for DeepSeek Harness: talk to it, hear it answer. |
| [dsh-test-drive](https://github.com/PerryLink/dsh-test-drive) | Isolated install-and-smoke test drives for DeepSeek Harness plugins. |
| [dsh-translate](https://github.com/PerryLink/dsh-translate) | Vendor parameter translation and deterministic JSON repair for DeepSeek Harness. |

## License

[Apache License 2.0](LICENSE) © 2026 dsh-budget contributors
