DSH HUB
HomePlugin StorePlugin PacksCommunityRankingsResourcesPublish Guide
Plugin source
Back to catalog

Enc-hanted /

dsh-pulse

Verified

Cross-session usage & cost observatory for the DeepSeek Harness web profile — trend/heatmap dashboards, per-model peak-hour pricing (CNY/USD), official DeepSeek balance with spend reconciliation.

★ 0 Stars0 Forks0 IssuesN/A Community rating0 Confirmed installs
View on GitHub
READMESource: main@5840e7fc

dsh-pulse

English | 简体中文

Per-session usage and cost observatory for dsh. Aggregates token usage across all sessions, estimates cost from built-in DeepSeek rates, and shows the official platform balance. Everything runs on the UI plane: no model-visible tools, zero tokens spent.

Features

  • Usage trend: hourly line chart for today, daily bars for 7/30 days, GitHub-style heatmap for 90 days/1 year, custom date ranges up to 30 days
  • Project / model filters: two searchable dropdowns restrict the whole dashboard to one workspace and/or one model
  • Cache hit rate: donut gauge with hit/read and uncached input/output detail; cache-write counts as a miss
  • Model distribution / project ranking: share bars and a ranked table
  • Cost estimate: per-model rates with peak/off-peak tiers; models without a rule are listed as unpriced
  • Cost trend: daily sparkline, with the official balance reconciliation line overlaid after a day of snapshots
  • Official balance: DeepSeek platform balance, queried with the key the host already stores, manual refresh included

Quick start

dsh plugin --profile web add -w dsh-pulse

Restart dsh web, then open Settings → Usage Pulse. In any conversation, /pulse prints a text summary (commands never reach the model); the sidebar foot button opens the floating panel. All surfaces share one data source, GET /pulse/stats.

With a stored DEEPSEEK_API_KEY, the dashboard also shows the official balance and, after a day of snapshots, the reconciliation line.

Install / Uninstall

dsh plugin --profile <name> runs pnpm inside the profile directory and reconciles dsh.profile.bundles automatically. Profiles are pnpm workspace roots, hence the -w:

# from the npm registry
dsh plugin --profile web add -w dsh-pulse

# from a packed tarball
dsh plugin --profile web add -w /abs/path/to/dsh-pulse-0.3.0.tgz

# from a source checkout (development)
dsh plugin --profile web add -w link:/abs/path/to/dsh-pulse

# from git
dsh plugin --profile web add -w git+https://github.com/Enc-hanted/dsh-pulse

…or add "dsh-pulse": "link:/abs/path/to/dsh-pulse" to ~/.dsh/profiles/web/package.json and run pnpm install there. Restart dsh web afterwards (adding the plugin hot-loads; editing its code requires a restart).

dsh plugin --profile web remove -w dsh-pulse

The next boot drops it from dsh.profile.bundles. Leftovers, safe to delete: the pulse section in ~/.dsh/settings.yaml and ~/.dsh/storages/pulse_balance.json. The plugin never stores secrets.

Cost model

