hermes-plugin-prism
A Hermes Agent terminal backend that runs the agent's shell commands on a dedicated NVIDIA GPU, rented by the second from the agent's own wallet on Prism Network and paid for on-chain in USDG.
The agent gets a real GPU box for the session, with CUDA and root. You get two spending caps it cannot raise, and a ledger of what it spent.
hermes config set terminal.backend prism
Install
The plugin is a directory drop, like every other Hermes plugin.
pip install prismnetwork
git clone https://github.com/prismnetwork-tech/hermes-plugin-prism ~/.hermes/plugins/prism
hermes plugins enable prism
hermes config set terminal.backend prism
hermes config set timeouts.tools.sequential_call 900
The last line matters. Hermes abandons a tool call after 420 seconds by
default, and the first command of a session rents the GPU and waits for it to
come up, which the escrow allows ten minutes for. Under the default a lease
could be funded with nothing left waiting for it, so the backend refuses to
rent until the ceiling is 900 or higher (0 removes it).
Then give it a wallet. Create a key, fund it with USDG for leases and a little
ETH for gas on Robinhood Chain (id 4663), and save the key in ~/.hermes/.env:
PRISM_AGENT_KEY=0x...
hermes doctor reports the wallet, the caps, what is left of today's budget,
the trust class, and whether a GPU is currently rented.
Requires hermes-agent v0.20.6 (tag v2026.8.27) or later, the release that made
terminal backends pluggable.
Configuration
All keys live under terminal.prism in ~/.hermes/config.yaml.
| Key | Default | What it does |
|---|---|---|
max_usdg |
1 |
Most a single lease may cost. |
daily_budget_usdg |
5 |
Most this wallet may spend in a rolling 24 hours. 0 removes the ceiling. |
min_vram_mib |
16000 |
Smallest GPU worth renting for this agent. |
trust_class |
open |
Every machine on the network is open today. Leave it. |
lease_seconds |
3600 |
Length of the paid window, 300 or more. Priced up front, see below. |
image |
Prism's pinned default | Digest-pinned container image to run. |
sync_credentials |
false |
Whether Hermes credential files are copied to the rented machine. |
idle_release_seconds |
300 |
Seconds without a command before the plugin gives the GPU back. 0 holds the lease until the session ends. |
ledger_path |
~/.prism/spend.json |
File the day's spend is counted in. |
hermes config set terminal.prism.max_usdg 1
hermes config set terminal.prism.daily_budget_usdg 5
hermes config set terminal.prism.min_vram_mib 40000
max_usdg, daily_budget_usdg and ledger_path are the same three settings as
the SDK's PRISM_MAX_USDG, PRISM_DAILY_BUDGET_USDG and PRISM_LEDGER_PATH.
A value set here wins over an exported one. Pin ledger_path too: it names the
file today's spend is counted in, and an environment that moves it hands back a
budget that has already been spent.
What it costs
No GPU is rented until the model's first command: starting Hermes, running
hermes doctor or hermes status, and a conversation that never reaches a tool
call all cost nothing.
A GPU is rented on the first command of a session and kept for the rest of it. The lease survives between turns, so a conversation that runs twenty commands pays for one machine. It is released when the session ends, or earlier by the plugin's own idle monitor: five minutes without a command and the GPU goes back.
Releasing is what stops the meter. Live capacity quotes 0.7992 USDG per hour, which is 222 base units per second. The whole window is deposited into escrow when the lease opens; settlement charges the seconds between the machine opening and the release and returns the rest. A lease that is never released bills until its window ends, so the deposit is what your caps see and the release is what decides the charge:
| Window | Deposit | Charged |
|---|---|---|
| 15 minutes | 0.1998 USDG | Seconds until release, at most the window |
| 1 hour (the default) | 0.7992 USDG | Seconds until release, at most the window |
The gap between the two is usually large. A settled 30-minute lease that ran a
23-second CUDA job deposited 0.3996 USDG, charged 0.005106, and returned the
rest. Receipt 25dd3d12-bf11-843b-8770-3b5ba725cc97 on
prismnetwork.tech/proof is that run. Budget
against the deposit and report the charge.
Rates move with supply. hermes doctor and the site carry the current number.
Two caps bound all of it, and the model can reach neither. Both are enforced before any money moves:
- Per lease. A quote above
max_usdgis refused, unfunded. - Per day. Every lease is written to
~/.prism/spend.jsonbefore it is funded. When the next lease would take the rolling 24-hour total pastdaily_budget_usdg, it is refused and nothing is charged. One wallet has one daily ceiling no matter which client is holding it, so the Prism MCP server and this backend draw down the same budget.
A lease that fails before its funding transaction is broadcast gives the reservation back and costs nothing. Once the transaction is on the wire the spend is counted against the day and the ledger entry records the hash. That includes a lease whose receipt never arrives inside the wait: the transaction usually lands, and forgiving it would let one wallet fund escrow after escrow while the day's total read zero. The error names the transaction so you can check it on Robinhood Chain. A lease the network refunds is credited back to the day's budget once the refund is seen on chain: a machine that never hands over access has its deposit returned by the escrow, and the ledger entry drops to zero when the control plane reports the refund, keeping the transaction on file.
Hermes runs a failed command again up to three times before it gives the error to the model, so a lease that fails with money already on the wire blocks the next one for two minutes. Each retry is handed the transaction the first attempt sent, so one command produces one lease.
A release the network refuses is written into the transcript and the capsule
(release: failed), because the machine then bills until its window ends. A
Hermes process that is killed outright never reaches its release; the lease
settles at the end of its window and the receipt shows the full charge.
The caps are re-read from config before every lease, so lowering
daily_budget_usdg mid-session applies to the next one. If
~/.hermes/config.yaml cannot be read or does not parse, the backend refuses to
rent anything and names the file to repair. Falling back to Hermes' built-in
defaults would spend at ceilings you never chose.
The rented machine is public
Every GPU on the network is trust class open, which means the machine's
operator can read anything the workload touches. That is fine for builds, tests
and training runs on public data. It rules out keys, customer records, and any
credential you cannot rotate. There is no attested or confidential rented
workspace on Prism today, and this plugin will not pretend otherwise.
Hermes credential files stay off the rented machine unless you set
sync_credentials: true. Skills and cache files are always synced; they are what
the agent's own tools need to work.
Confidential inference is a different product: prompts sealed to a hardware
enclave, with no shell. docs/confidential-side-models.md
covers it.
The workspace is ephemeral
The rented machine's disk lives and dies with the lease. There is no resumable volume and nothing is copied back on teardown. Work that must survive the session belongs in a repository, an object store, or a file the agent writes home over the network before the lease ends.
A background thread in the plugin watches for idleness and releases the lease
after five minutes with no command, so an agent that goes quiet stops paying for
the machine. The next command rents a fresh one, against the same caps, and the
model is told its disk went with the old machine. Change the window with
terminal.prism.idle_release_seconds, or set it to 0 to hold the lease for
the whole session.
Sessions share one rented machine by default. Set
terminal.container_persistent: false to give each session a lease of its own.
File transfer
The SDK exposes commands over the lease's SSH channel and no separate file
transfer, so files are inlined: base64 on stdin into base64 -d on the far
side. That is fine for skills, cache entries and small artifacts. Anything over
4 MiB is skipped with a warning, so one large file cannot stall the session.
Move large payloads by fetching them on the box.
Capacity
When nothing on the network matches the request, the command fails with a plain
"no GPU is available right now, retry" and nothing is charged. It never blocks
waiting for supply. Lower min_vram_mib or trust_class if it persists.
Skills
Three skills ship in skills/. They carry judgment and procedure: what to buy,
in what order, and how to hand the result to someone who does not trust you.
| Skill | Answers |
|---|---|
prism-compute |
Should this run here, in Docker, or on a rented GPU? One-shot command or a lease? Which class, what will it cost, what do the caps mean, and what to do when there is no capacity. references/costs.md and references/gpu-classes.md carry the numbers. |
prism-cuda-repro |
The audited CUDA reproduction as a procedure: pin the image and command, prepare, review the quote, get it funded, wait, collect the signed evidence, verify, cite the receipt. |
prism-receipts |
Turning a settled lease into a citation, and checking one somebody else cited. Defines the proof capsule and ships scripts/verify_receipt.py. |
The verifier recomputes a published receipt hash with nothing but the standard
library, and its exit code is the answer: 0 verified and clean, 1 a check
failed, 3 verified but the run carries a failure_class and must not be cited
as a clean result.
python3 skills/prism-receipts/scripts/verify_receipt.py --self-test
python3 skills/prism-receipts/scripts/verify_receipt.py 25dd3d12-bf11-843b-8770-3b5ba725cc97
Point a profile at them:
hermes config set skills.external_dirs '["plugins/prism/skills"]'
The path resolves against that profile's Hermes home, the skills load read-only,
and skill creation still writes to ~/.hermes/skills/.
Lint them the way Hermes does, and check that Hermes really finds them:
~/.hermes/hermes-agent/venv/bin/python -m tools.skill_linter skills/
python -m pytest tests/test_skills_and_profile.py
The test copies the plugin into a throwaway Hermes home, loads it through the
real plugin manager, and asserts the skills are discovered, the SKILL.md files
render, mcp.json parses under the Agent Plugins v1 validator, and the Compute
Bot fragment does not loosen the plugin's ceilings. No wallet and no network.
The MCP surface
mcp.json at the repo root declares one server: the Prism repro endpoint at
https://prismnetwork.tech/api/mcp. It publishes exactly six tools, all
annotated read-only, none of which can spend or sign:
prism_gpu_capacity, prism_prepare_gpu_repro, prism_gpu_repro_status,
prism_gpu_repro_evidence, prism_verify_gpu_repro, prism_gpu_receipts.
No wallet and no key. The filtering is the server's, so there is nothing to
allowlist.
Hermes does not load that file for this plugin, so treat it as a declaration you
can copy. Tool filtering lives in config.yaml, which supports it:
hermes mcp add prism-repro --url https://prismnetwork.tech/api/mcp
then set mcp_servers.prism-repro.tools.include to the six names, matched
exactly or by glob. This matters for the wallet-side @prismnetwork/mcp npm
server, a different set of tools that includes leasing, inference and the vault.
Adding that one without an include list gives the model everything in it.
profiles/compute/config.yaml has both entries written out.
Compute Bot
A ready-made profile template lives in profiles/compute/: a Bot whose terminal
is a rented GPU, with ceilings below the plugin defaults, the three skills
enabled, and the read-only MCP surface wired up. Other Bots hand it GPU work by
assigning a Kanban card to compute, and it reports back what ran, what it cost
in USDG, and the receipt.
hermes profile create compute \
--description "Runs GPU work on a rented NVIDIA card and reports what it cost."
profiles/compute/README.md walks the rest: installing the plugin into the
profile, giving it a wallet of its own, merging config.yaml, and copying
SOUL.md. The soul is where the refusals are written down. It will not raise a
cap or split a job to slip under one. It will not put a credential on a machine
whose operator can read it. It stops for approval above a 0.25 USDG deposit,
which is why the profile's default lease is 15 minutes and 0.1998 USDG. And it
says plainly when something is not offered: persistent disks, attested rented
workspaces, pinned training images.
Tests
pip install -e ~/path/to/prismnetwork pytest
python -m pytest tests/test_prism_environment.py # unit, no wallet, no network
PRISM_LIVE_SPEND=1 python -m pytest tests/test_prism_terminal_live.py -m integration
The unit suite mocks everything at the PrismAgent boundary. The integration
suite rents a real GPU and spends real USDG, which is why it takes two opt-ins.
Both need a hermes-agent checkout on the path; set HERMES_AGENT_REPO if yours
is not at ~/.hermes/hermes-agent.
License
Apache-2.0. Built by Prism Network. Not affiliated with Nous Research.
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file hermes_plugin_prism-0.2.0.tar.gz.
File metadata
- Download URL: hermes_plugin_prism-0.2.0.tar.gz
- Upload date:
- Size: 95.4 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via:
twine/6.2.0 CPython/3.9.6
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
9e6f1ec1c0dd5e229b5dd2bb54fad0f1ac2521785611b124645c1f96cf15e363
|
|
| MD5 |
100f94fb60d2aa8efc6758a7d23d4949
|
|
| BLAKE2b-256 |
f98096770232a68fd4764687cc647632920ecb0106c81ab9e8a236f1eb1219ff
|
File details
Details for the file hermes_plugin_prism-0.2.0-py3-none-any.whl.
File metadata
- Download URL: hermes_plugin_prism-0.2.0-py3-none-any.whl
- Upload date:
- Size: 36.4 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via:
twine/6.2.0 CPython/3.9.6
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b2f45cc766138829cac196fec078b69fd651df64910f42376a61588d2d8f34fa
|
|
| MD5 |
e147703467aba09695b37cb2afdc3ac5
|
|
| BLAKE2b-256 |
3f30fd276ffcb65469a8e4df74189ceed8b7ba38235c8cb6dc03d831d05ece02
|