atbash-hermes-plugin 0.9.12.dev0__tar.gz → 0.11.1__tar.gz

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.
Files changed (26) hide show
  1. {atbash_hermes_plugin-0.9.12.dev0/atbash_hermes_plugin.egg-info → atbash_hermes_plugin-0.11.1}/PKG-INFO +67 -5
  2. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/README.md +65 -3
  3. atbash_hermes_plugin-0.11.1/atbash_hermes_plugin/__init__.py +2911 -0
  4. atbash_hermes_plugin-0.11.1/atbash_hermes_plugin/__main__.py +49 -0
  5. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1/atbash_hermes_plugin.egg-info}/PKG-INFO +67 -5
  6. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/atbash_hermes_plugin.egg-info/SOURCES.txt +7 -1
  7. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/atbash_hermes_plugin.egg-info/requires.txt +1 -1
  8. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/plugin.yaml +6 -3
  9. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/pyproject.toml +2 -2
  10. atbash_hermes_plugin-0.11.1/tests/test_guard_selfprotection.py +807 -0
  11. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/tests/test_memory_poisoning.py +24 -5
  12. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/tests/test_memory_write_fail_closed.py +10 -1
  13. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/tests/test_pre_tool_call_verdicts.py +20 -1
  14. atbash_hermes_plugin-0.11.1/tests/test_zero_bugs_fuzz.py +470 -0
  15. atbash_hermes_plugin-0.11.1/tests/test_zero_bugs_issues.py +870 -0
  16. atbash_hermes_plugin-0.11.1/tests/test_zero_bugs_more.py +347 -0
  17. atbash_hermes_plugin-0.11.1/tests/test_zero_bugs_round.py +448 -0
  18. atbash_hermes_plugin-0.9.12.dev0/atbash_hermes_plugin/__init__.py +0 -1378
  19. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/LICENSE +0 -0
  20. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/MANIFEST.in +0 -0
  21. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/NOTICE +0 -0
  22. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/atbash_hermes_plugin.egg-info/dependency_links.txt +0 -0
  23. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/atbash_hermes_plugin.egg-info/entry_points.txt +0 -0
  24. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/atbash_hermes_plugin.egg-info/top_level.txt +0 -0
  25. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/setup.cfg +0 -0
  26. {atbash_hermes_plugin-0.9.12.dev0 → atbash_hermes_plugin-0.11.1}/tests/test_release_contract.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: atbash-hermes-plugin
3
- Version: 0.9.12.dev0
3
+ Version: 0.11.1
4
4
  Summary: Atbash safety plugin for Hermes Agent
5
5
  Author: atbash
6
6
  License-Expression: Apache-2.0
@@ -11,7 +11,7 @@ Requires-Python: <3.13,>=3.9
11
11
  Description-Content-Type: text/markdown
12
12
  License-File: LICENSE
13
13
  License-File: NOTICE
14
- Requires-Dist: atbash-sdk==0.9.12.dev0
14
+ Requires-Dist: atbash-sdk==0.11.0
15
15
  Requires-Dist: httpx<1,>=0.27
16
16
  Requires-Dist: opentelemetry-exporter-otlp-proto-http<2,>=1.29
17
17
  Requires-Dist: opentelemetry-sdk<2,>=1.29
@@ -124,8 +124,10 @@ hermes
124
124
  ## Optional Settings
125
125
 