Rates are CNY per million tokens; defaults are built in from the official price page (https://api-docs.deepseek.com/zh-cn/quick_start/pricing/, checked 2026-08-17). DeepSeek bills by peak/off-peak windows: Beijing time 09:00–12:00 and 14:00–18:00 are peak; all other hours are off-peak at half the peak rate.

model tier uncached input cache-hit input output
deepseek-v4-flash peak 3 0.1 9
deepseek-v4-flash off-peak 1.5 0.05 4.5
deepseek-v4-pro peak 9 0.3 27
deepseek-v4-pro off-peak 4.5 0.15 13.5

Rules: a rule without a peak block is flat; without cacheRead it falls back to its input rate; records without a tier split (pre-upgrade hosts) price wholly at off-peak rates. Peak hours default to the official windows and can be customized per rule (peakHours, hour granularity, Beijing time); peakHours: [] means flat even when peak rates are set. Models without a rule are shown separately as unpriced. The estimate counts uncachedInput = input + cacheWrite per tier.

Currency: rules price in CNY (default) or USD; USD-priced models convert through one configurable rate (usdToCny, default 6.8, editable in the pricing page), so the total is always a single CNY sum. The conversion is a manual rate by design: this is an estimator, not accounting. costEnabled: false hides the cost figures while keeping every other number.

Configuration

Settings → Usage Pulse → Pricing & cost edits the rates. Model rows come from the Models settings page with official DeepSeek rates prefilled; each row takes off-peak input / cache-hit / output rates, a CNY/USD selector, and a 24-hour peak strip (Beijing time, official windows by default, all deselected = flat). The exchange-rate field re-prices the loaded window with your unsaved edits. Official rates resets a row to the baseline; Refresh catalog re-reads the model catalog; Enable cost estimates turns cost figures off entirely. Fallback rows cover models with usage but no catalog entry, saved rules matching neither, and a manual add for the rest; without the llm service the editor runs on these rows alone.

Saves go to $DSH_HOME/settings.yaml (pulse: section), apply immediately, and survive restarts. Restore defaults clears the user section back to the composition config and the official defaults. Without a settings service the page is read-only.

Profile overrides in cordis.patch.yml:

- insert:
    - id: pulse
      name: 'dsh-pulse'
      config:
        defaultDays: 30   # window served when the client sends none
        topProjects: 8    # ranked-project row cap
        projectDepth: 1   # path segments in a project label (1..3)
        costEnabled: true # false hides the cost figures
        usdToCny: 6.8     # USD→CNY rate for the unified CNY total
        pricing:          # overrides the built-in defaults per model
          - model: deepseek-v4-pro
            input: 4.5
            cacheRead: 0.15
            output: 13.5
            peak:         # peak-hour rates (official windows by default)
              input: 9
              cacheRead: 0.3
              output: 27
            currency: CNY
          - model: third-party-x   # flat USD rule with custom peak hours
            input: 0.5
            output: 2
            currency: USD
            peakHours: [0, 1, 2, 3, 4, 5]   # Beijing-time hours billed at peak

projectDepth controls how the session working directory becomes a project label: 1 keeps the basename (default), 2 keeps parent/name, and so on up to 3. Deepening the label re-groups existing data; nothing is lost.

Official balance

GET /pulse/balance queries the DeepSeek open platform with the key the host already stores, resolved per request through the credentials seam. Zero new configuration, zero new secret storage: the key never leaves the host process (it appears only in one outbound Authorization header), failures map to generic cause codes, replies are cached 60 s server-side (?refresh=1 bypasses), responses carry cache-control: no-store, and outbound requests refuse redirects. Unconfigured or unreachable, the card hides itself or shows a retry.

Every successful query records one {t, total} snapshot, money only, in a rolling 30-day storage (pulse_balance, capped at 1000 entries, 5-minute dedupe). Per-day official spend is derived from the balance series; days where it can't be known (a top-up masks the spend, no prior snapshot, past the newest snapshot) are null. The cost sparkline draws this as a third line. Note that it is that key's total spend: if other tools share the key, it includes them.

Compatibility

Verified against @deepseek-ai/dsh 0.1.0-rc.6 (2026-08-17, Windows, Node 24.14.1); dsh requires Node ≥ 22.15. Required host services: commands, sessionQuery, webServer, sessionProjections, sessionProjectionCache, sessions. Optional, auto-detected: llm, settings, credentials, storageDomain. Hosts without tiersByDay (schema 2) still render, with costs priced at off-peak rates. During rolling upgrades the client accepts both payload schemas, so a page refresh against an old host keeps working; restart the host to regain window-exact ranges.

Development

node test/aggregate-test.mjs && node test/view-test.mjs && node test/mirror-test.mjs && node test/host-test.mjs
node scripts/sync-mirror.mjs   # regenerate the bundle mirror after editing src/view.js
dsh web --dump-config | grep pulse
curl 'http://127.0.0.1:3080/pulse/stats?from=2026-08-01&to=2026-08-14' | head -c 400

In short: the host half is a session projection unit (pulseUsage) that folds usage per day/model/hour as events commit, reads cold sessions from the persisted projection cache, and serves window-exact slices from GET /pulse/stats (concurrent requests share one in-flight fold, cached 15 s). The browser half is a zero-build client bundle (plain JS + react/dsh-client-ui-primitives) registered through public slots (conversation.chat.commandview, settings.section, sidebar.footer.action + shell.overlay); all mounted surfaces share one stats store. Charts are dependency-free div+CSS with one inline SVG per plot; the heatmap and hourly chart are pure client-side folds. src/view.js is mirrored into the bundle by scripts/sync-mirror.mjs, and the mirror test fails on drift.

MIT — see LICENSE.

—/ 5

No ratings yet

Verified DSH bundle

Commit 5840e7fc798e

Community comments

No comments yet. Be the first to write one.

DSH HUB

A community index for DSH plugins. Not an official GitHub or DeepSeek AI product.

CommunityResourcesAPIAbout