hermes-profile-kit 3.0.0__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.
- hermes_profile_kit-3.0.0/LICENSE +21 -0
- hermes_profile_kit-3.0.0/PKG-INFO +89 -0
- hermes_profile_kit-3.0.0/README.md +66 -0
- hermes_profile_kit-3.0.0/pyproject.toml +47 -0
- hermes_profile_kit-3.0.0/setup.cfg +4 -0
- hermes_profile_kit-3.0.0/src/hermes_profile_kit.egg-info/PKG-INFO +89 -0
- hermes_profile_kit-3.0.0/src/hermes_profile_kit.egg-info/SOURCES.txt +44 -0
- hermes_profile_kit-3.0.0/src/hermes_profile_kit.egg-info/dependency_links.txt +1 -0
- hermes_profile_kit-3.0.0/src/hermes_profile_kit.egg-info/entry_points.txt +2 -0
- hermes_profile_kit-3.0.0/src/hermes_profile_kit.egg-info/requires.txt +13 -0
- hermes_profile_kit-3.0.0/src/hermes_profile_kit.egg-info/top_level.txt +1 -0
- hermes_profile_kit-3.0.0/src/hpk/__init__.py +3 -0
- hermes_profile_kit-3.0.0/src/hpk/__main__.py +4 -0
- hermes_profile_kit-3.0.0/src/hpk/cli.py +176 -0
- hermes_profile_kit-3.0.0/src/hpk/codegen/__init__.py +0 -0
- hermes_profile_kit-3.0.0/src/hpk/codegen/argparse_walker.py +158 -0
- hermes_profile_kit-3.0.0/src/hpk/codegen/cmd_index.py +12 -0
- hermes_profile_kit-3.0.0/src/hpk/codegen/validate.py +25 -0
- hermes_profile_kit-3.0.0/src/hpk/hermes.py +60 -0
- hermes_profile_kit-3.0.0/src/hpk/manifest.py +151 -0
- hermes_profile_kit-3.0.0/src/hpk/plugins.py +36 -0
- hermes_profile_kit-3.0.0/src/hpk/profiles.py +64 -0
- hermes_profile_kit-3.0.0/src/hpk/py.typed +0 -0
- hermes_profile_kit-3.0.0/src/hpk/tokens/__init__.py +30 -0
- hermes_profile_kit-3.0.0/src/hpk/tokens/anthropic.py +27 -0
- hermes_profile_kit-3.0.0/src/hpk/tokens/base.py +30 -0
- hermes_profile_kit-3.0.0/src/hpk/tokens/brave.py +13 -0
- hermes_profile_kit-3.0.0/src/hpk/tokens/discord.py +29 -0
- hermes_profile_kit-3.0.0/src/hpk/tokens/exa.py +13 -0
- hermes_profile_kit-3.0.0/src/hpk/tokens/openai_codex.py +54 -0
- hermes_profile_kit-3.0.0/src/hpk/tokens/slack.py +69 -0
- hermes_profile_kit-3.0.0/src/hpk/tokens/telegram.py +31 -0
- hermes_profile_kit-3.0.0/src/hpk/ui.py +38 -0
- hermes_profile_kit-3.0.0/src/hpk/verify.py +43 -0
- hermes_profile_kit-3.0.0/src/hpk/wizard.py +178 -0
- hermes_profile_kit-3.0.0/tests/test_cli.py +100 -0
- hermes_profile_kit-3.0.0/tests/test_codegen.py +121 -0
- hermes_profile_kit-3.0.0/tests/test_drift_report.py +13 -0
- hermes_profile_kit-3.0.0/tests/test_hermes.py +26 -0
- hermes_profile_kit-3.0.0/tests/test_manifest.py +189 -0
- hermes_profile_kit-3.0.0/tests/test_plugins.py +59 -0
- hermes_profile_kit-3.0.0/tests/test_profiles.py +97 -0
- hermes_profile_kit-3.0.0/tests/test_ui.py +15 -0
- hermes_profile_kit-3.0.0/tests/test_update_pin.py +22 -0
- hermes_profile_kit-3.0.0/tests/test_verify.py +56 -0
- hermes_profile_kit-3.0.0/tests/test_wizard.py +226 -0
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 hermes-profile-kit contributors
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
|
@@ -0,0 +1,89 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: hermes-profile-kit
|
|
3
|
+
Version: 3.0.0
|
|
4
|
+
Summary: Interactive multi-profile setup utility for Hermes Agent
|
|
5
|
+
Author: NewTurn2017
|
|
6
|
+
License: MIT
|
|
7
|
+
Requires-Python: >=3.10
|
|
8
|
+
Description-Content-Type: text/markdown
|
|
9
|
+
License-File: LICENSE
|
|
10
|
+
Requires-Dist: click>=8.1
|
|
11
|
+
Requires-Dist: packaging>=23
|
|
12
|
+
Requires-Dist: questionary>=2.0
|
|
13
|
+
Requires-Dist: rich>=13
|
|
14
|
+
Requires-Dist: pyyaml>=6
|
|
15
|
+
Requires-Dist: pydantic>=2
|
|
16
|
+
Provides-Extra: dev
|
|
17
|
+
Requires-Dist: pytest>=8; extra == "dev"
|
|
18
|
+
Requires-Dist: pytest-mock>=3; extra == "dev"
|
|
19
|
+
Requires-Dist: ruff>=0.5; extra == "dev"
|
|
20
|
+
Requires-Dist: mypy>=1.10; extra == "dev"
|
|
21
|
+
Requires-Dist: types-PyYAML; extra == "dev"
|
|
22
|
+
Dynamic: license-file
|
|
23
|
+
|
|
24
|
+
# hermes-profile-kit
|
|
25
|
+
|
|
26
|
+
Interactive multi-profile setup utility for [Hermes Agent](https://github.com/NousResearch/hermes-agent).
|
|
27
|
+
|
|
28
|
+
[](LICENSE)
|
|
29
|
+
[](https://github.com/NewTurn2017/hermes-profile-kit/actions/workflows/ci.yml)
|
|
30
|
+
|
|
31
|
+
> 🇰🇷 [한국어 README](README.ko.md)
|
|
32
|
+
|
|
33
|
+
## Quick start
|
|
34
|
+
|
|
35
|
+
```bash
|
|
36
|
+
pipx install hermes-profile-kit
|
|
37
|
+
hpk setup
|
|
38
|
+
```
|
|
39
|
+
|
|
40
|
+
The wizard walks you through 4 profiles (`coder` / `assistant` / `research` / `community-bot`), prompts for the right tokens per channel (Anthropic, Telegram, Slack, Discord, Brave, Exa), and optionally enables recommended plugins (Honcho memory, Brave search tool).
|
|
41
|
+
|
|
42
|
+
## What hpk does (and doesn't)
|
|
43
|
+
|
|
44
|
+
- ✅ Creates and configures four isolated Hermes profiles.
|
|
45
|
+
- ✅ Walks you through BotFather, Slack app, Discord devportal flows.
|
|
46
|
+
- ✅ Atomic, idempotent `.env` writes (chmod 600). Re-running is safe.
|
|
47
|
+
- ✅ Daily upstream-sync via GitHub Actions — kit stays current with Hermes changes.
|
|
48
|
+
- ❌ Does not install Hermes itself (see [Hermes installation](https://github.com/NousResearch/hermes-agent#installation)).
|
|
49
|
+
- ❌ Does not start gateway services automatically.
|
|
50
|
+
- ❌ Does not invoke any hermes command that isn't verified in upstream.
|
|
51
|
+
|
|
52
|
+
## How it stays correct
|
|
53
|
+
|
|
54
|
+
`hpk` never embeds a hermes command that hasn't been observed in the upstream argparse tree. CI AST-parses `hermes_cli/main.py` daily, regenerates `docs/commands.md` and `build/cmd_index.json`, and opens a PR when drift is detected.
|
|
55
|
+
|
|
56
|
+
## Profiles
|
|
57
|
+
|
|
58
|
+
| Profile | Role | Model tier | Channels |
|
|
59
|
+
|---|---|---|---|
|
|
60
|
+
| `coder` | Full-stack dev assistant | Sonnet | CLI |
|
|
61
|
+
| `assistant` | Personal daily assistant | Sonnet | CLI + Telegram |
|
|
62
|
+
| `research` | Web-search-backed research | Opus | CLI |
|
|
63
|
+
| `community-bot` | Korean dev community helper | Haiku | Telegram + Discord |
|
|
64
|
+
|
|
65
|
+
## Customization
|
|
66
|
+
|
|
67
|
+
| Goal | Edit |
|
|
68
|
+
|---|---|
|
|
69
|
+
| Change model | `~/.hermes/profiles/<name>/config.yaml` |
|
|
70
|
+
| Change persona | `~/.hermes/profiles/<name>/SOUL.md` |
|
|
71
|
+
| Add new profile | `profiles/<name>/{SOUL.md,config.yaml,.env.example}` + add to `manifest.yaml` → `hpk setup` |
|
|
72
|
+
| Enable a plugin | Add to `manifest.yaml` `plugins:` + reference from `recommended_plugins` |
|
|
73
|
+
|
|
74
|
+
API keys go in `~/.hermes/profiles/<name>/.env`. They're plain text with `chmod 600` — the kit deliberately does not pretend to encrypt them.
|
|
75
|
+
|
|
76
|
+
## Commands
|
|
77
|
+
|
|
78
|
+
```bash
|
|
79
|
+
hpk setup [profile...] # interactive wizard
|
|
80
|
+
hpk verify # doctor + FILL_IN scan
|
|
81
|
+
hpk doctor # hpk's own health
|
|
82
|
+
hpk reset [profile...] # remove kit-created profiles
|
|
83
|
+
hpk plugin list # show recommended_plugins
|
|
84
|
+
hpk sync --dry-run # local drift check
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
## License
|
|
88
|
+
|
|
89
|
+
MIT. See `LICENSE`.
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
# hermes-profile-kit
|
|
2
|
+
|
|
3
|
+
Interactive multi-profile setup utility for [Hermes Agent](https://github.com/NousResearch/hermes-agent).
|
|
4
|
+
|
|
5
|
+
[](LICENSE)
|
|
6
|
+
[](https://github.com/NewTurn2017/hermes-profile-kit/actions/workflows/ci.yml)
|
|
7
|
+
|
|
8
|
+
> 🇰🇷 [한국어 README](README.ko.md)
|
|
9
|
+
|
|
10
|
+
## Quick start
|
|
11
|
+
|
|
12
|
+
```bash
|
|
13
|
+
pipx install hermes-profile-kit
|
|
14
|
+
hpk setup
|
|
15
|
+
```
|
|
16
|
+
|
|
17
|
+
The wizard walks you through 4 profiles (`coder` / `assistant` / `research` / `community-bot`), prompts for the right tokens per channel (Anthropic, Telegram, Slack, Discord, Brave, Exa), and optionally enables recommended plugins (Honcho memory, Brave search tool).
|
|
18
|
+
|
|
19
|
+
## What hpk does (and doesn't)
|
|
20
|
+
|
|
21
|
+
- ✅ Creates and configures four isolated Hermes profiles.
|
|
22
|
+
- ✅ Walks you through BotFather, Slack app, Discord devportal flows.
|
|
23
|
+
- ✅ Atomic, idempotent `.env` writes (chmod 600). Re-running is safe.
|
|
24
|
+
- ✅ Daily upstream-sync via GitHub Actions — kit stays current with Hermes changes.
|
|
25
|
+
- ❌ Does not install Hermes itself (see [Hermes installation](https://github.com/NousResearch/hermes-agent#installation)).
|
|
26
|
+
- ❌ Does not start gateway services automatically.
|
|
27
|
+
- ❌ Does not invoke any hermes command that isn't verified in upstream.
|
|
28
|
+
|
|
29
|
+
## How it stays correct
|
|
30
|
+
|
|
31
|
+
`hpk` never embeds a hermes command that hasn't been observed in the upstream argparse tree. CI AST-parses `hermes_cli/main.py` daily, regenerates `docs/commands.md` and `build/cmd_index.json`, and opens a PR when drift is detected.
|
|
32
|
+
|
|
33
|
+
## Profiles
|
|
34
|
+
|
|
35
|
+
| Profile | Role | Model tier | Channels |
|
|
36
|
+
|---|---|---|---|
|
|
37
|
+
| `coder` | Full-stack dev assistant | Sonnet | CLI |
|
|
38
|
+
| `assistant` | Personal daily assistant | Sonnet | CLI + Telegram |
|
|
39
|
+
| `research` | Web-search-backed research | Opus | CLI |
|
|
40
|
+
| `community-bot` | Korean dev community helper | Haiku | Telegram + Discord |
|
|
41
|
+
|
|
42
|
+
## Customization
|
|
43
|
+
|
|
44
|
+
| Goal | Edit |
|
|
45
|
+
|---|---|
|
|
46
|
+
| Change model | `~/.hermes/profiles/<name>/config.yaml` |
|
|
47
|
+
| Change persona | `~/.hermes/profiles/<name>/SOUL.md` |
|
|
48
|
+
| Add new profile | `profiles/<name>/{SOUL.md,config.yaml,.env.example}` + add to `manifest.yaml` → `hpk setup` |
|
|
49
|
+
| Enable a plugin | Add to `manifest.yaml` `plugins:` + reference from `recommended_plugins` |
|
|
50
|
+
|
|
51
|
+
API keys go in `~/.hermes/profiles/<name>/.env`. They're plain text with `chmod 600` — the kit deliberately does not pretend to encrypt them.
|
|
52
|
+
|
|
53
|
+
## Commands
|
|
54
|
+
|
|
55
|
+
```bash
|
|
56
|
+
hpk setup [profile...] # interactive wizard
|
|
57
|
+
hpk verify # doctor + FILL_IN scan
|
|
58
|
+
hpk doctor # hpk's own health
|
|
59
|
+
hpk reset [profile...] # remove kit-created profiles
|
|
60
|
+
hpk plugin list # show recommended_plugins
|
|
61
|
+
hpk sync --dry-run # local drift check
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
## License
|
|
65
|
+
|
|
66
|
+
MIT. See `LICENSE`.
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
[build-system]
|
|
2
|
+
requires = ["setuptools>=68", "wheel"]
|
|
3
|
+
build-backend = "setuptools.build_meta"
|
|
4
|
+
|
|
5
|
+
[project]
|
|
6
|
+
name = "hermes-profile-kit"
|
|
7
|
+
version = "3.0.0"
|
|
8
|
+
description = "Interactive multi-profile setup utility for Hermes Agent"
|
|
9
|
+
readme = "README.md"
|
|
10
|
+
requires-python = ">=3.10"
|
|
11
|
+
license = { text = "MIT" }
|
|
12
|
+
authors = [{ name = "NewTurn2017" }]
|
|
13
|
+
dependencies = [
|
|
14
|
+
"click>=8.1",
|
|
15
|
+
"packaging>=23",
|
|
16
|
+
"questionary>=2.0",
|
|
17
|
+
"rich>=13",
|
|
18
|
+
"pyyaml>=6",
|
|
19
|
+
"pydantic>=2",
|
|
20
|
+
]
|
|
21
|
+
|
|
22
|
+
[project.optional-dependencies]
|
|
23
|
+
dev = ["pytest>=8", "pytest-mock>=3", "ruff>=0.5", "mypy>=1.10", "types-PyYAML"]
|
|
24
|
+
|
|
25
|
+
[project.scripts]
|
|
26
|
+
hpk = "hpk.cli:main"
|
|
27
|
+
|
|
28
|
+
[tool.setuptools.packages.find]
|
|
29
|
+
where = ["src"]
|
|
30
|
+
|
|
31
|
+
[tool.setuptools.package-data]
|
|
32
|
+
hpk = ["py.typed"]
|
|
33
|
+
|
|
34
|
+
[tool.ruff]
|
|
35
|
+
line-length = 100
|
|
36
|
+
target-version = "py310"
|
|
37
|
+
|
|
38
|
+
[tool.ruff.lint]
|
|
39
|
+
select = ["E", "F", "I", "B", "UP", "RUF"]
|
|
40
|
+
|
|
41
|
+
[tool.mypy]
|
|
42
|
+
strict = true
|
|
43
|
+
files = ["src/hpk"]
|
|
44
|
+
|
|
45
|
+
[tool.pytest.ini_options]
|
|
46
|
+
testpaths = ["tests"]
|
|
47
|
+
addopts = "-ra -q"
|
|
@@ -0,0 +1,89 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: hermes-profile-kit
|
|
3
|
+
Version: 3.0.0
|
|
4
|
+
Summary: Interactive multi-profile setup utility for Hermes Agent
|
|
5
|
+
Author: NewTurn2017
|
|
6
|
+
License: MIT
|
|
7
|
+
Requires-Python: >=3.10
|
|
8
|
+
Description-Content-Type: text/markdown
|
|
9
|
+
License-File: LICENSE
|
|
10
|
+
Requires-Dist: click>=8.1
|
|
11
|
+
Requires-Dist: packaging>=23
|
|
12
|
+
Requires-Dist: questionary>=2.0
|
|
13
|
+
Requires-Dist: rich>=13
|
|
14
|
+
Requires-Dist: pyyaml>=6
|
|
15
|
+
Requires-Dist: pydantic>=2
|
|
16
|
+
Provides-Extra: dev
|
|
17
|
+
Requires-Dist: pytest>=8; extra == "dev"
|
|
18
|
+
Requires-Dist: pytest-mock>=3; extra == "dev"
|
|
19
|
+
Requires-Dist: ruff>=0.5; extra == "dev"
|
|
20
|
+
Requires-Dist: mypy>=1.10; extra == "dev"
|
|
21
|
+
Requires-Dist: types-PyYAML; extra == "dev"
|
|
22
|
+
Dynamic: license-file
|
|
23
|
+
|
|
24
|
+
# hermes-profile-kit
|
|
25
|
+
|
|
26
|
+
Interactive multi-profile setup utility for [Hermes Agent](https://github.com/NousResearch/hermes-agent).
|
|
27
|
+
|
|
28
|
+
[](LICENSE)
|
|
29
|
+
[](https://github.com/NewTurn2017/hermes-profile-kit/actions/workflows/ci.yml)
|
|
30
|
+
|
|
31
|
+
> 🇰🇷 [한국어 README](README.ko.md)
|
|
32
|
+
|
|
33
|
+
## Quick start
|
|
34
|
+
|
|
35
|
+
```bash
|
|
36
|
+
pipx install hermes-profile-kit
|
|
37
|
+
hpk setup
|
|
38
|
+
```
|
|
39
|
+
|
|
40
|
+
The wizard walks you through 4 profiles (`coder` / `assistant` / `research` / `community-bot`), prompts for the right tokens per channel (Anthropic, Telegram, Slack, Discord, Brave, Exa), and optionally enables recommended plugins (Honcho memory, Brave search tool).
|
|
41
|
+
|
|
42
|
+
## What hpk does (and doesn't)
|
|
43
|
+
|
|
44
|
+
- ✅ Creates and configures four isolated Hermes profiles.
|
|
45
|
+
- ✅ Walks you through BotFather, Slack app, Discord devportal flows.
|
|
46
|
+
- ✅ Atomic, idempotent `.env` writes (chmod 600). Re-running is safe.
|
|
47
|
+
- ✅ Daily upstream-sync via GitHub Actions — kit stays current with Hermes changes.
|
|
48
|
+
- ❌ Does not install Hermes itself (see [Hermes installation](https://github.com/NousResearch/hermes-agent#installation)).
|
|
49
|
+
- ❌ Does not start gateway services automatically.
|
|
50
|
+
- ❌ Does not invoke any hermes command that isn't verified in upstream.
|
|
51
|
+
|
|
52
|
+
## How it stays correct
|
|
53
|
+
|
|
54
|
+
`hpk` never embeds a hermes command that hasn't been observed in the upstream argparse tree. CI AST-parses `hermes_cli/main.py` daily, regenerates `docs/commands.md` and `build/cmd_index.json`, and opens a PR when drift is detected.
|
|
55
|
+
|
|
56
|
+
## Profiles
|
|
57
|
+
|
|
58
|
+
| Profile | Role | Model tier | Channels |
|
|
59
|
+
|---|---|---|---|
|
|
60
|
+
| `coder` | Full-stack dev assistant | Sonnet | CLI |
|
|
61
|
+
| `assistant` | Personal daily assistant | Sonnet | CLI + Telegram |
|
|
62
|
+
| `research` | Web-search-backed research | Opus | CLI |
|
|
63
|
+
| `community-bot` | Korean dev community helper | Haiku | Telegram + Discord |
|
|
64
|
+
|
|
65
|
+
## Customization
|
|
66
|
+
|
|
67
|
+
| Goal | Edit |
|
|
68
|
+
|---|---|
|
|
69
|
+
| Change model | `~/.hermes/profiles/<name>/config.yaml` |
|
|
70
|
+
| Change persona | `~/.hermes/profiles/<name>/SOUL.md` |
|
|
71
|
+
| Add new profile | `profiles/<name>/{SOUL.md,config.yaml,.env.example}` + add to `manifest.yaml` → `hpk setup` |
|
|
72
|
+
| Enable a plugin | Add to `manifest.yaml` `plugins:` + reference from `recommended_plugins` |
|
|
73
|
+
|
|
74
|
+
API keys go in `~/.hermes/profiles/<name>/.env`. They're plain text with `chmod 600` — the kit deliberately does not pretend to encrypt them.
|
|
75
|
+
|
|
76
|
+
## Commands
|
|
77
|
+
|
|
78
|
+
```bash
|
|
79
|
+
hpk setup [profile...] # interactive wizard
|
|
80
|
+
hpk verify # doctor + FILL_IN scan
|
|
81
|
+
hpk doctor # hpk's own health
|
|
82
|
+
hpk reset [profile...] # remove kit-created profiles
|
|
83
|
+
hpk plugin list # show recommended_plugins
|
|
84
|
+
hpk sync --dry-run # local drift check
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
## License
|
|
88
|
+
|
|
89
|
+
MIT. See `LICENSE`.
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
LICENSE
|
|
2
|
+
README.md
|
|
3
|
+
pyproject.toml
|
|
4
|
+
src/hermes_profile_kit.egg-info/PKG-INFO
|
|
5
|
+
src/hermes_profile_kit.egg-info/SOURCES.txt
|
|
6
|
+
src/hermes_profile_kit.egg-info/dependency_links.txt
|
|
7
|
+
src/hermes_profile_kit.egg-info/entry_points.txt
|
|
8
|
+
src/hermes_profile_kit.egg-info/requires.txt
|
|
9
|
+
src/hermes_profile_kit.egg-info/top_level.txt
|
|
10
|
+
src/hpk/__init__.py
|
|
11
|
+
src/hpk/__main__.py
|
|
12
|
+
src/hpk/cli.py
|
|
13
|
+
src/hpk/hermes.py
|
|
14
|
+
src/hpk/manifest.py
|
|
15
|
+
src/hpk/plugins.py
|
|
16
|
+
src/hpk/profiles.py
|
|
17
|
+
src/hpk/py.typed
|
|
18
|
+
src/hpk/ui.py
|
|
19
|
+
src/hpk/verify.py
|
|
20
|
+
src/hpk/wizard.py
|
|
21
|
+
src/hpk/codegen/__init__.py
|
|
22
|
+
src/hpk/codegen/argparse_walker.py
|
|
23
|
+
src/hpk/codegen/cmd_index.py
|
|
24
|
+
src/hpk/codegen/validate.py
|
|
25
|
+
src/hpk/tokens/__init__.py
|
|
26
|
+
src/hpk/tokens/anthropic.py
|
|
27
|
+
src/hpk/tokens/base.py
|
|
28
|
+
src/hpk/tokens/brave.py
|
|
29
|
+
src/hpk/tokens/discord.py
|
|
30
|
+
src/hpk/tokens/exa.py
|
|
31
|
+
src/hpk/tokens/openai_codex.py
|
|
32
|
+
src/hpk/tokens/slack.py
|
|
33
|
+
src/hpk/tokens/telegram.py
|
|
34
|
+
tests/test_cli.py
|
|
35
|
+
tests/test_codegen.py
|
|
36
|
+
tests/test_drift_report.py
|
|
37
|
+
tests/test_hermes.py
|
|
38
|
+
tests/test_manifest.py
|
|
39
|
+
tests/test_plugins.py
|
|
40
|
+
tests/test_profiles.py
|
|
41
|
+
tests/test_ui.py
|
|
42
|
+
tests/test_update_pin.py
|
|
43
|
+
tests/test_verify.py
|
|
44
|
+
tests/test_wizard.py
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
hpk
|
|
@@ -0,0 +1,176 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
import sys
|
|
4
|
+
from pathlib import Path
|
|
5
|
+
|
|
6
|
+
import click
|
|
7
|
+
|
|
8
|
+
from hpk import __version__, ui, verify, wizard
|
|
9
|
+
from hpk.manifest import Manifest, ManifestValidationError, load_manifest
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
def _manifest_path() -> Path:
|
|
13
|
+
return Path.cwd() / "manifest.yaml"
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
def _load() -> Manifest:
|
|
17
|
+
try:
|
|
18
|
+
return load_manifest(_manifest_path())
|
|
19
|
+
except ManifestValidationError as e:
|
|
20
|
+
ui.err(f"manifest invalid: {e}")
|
|
21
|
+
sys.exit(40)
|
|
22
|
+
except FileNotFoundError:
|
|
23
|
+
ui.err(f"manifest.yaml not found at {_manifest_path()}")
|
|
24
|
+
sys.exit(40)
|
|
25
|
+
|
|
26
|
+
|
|
27
|
+
@click.group(invoke_without_command=True)
|
|
28
|
+
@click.version_option(version=__version__, prog_name="hpk")
|
|
29
|
+
@click.pass_context
|
|
30
|
+
def main(ctx: click.Context) -> None:
|
|
31
|
+
"""hpk — interactive multi-profile setup for Hermes Agent."""
|
|
32
|
+
if ctx.invoked_subcommand is None:
|
|
33
|
+
ctx.invoke(setup)
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
@main.command()
|
|
37
|
+
@click.argument("profile", nargs=-1)
|
|
38
|
+
@click.option("--force", is_flag=True, help="Overwrite SOUL.md/config.yaml even if present.")
|
|
39
|
+
@click.option("--skip-tokens", is_flag=True)
|
|
40
|
+
@click.option("--skip-plugins", is_flag=True)
|
|
41
|
+
def setup(
|
|
42
|
+
profile: tuple[str, ...],
|
|
43
|
+
force: bool,
|
|
44
|
+
skip_tokens: bool,
|
|
45
|
+
skip_plugins: bool,
|
|
46
|
+
) -> None:
|
|
47
|
+
"""Interactive multi-profile setup."""
|
|
48
|
+
manifest = _load()
|
|
49
|
+
try:
|
|
50
|
+
wizard.run_wizard(
|
|
51
|
+
manifest,
|
|
52
|
+
targets=list(profile),
|
|
53
|
+
force=force,
|
|
54
|
+
skip_tokens=skip_tokens,
|
|
55
|
+
skip_plugins=skip_plugins,
|
|
56
|
+
)
|
|
57
|
+
except wizard.HermesNotInstalledError as e:
|
|
58
|
+
ui.err(str(e))
|
|
59
|
+
sys.exit(10)
|
|
60
|
+
except wizard.HermesVersionTooOldError as e:
|
|
61
|
+
ui.err(str(e))
|
|
62
|
+
sys.exit(11)
|
|
63
|
+
except wizard.PreflightError as e:
|
|
64
|
+
ui.err(str(e))
|
|
65
|
+
sys.exit(30)
|
|
66
|
+
|
|
67
|
+
|
|
68
|
+
@main.command()
|
|
69
|
+
@click.argument("profile", nargs=-1)
|
|
70
|
+
def verify_cmd(profile: tuple[str, ...]) -> None:
|
|
71
|
+
"""Run hermes doctor + FILL_IN scan."""
|
|
72
|
+
manifest = _load()
|
|
73
|
+
names = list(profile) or [p.name for p in manifest.profiles]
|
|
74
|
+
r = verify.run_verify(names)
|
|
75
|
+
for name in r.passing:
|
|
76
|
+
ui.ok(f"{name}: doctor green")
|
|
77
|
+
for name, reason in r.failing:
|
|
78
|
+
ui.err(f"{name}: {reason}")
|
|
79
|
+
for name, rows in r.fill_in_remaining.items():
|
|
80
|
+
for line, key in rows:
|
|
81
|
+
ui.warn(f"{name}/.env:{line}: {key} still FILL_IN")
|
|
82
|
+
sys.exit(0 if r.ok else 30)
|
|
83
|
+
|
|
84
|
+
|
|
85
|
+
@main.command()
|
|
86
|
+
def doctor() -> None:
|
|
87
|
+
"""Check hpk's own health: hermes presence, manifest validity, codegen freshness."""
|
|
88
|
+
manifest = _load()
|
|
89
|
+
from hpk import hermes as _h
|
|
90
|
+
|
|
91
|
+
try:
|
|
92
|
+
v = _h.get_version()
|
|
93
|
+
ui.ok(f"hermes {v}")
|
|
94
|
+
except _h.HermesNotFoundError:
|
|
95
|
+
ui.err("hermes not found")
|
|
96
|
+
sys.exit(10)
|
|
97
|
+
ui.ok(f"manifest valid; pinned to {manifest.upstream.pinned_commit}")
|
|
98
|
+
|
|
99
|
+
|
|
100
|
+
@main.command()
|
|
101
|
+
@click.argument("profile", nargs=-1)
|
|
102
|
+
@click.option("--yes", is_flag=True, help="Skip confirmation.")
|
|
103
|
+
@click.option("--backup", is_flag=True, help="Export profile before deleting.")
|
|
104
|
+
def reset(profile: tuple[str, ...], yes: bool, backup: bool) -> None:
|
|
105
|
+
"""Remove profiles created by this kit (never touches default ~/.hermes/)."""
|
|
106
|
+
manifest = _load()
|
|
107
|
+
names = list(profile) or [p.name for p in manifest.profiles]
|
|
108
|
+
if not yes:
|
|
109
|
+
click.confirm(f"Really delete profiles: {', '.join(names)}?", abort=True)
|
|
110
|
+
from hpk import hermes as _h
|
|
111
|
+
|
|
112
|
+
for n in names:
|
|
113
|
+
if backup:
|
|
114
|
+
_h.run_raw(["hermes", "profile", "export", n])
|
|
115
|
+
_h.run_raw(["hermes", "profile", "delete", n, "--yes"])
|
|
116
|
+
ui.ok(f"deleted {n}")
|
|
117
|
+
|
|
118
|
+
|
|
119
|
+
@main.group()
|
|
120
|
+
def plugin() -> None:
|
|
121
|
+
"""List, enable, or disable manifest-declared recommended plugins."""
|
|
122
|
+
|
|
123
|
+
|
|
124
|
+
@plugin.command("list")
|
|
125
|
+
def plugin_list() -> None:
|
|
126
|
+
manifest = _load()
|
|
127
|
+
for p in manifest.profiles:
|
|
128
|
+
ids = [rp.id for rp in p.recommended_plugins]
|
|
129
|
+
ui.console.print(f" {p.name}: {ids or '(none)'}")
|
|
130
|
+
|
|
131
|
+
|
|
132
|
+
@plugin.command("enable")
|
|
133
|
+
@click.argument("profile")
|
|
134
|
+
@click.argument("plugin_id")
|
|
135
|
+
def plugin_enable(profile: str, plugin_id: str) -> None:
|
|
136
|
+
manifest = _load()
|
|
137
|
+
plugins_catalog = manifest.plugins
|
|
138
|
+
if plugin_id not in plugins_catalog:
|
|
139
|
+
ui.err(f"unknown plugin: {plugin_id}")
|
|
140
|
+
sys.exit(40)
|
|
141
|
+
from hpk import plugins as _p
|
|
142
|
+
|
|
143
|
+
_p.run_plugin(plugins_catalog[plugin_id], profile=profile)
|
|
144
|
+
ui.ok(f"enabled {plugin_id} for {profile}")
|
|
145
|
+
|
|
146
|
+
|
|
147
|
+
@plugin.command("disable")
|
|
148
|
+
@click.argument("profile")
|
|
149
|
+
@click.argument("plugin_id")
|
|
150
|
+
def plugin_disable(profile: str, plugin_id: str) -> None:
|
|
151
|
+
ui.warn(f"manual disable required for {plugin_id} on {profile}; see plugin docs")
|
|
152
|
+
|
|
153
|
+
|
|
154
|
+
@main.command()
|
|
155
|
+
@click.option(
|
|
156
|
+
"--upstream",
|
|
157
|
+
type=click.Path(exists=True, file_okay=False, path_type=Path),
|
|
158
|
+
help="Path to a local hermes-agent clone. Without it, sync prints guidance and exits.",
|
|
159
|
+
)
|
|
160
|
+
@click.option("--dry-run", is_flag=True, help="Run --check mode (no writes).")
|
|
161
|
+
def sync(upstream: Path | None, dry_run: bool) -> None:
|
|
162
|
+
"""Local upstream-drift check (CI does it daily). Requires an upstream clone."""
|
|
163
|
+
import subprocess as _sp
|
|
164
|
+
|
|
165
|
+
if upstream is None:
|
|
166
|
+
ui.warn("hpk sync needs --upstream PATH (a local hermes-agent clone).")
|
|
167
|
+
ui.warn("CI's daily upstream-sync workflow does this automatically.")
|
|
168
|
+
sys.exit(0)
|
|
169
|
+
cmd = [sys.executable, "scripts/regen_docs.py", "--upstream", str(upstream)]
|
|
170
|
+
if dry_run:
|
|
171
|
+
cmd.append("--check")
|
|
172
|
+
r = _sp.run(cmd)
|
|
173
|
+
sys.exit(50 if r.returncode else 0)
|
|
174
|
+
|
|
175
|
+
|
|
176
|
+
main.add_command(verify_cmd, name="verify")
|
|
File without changes
|