126
126
  ```bash
127
- # Override the Atbash API endpoint.
128
- ATBASH_ENDPOINT=https://api.atbash.io
127
+ # Override the Atbash API endpoint. Must be a trusted judge host
128
+ # (atbash.ai / www.atbash.ai under the default policy); other hosts need
129
+ # ATBASH_JUDGE_ENDPOINT_POLICY=self-hosted plus ATBASH_JUDGE_VERIFY_PUBKEY.
130
+ ATBASH_ENDPOINT=https://atbash.ai
129
131
 
130
132
  # Set to self-hosted when using your own judge endpoint. Self-hosted judges
131
133
  # require ATBASH_JUDGE_VERIFY_PUBKEY so the SDK can verify signed responses.
@@ -274,7 +276,9 @@ Hermes sessions.
274
276
  - `ATBASH_ENFORCE_DECISION=false`: fail open and allow.
275
277
  - Memory writes (`MEMORY.md`, `CLAUDE.md`, `memory/` paths) with `No verdict`: allowed
276
278
  and recorded as the new tamper baseline only when the judge marks the response as the
277
- AUDIT tier (`status: "logged"`). Any other missing verdict — empty body, truncated
279
+ AUDIT tier (`status: "logged"`) **and** the deployment opts in to monitor-only with
280
+ `ATBASH_ALLOW_AUDIT_TIER=1`. Without the opt-in a `logged` answer is refused like any
281
+ other unjudged one. Any other missing verdict — empty body, truncated
278
282
  payload, a proxy error served as 200, a compromised judge — is blocked under
279
283
  `ATBASH_ENFORCE_DECISION=true`; under `false` the write proceeds but is never
280
284
  recorded as the baseline, because it was not judged.
@@ -299,6 +303,64 @@ After dashboard approval or rejection, the SDK can query held-action status with
299
303
  the judgment ID. The Hermes plugin blocks the original tool call and asks the
300
304
  user to retry after review, rather than automatically re-running the action.
301
305
 
306
+ ## Guard Self-Protection And Memory Baselines
307
+
308
+ - **The guard's own state is not writable by the agent.** Write tools (`write`, `edit`,
309
+ `multiedit`, `write_file`, `create_file`, `patch`, `apply_patch`, `str_replace_editor`,
310
+ `fs_write`, `notebook_edit`, and anything the tool map classes as `filesystem_write`)
311
+ are refused, before judging and in monitor mode too, when they target
312
+ `~/.config/atbash`, the configured tool map, agent key and hash baseline, a dedicated
313
+ key directory (such as `/opt/data/atbash`), the Hermes home's `.env`, `.op.env`,
314
+ `config.yaml` and `SOUL.md` (`~/.hermes`, `$HERMES_HOME`, and `%LOCALAPPDATA%\hermes` on
315
+ Windows), the Hermes install folder's `.env`, or the plugin's install directory. To
316
+ change one of these (for example your persona in `SOUL.md`), edit the file yourself;
317
+ the agent's write is refused even if you approve it inside Hermes. Paths are
318
+ compared by file identity, so hard links and case variants count. Patch tools are also
319
+ refused when their body names one of those paths.
320
+ - **A memory file with no trusted baseline is blocked, and nothing is sent anywhere.**
321
+ A memory file is one of `AGENTS.md`, `AGENTS.override.md`, `CLAUDE.md`, `MEMORY.md`,
322
+ `USER.md`, `DREAMS.md`, `.hermes.md`, `HERMES.md`, `.cursorrules` (by exact name, and on
323
+ Windows also the spellings Windows opens as that file, such as `AGENTS.md.`), a
324
+ `.cursor/rules/*.mdc` file, a `.md`/`.txt` document inside a `memory/` or `memories/`
325
+ folder, or a file under `~/.claude/projects/` or `~/.openclaw/{workspace,memory}/`.
326
+ Ordinary code such as `src/memory/alloc.rs` is not memory and is judged like any other
327
+ file.
328
+ Files the guard records itself (judged writes) are trusted. For files that existed
329
+ before the guard (a repository's `AGENTS.md`), review them and trust them yourself,
330
+ outside the agent:
331
+
332
+ ```bash
333
+ python -m atbash_hermes_plugin seed AGENTS.md memory/notes.md
334
+ ```
335
+
336
+ Run it from outside the repository you are trusting, with absolute paths (for example
337
+ `cd ~ && python -m atbash_hermes_plugin seed /path/to/repo/AGENTS.md`): `python -m`
338
+ puts the current folder first on Python's import path, so a hostile repository could
339
+ otherwise shadow a standard module. The command itself never imports Hermes code.
340
+
341
+ It prints the baseline file it wrote. That is the one the guard reads:
342
+ `ATBASH_MEMORY_HASH_PATH` from your environment or from the Hermes home `.env`, else
343
+ `~/.config/atbash/hermes-memory-hashes.json`. Pass `--store <file>` to choose it
344
+ explicitly. If any file in the list cannot be read, nothing is trusted.
345
+
346
+ The guard refuses agent tool calls that look like they run the seeder (the command,
347
+ `seed_memory_baselines`, the baseline file's name, including quoted, variable-split or
348
+ base64-encoded forms). This is best effort - see the known limit below - and it also
349
+ refuses harmless agent calls that merely mention those names (editing these docs, a
350
+ grep for the command).
351
+
352
+ In Docker, point the baseline file at the mounted volume so trust survives restarts,
353
+ e.g. `-e ATBASH_MEMORY_HASH_PATH=/opt/data/atbash/hermes-memory-hashes.json`, and run
354
+ the seed command inside the container.
355
+ - **What the guard sees:** tool calls only. Hermes loads its context files (`AGENTS.md`,
356
+ `.hermes.md`, `SOUL.md`, ...) into a new session's instructions without a tool call, so
357
+ baselines protect the agent's tool reads, and the real control on those files is that
358
+ agent writes to them are scanned and judged.
359
+ - **Known limit:** the baseline file (`~/.config/atbash/hermes-memory-hashes.json`) is
360
+ plain JSON. The guard refuses the agent's file tools on it, but a shell command that
361
+ rewrites a memory file and recomputes its SHA-256 is left to the judge. Closing that
362
+ needs an authenticated baseline (a MAC) or state outside the agent's reach.
363
+
302
364
  ## Troubleshooting
303
365
 
304
366
  If Hermes does not show the plugin:
@@ -105,8 +105,10 @@ hermes
105
105
  ## Optional Settings
106
106
 
107
107
  ```bash
108
- # Override the Atbash API endpoint.
109
- ATBASH_ENDPOINT=https://api.atbash.io
108
+ # Override the Atbash API endpoint. Must be a trusted judge host
109
+ # (atbash.ai / www.atbash.ai under the default policy); other hosts need
110
+ # ATBASH_JUDGE_ENDPOINT_POLICY=self-hosted plus ATBASH_JUDGE_VERIFY_PUBKEY.
111
+ ATBASH_ENDPOINT=https://atbash.ai
110
112
 
111
113
  # Set to self-hosted when using your own judge endpoint. Self-hosted judges
112
114
  # require ATBASH_JUDGE_VERIFY_PUBKEY so the SDK can verify signed responses.
@@ -255,7 +257,9 @@ Hermes sessions.
255
257
  - `ATBASH_ENFORCE_DECISION=false`: fail open and allow.
256
258
  - Memory writes (`MEMORY.md`, `CLAUDE.md`, `memory/` paths) with `No verdict`: allowed
257
259
  and recorded as the new tamper baseline only when the judge marks the response as the
258
- AUDIT tier (`status: "logged"`). Any other missing verdict — empty body, truncated
260
+ AUDIT tier (`status: "logged"`) **and** the deployment opts in to monitor-only with
261
+ `ATBASH_ALLOW_AUDIT_TIER=1`. Without the opt-in a `logged` answer is refused like any
262
+ other unjudged one. Any other missing verdict — empty body, truncated
259
263
  payload, a proxy error served as 200, a compromised judge — is blocked under
260
264
  `ATBASH_ENFORCE_DECISION=true`; under `false` the write proceeds but is never
261
265
  recorded as the baseline, because it was not judged.
@@ -280,6 +284,64 @@ After dashboard approval or rejection, the SDK can query held-action status with
280
284
  the judgment ID. The Hermes plugin blocks the original tool call and asks the
281
285
  user to retry after review, rather than automatically re-running the action.
282
286
 
287
+ ## Guard Self-Protection And Memory Baselines
288
+
289
+ - **The guard's own state is not writable by the agent.** Write tools (`write`, `edit`,
290
+ `multiedit`, `write_file`, `create_file`, `patch`, `apply_patch`, `str_replace_editor`,
291
+ `fs_write`, `notebook_edit`, and anything the tool map classes as `filesystem_write`)
292
+ are refused, before judging and in monitor mode too, when they target
293
+ `~/.config/atbash`, the configured tool map, agent key and hash baseline, a dedicated
294
+ key directory (such as `/opt/data/atbash`), the Hermes home's `.env`, `.op.env`,
295
+ `config.yaml` and `SOUL.md` (`~/.hermes`, `$HERMES_HOME`, and `%LOCALAPPDATA%\hermes` on
296
+ Windows), the Hermes install folder's `.env`, or the plugin's install directory. To
297
+ change one of these (for example your persona in `SOUL.md`), edit the file yourself;
298
+ the agent's write is refused even if you approve it inside Hermes. Paths are
299
+ compared by file identity, so hard links and case variants count. Patch tools are also
300
+ refused when their body names one of those paths.
301
+ - **A memory file with no trusted baseline is blocked, and nothing is sent anywhere.**
302
+ A memory file is one of `AGENTS.md`, `AGENTS.override.md`, `CLAUDE.md`, `MEMORY.md`,
303
+ `USER.md`, `DREAMS.md`, `.hermes.md`, `HERMES.md`, `.cursorrules` (by exact name, and on
304
+ Windows also the spellings Windows opens as that file, such as `AGENTS.md.`), a
305
+ `.cursor/rules/*.mdc` file, a `.md`/`.txt` document inside a `memory/` or `memories/`
306
+ folder, or a file under `~/.claude/projects/` or `~/.openclaw/{workspace,memory}/`.
307
+ Ordinary code such as `src/memory/alloc.rs` is not memory and is judged like any other
308
+ file.
309
+ Files the guard records itself (judged writes) are trusted. For files that existed
310
+ before the guard (a repository's `AGENTS.md`), review them and trust them yourself,
311
+ outside the agent:
312
+
313
+ ```bash
314
+ python -m atbash_hermes_plugin seed AGENTS.md memory/notes.md
315
+ ```
316
+
317
+ Run it from outside the repository you are trusting, with absolute paths (for example
318
+ `cd ~ && python -m atbash_hermes_plugin seed /path/to/repo/AGENTS.md`): `python -m`
319
+ puts the current folder first on Python's import path, so a hostile repository could
320
+ otherwise shadow a standard module. The command itself never imports Hermes code.
321
+
322
+ It prints the baseline file it wrote. That is the one the guard reads:
323
+ `ATBASH_MEMORY_HASH_PATH` from your environment or from the Hermes home `.env`, else
324
+ `~/.config/atbash/hermes-memory-hashes.json`. Pass `--store <file>` to choose it
325
+ explicitly. If any file in the list cannot be read, nothing is trusted.
326
+
327
+ The guard refuses agent tool calls that look like they run the seeder (the command,
328
+ `seed_memory_baselines`, the baseline file's name, including quoted, variable-split or
329
+ base64-encoded forms). This is best effort - see the known limit below - and it also
330
+ refuses harmless agent calls that merely mention those names (editing these docs, a
331
+ grep for the command).
332
+
333
+ In Docker, point the baseline file at the mounted volume so trust survives restarts,
334
+ e.g. `-e ATBASH_MEMORY_HASH_PATH=/opt/data/atbash/hermes-memory-hashes.json`, and run
335
+ the seed command inside the container.
336
+ - **What the guard sees:** tool calls only. Hermes loads its context files (`AGENTS.md`,
337
+ `.hermes.md`, `SOUL.md`, ...) into a new session's instructions without a tool call, so
338
+ baselines protect the agent's tool reads, and the real control on those files is that
339
+ agent writes to them are scanned and judged.
340
+ - **Known limit:** the baseline file (`~/.config/atbash/hermes-memory-hashes.json`) is
341
+ plain JSON. The guard refuses the agent's file tools on it, but a shell command that
342
+ rewrites a memory file and recomputes its SHA-256 is left to the judge. Closing that
343
+ needs an authenticated baseline (a MAC) or state outside the agent's reach.
344
+
283
345
  ## Troubleshooting
284
346
 
285
347
  If Hermes does not show the plugin: