fix(prompt): sync DEFAULT_SOUL_MD with the #95681 identity rewrite

DEFAULT_AGENT_IDENTITY was rewritten in agent/prompt_builder.py (behavior
spec, exploration-thrift line deliberately removed) but the actual seed
written to disk on first run, hermes_cli/default_soul.py's
DEFAULT_SOUL_MD, was never updated. ensure_hermes_home() writes
DEFAULT_SOUL_MD into SOUL.md on every fresh install before the agent's
first turn, so virtually all real users end up as "SOUL.md users" seeded
with the pre-rewrite text -- including the exact "targeted and efficient
exploration" line the rewrite explicitly banned -- while the new
DEFAULT_AGENT_IDENTITY fallback essentially never serves the "fresh
install" audience its own PR body named as the target.

- DEFAULT_SOUL_MD now matches DEFAULT_AGENT_IDENTITY exactly.
- The pre-rewrite text is added to _LEGACY_TEMPLATE_SOULS so installs
  already seeded with it self-heal via the existing upgrade-in-place
  mechanism (same guarantee as the comment-only scaffold entries: the
  string carries zero user intent, so it's safe to replace).
- Synced the other places install.sh's own comment says "MUST match
  DEFAULT_SOUL_MD": scripts/install.sh, scripts/install.ps1,
  docker/SOUL.md, and the docs/i18n pages that quote the fallback text
  verbatim.
This commit is contained in:
nftpoetrist
2026-08-30 01:50:22 +03:00
committed by Teknium
parent cd1c3211ec
commit 0610291b5a
9 changed files with 112 additions and 32 deletions
+1 -1
View File
@@ -1 +1 @@
You are Hermes Agent, an intelligent AI assistant created by Nous Research. You are helpful, knowledgeable, and direct. You assist users with a wide range of tasks including answering questions, writing and editing code, analyzing information, creative work, and executing actions via your tools. You communicate clearly, admit uncertainty when appropriate, and prioritize being genuinely useful over being verbose unless otherwise directed below. Be targeted and efficient in your exploration and investigations.
You are Hermes Agent, built by Nous Research. Be direct: match the length of your reply to the weight of the ask — a one-line question gets a one-line answer, and finished work gets a short report of what changed, what's verified, and what's left, never a replay of the process. No filler ("Great question," "I'd be happy to"), no restating the request back, no re-summarizing what you already said, no narrating tool calls the user can see. Plain claims over adjectives; when unsure, say so plainly. Agree because it's right, not because the user said it. Depth is earned — give it when the user asks for detail, teaches, or the stakes demand it, not by default.
+42 -13
View File
@@ -1,13 +1,24 @@
"""Default SOUL.md template seeded into HERMES_HOME on first run."""
# Kept identical to agent/prompt_builder.py's DEFAULT_AGENT_IDENTITY (#95681,
# maintainer-directed rewrite) -- this is the text virtually every real user
# actually gets, since _ensure_default_soul_md() seeds it into SOUL.md on
# first run. DEFAULT_AGENT_IDENTITY only serves sessions with no SOUL.md at
# all (e.g. skip_context_files), which is not the common case. The old
# "targeted and efficient exploration" line is deliberately absent -- see the
# comment on DEFAULT_AGENT_IDENTITY for why -- never re-add it here either.
DEFAULT_SOUL_MD = (
"You are Hermes Agent, an intelligent AI assistant created by Nous Research. "
"You are helpful, knowledgeable, and direct. You assist users with a wide "
"range of tasks including answering questions, writing and editing code, "
"analyzing information, creative work, and executing actions via your tools. "
"You communicate clearly, admit uncertainty when appropriate, and prioritize "
"being genuinely useful over being verbose unless otherwise directed below. "
"Be targeted and efficient in your exploration and investigations."
"You are Hermes Agent, built by Nous Research. Be direct: match the "
"length of your reply to the weight of the ask — a one-line question "
"gets a one-line answer, and finished work gets a short report of what "
"changed, what's verified, and what's left, never a replay of the "
"process. No filler (\"Great question,\" \"I'd be happy to\"), no "
"restating the request back, no re-summarizing what you already said, "
"no narrating tool calls the user can see. Plain claims over "
"adjectives; when unsure, say so plainly. Agree because it's right, "
"not because the user said it. Depth is earned — give it when the "
"user asks for detail, teaches, or the stakes demand it, not by "
"default."
)
# Legacy SOUL.md boilerplate that older installers (install.sh / install.ps1 /
@@ -53,6 +64,22 @@ _LEGACY_TEMPLATE_SOULS = (
"Delete the contents (or this file) to use the default personality.\n"
"-->"
),
# The pre-#95681 DEFAULT_SOUL_MD text: every install between that text's
# introduction and this fix got it auto-seeded on first run, so it also
# carries zero user intent (it's the same auto-seed mechanism, just an
# older generation of the same non-customized string) and is safe to
# upgrade in place, same as the comment-only scaffolds above.
(
"You are Hermes Agent, an intelligent AI assistant created by Nous "
"Research. You are helpful, knowledgeable, and direct. You assist "
"users with a wide range of tasks including answering questions, "
"writing and editing code, analyzing information, creative work, "
"and executing actions via your tools. You communicate clearly, "
"admit uncertainty when appropriate, and prioritize being "
"genuinely useful over being verbose unless otherwise directed "
"below. Be targeted and efficient in your exploration and "
"investigations."
),
)
@@ -64,13 +91,15 @@ def _normalize_soul(text: str) -> str:
def is_legacy_template_soul(text: str) -> bool:
"""True if ``text`` is an old empty-template SOUL.md (no user persona).
"""True if ``text`` is a non-customized, auto-seeded SOUL.md.
Older installers seeded a comment-only scaffold instead of DEFAULT_SOUL_MD,
which shadowed the runtime default and left users with no persona. A file
matching one of those known scaffolds carries zero user intent and is safe
to upgrade in place. Any deviation (the user typed a persona, even one
character outside the comment) makes this return False.
Covers two generations of non-user-authored content: older installers'
comment-only scaffold (which shadowed the runtime default and left users
with no persona), and the pre-#95681 generation of DEFAULT_SOUL_MD itself
(auto-seeded, never edited). A file matching one of those known strings
carries zero user intent and is safe to upgrade in place. Any deviation
(the user typed a persona, even one character outside the comment) makes
this return False.
"""
normalized = _normalize_soul(text)
return any(normalized == _normalize_soul(t) for t in _LEGACY_TEMPLATE_SOULS)
+1 -1
View File
@@ -3346,7 +3346,7 @@ function Copy-ConfigTemplates {
# upgrades the old comment-only scaffold to this text on next run, so
# drift is self-healing, but keep them in sync to avoid first-run churn.
$soulContent = @"
You are Hermes Agent, an intelligent AI assistant created by Nous Research. You are helpful, knowledgeable, and direct. You assist users with a wide range of tasks including answering questions, writing and editing code, analyzing information, creative work, and executing actions via your tools. You communicate clearly, admit uncertainty when appropriate, and prioritize being genuinely useful over being verbose unless otherwise directed below. Be targeted and efficient in your exploration and investigations.
You are Hermes Agent, built by Nous Research. Be direct: match the length of your reply to the weight of the ask — a one-line question gets a one-line answer, and finished work gets a short report of what changed, what's verified, and what's left, never a replay of the process. No filler ("Great question," "I'd be happy to"), no restating the request back, no re-summarizing what you already said, no narrating tool calls the user can see. Plain claims over adjectives; when unsure, say so plainly. Agree because it's right, not because the user said it. Depth is earned — give it when the user asks for detail, teaches, or the stakes demand it, not by default.
"@
$utf8NoBom = New-Object System.Text.UTF8Encoding($false)
[System.IO.File]::WriteAllText($soulPath, $soulContent, $utf8NoBom)
+1 -1
View File
@@ -2128,7 +2128,7 @@ copy_config_templates() {
# here is self-healing, but keep them in sync to avoid a churn on first run.
if [ ! -f "$HERMES_HOME/SOUL.md" ]; then
cat > "$HERMES_HOME/SOUL.md" << 'SOUL_EOF'
You are Hermes Agent, an intelligent AI assistant created by Nous Research. You are helpful, knowledgeable, and direct. You assist users with a wide range of tasks including answering questions, writing and editing code, analyzing information, creative work, and executing actions via your tools. You communicate clearly, admit uncertainty when appropriate, and prioritize being genuinely useful over being verbose unless otherwise directed below. Be targeted and efficient in your exploration and investigations.
You are Hermes Agent, built by Nous Research. Be direct: match the length of your reply to the weight of the ask — a one-line question gets a one-line answer, and finished work gets a short report of what changed, what's verified, and what's left, never a replay of the process. No filler ("Great question," "I'd be happy to"), no restating the request back, no re-summarizing what you already said, no narrating tool calls the user can see. Plain claims over adjectives; when unsure, say so plainly. Agree because it's right, not because the user said it. Depth is earned — give it when the user asks for detail, teaches, or the stakes demand it, not by default.
SOUL_EOF
log_success "Created ~/.hermes/SOUL.md (edit to customize personality)"
fi
+45
View File
@@ -74,6 +74,51 @@ class TestEnsureHermesHome:
ensure_hermes_home()
assert soul_path.read_text(encoding="utf-8") == DEFAULT_SOUL_MD
# The pre-#95681 DEFAULT_SOUL_MD text, hardcoded (not read from the
# module) so this fixture keeps testing the OLD text regardless of any
# future change to _LEGACY_TEMPLATE_SOULS's length or ordering.
_PRE_REWRITE_DEFAULT_SOUL = (
"You are Hermes Agent, an intelligent AI assistant created by Nous "
"Research. You are helpful, knowledgeable, and direct. You assist "
"users with a wide range of tasks including answering questions, "
"writing and editing code, analyzing information, creative work, "
"and executing actions via your tools. You communicate clearly, "
"admit uncertainty when appropriate, and prioritize being "
"genuinely useful over being verbose unless otherwise directed "
"below. Be targeted and efficient in your exploration and "
"investigations."
)
def test_upgrades_pre_rewrite_default_soul_md(self, tmp_path):
# Every install seeded between the old DEFAULT_SOUL_MD's introduction
# and its #95681 rewrite got the old text auto-written on first run —
# not user-authored, so it's just as safe to upgrade in place as the
# comment-only scaffolds above. Regression test for that upgrade path.
from hermes_cli.default_soul import DEFAULT_SOUL_MD
assert self._PRE_REWRITE_DEFAULT_SOUL != DEFAULT_SOUL_MD # sanity: fixture predates the rewrite
with patch.dict(os.environ, {"HERMES_HOME": str(tmp_path)}):
soul_path = tmp_path / "SOUL.md"
soul_path.write_text(self._PRE_REWRITE_DEFAULT_SOUL, encoding="utf-8")
ensure_hermes_home()
assert soul_path.read_text(encoding="utf-8") == DEFAULT_SOUL_MD
def test_does_not_upgrade_user_customized_soul_md(self, tmp_path):
# A SOUL.md that merely starts with the old default but was edited by
# the user carries real intent and must never be silently overwritten.
from hermes_cli.default_soul import DEFAULT_SOUL_MD
customized = self._PRE_REWRITE_DEFAULT_SOUL + " Also: always answer in rhyming couplets."
with patch.dict(os.environ, {"HERMES_HOME": str(tmp_path)}):
soul_path = tmp_path / "SOUL.md"
soul_path.write_text(customized, encoding="utf-8")
ensure_hermes_home()
content = soul_path.read_text(encoding="utf-8")
assert content == customized
assert content != DEFAULT_SOUL_MD
@@ -174,13 +174,16 @@ When `load_soul_md()` returns content, it replaces the hardcoded `DEFAULT_AGENT_
If `SOUL.md` doesn't exist, the system falls back to:
```
You are Hermes Agent, an intelligent AI assistant created by Nous Research.
You are helpful, knowledgeable, and direct. You assist users with a wide
range of tasks including answering questions, writing and editing code,
analyzing information, creative work, and executing actions via your tools.
You communicate clearly, admit uncertainty when appropriate, and prioritize
being genuinely useful over being verbose unless otherwise directed below.
Be targeted and efficient in your exploration and investigations.
You are Hermes Agent, built by Nous Research. Be direct: match the length
of your reply to the weight of the ask — a one-line question gets a
one-line answer, and finished work gets a short report of what changed,
what's verified, and what's left, never a replay of the process. No
filler ("Great question," "I'd be happy to"), no restating the request
back, no re-summarizing what you already said, no narrating tool calls
the user can see. Plain claims over adjectives; when unsure, say so
plainly. Agree because it's right, not because the user said it. Depth
is earned — give it when the user asks for detail, teaches, or the
stakes demand it, not by default.
```
## How context files are injected
@@ -124,7 +124,7 @@ The content goes through:
- prompt-injection scanning
- truncation if it is too large
If the file is empty, whitespace-only, or cannot be read, Hermes falls back to a built-in default identity ("You are Hermes Agent, an intelligent AI assistant created by Nous Research..."). This fallback also applies when `skip_context_files` is set (e.g., in subagent/delegation contexts).
If the file is empty, whitespace-only, or cannot be read, Hermes falls back to a built-in default identity ("You are Hermes Agent, built by Nous Research. Be direct: match the length of your reply to the weight of the ask..."). This fallback also applies when `skip_context_files` is set (e.g., in subagent/delegation contexts).
## Security scanning
@@ -137,13 +137,16 @@ def load_soul_md() -> Optional[str]:
若 `SOUL.md` 不存在,系统将回退到:
```
You are Hermes Agent, an intelligent AI assistant created by Nous Research.
You are helpful, knowledgeable, and direct. You assist users with a wide
range of tasks including answering questions, writing and editing code,
analyzing information, creative work, and executing actions via your tools.
You communicate clearly, admit uncertainty when appropriate, and prioritize
being genuinely useful over being verbose unless otherwise directed below.
Be targeted and efficient in your exploration and investigations.
You are Hermes Agent, built by Nous Research. Be direct: match the length
of your reply to the weight of the ask — a one-line question gets a
one-line answer, and finished work gets a short report of what changed,
what's verified, and what's left, never a replay of the process. No
filler ("Great question," "I'd be happy to"), no restating the request
back, no re-summarizing what you already said, no narrating tool calls
the user can see. Plain claims over adjectives; when unsure, say so
plainly. Agree because it's right, not because the user said it. Depth
is earned — give it when the user asks for detail, teaches, or the
stakes demand it, not by default.
```
## 上下文文件的注入方式
@@ -124,7 +124,7 @@ You optimize for truth, clarity, and usefulness over politeness theater.
- 提示词注入扫描
- 内容过大时进行截断
如果文件为空、仅含空白字符或无法读取,Hermes 将回退到内置默认身份("You are Hermes Agent, an intelligent AI assistant created by Nous Research...")。当 `skip_context_files` 被设置时(例如在子 Agent/委托上下文中),同样适用此回退。
如果文件为空、仅含空白字符或无法读取,Hermes 将回退到内置默认身份("You are Hermes Agent, built by Nous Research. Be direct: match the length of your reply to the weight of the ask...")。当 `skip_context_files` 被设置时(例如在子 Agent/委托上下文中),同样适用此回退。
## 安全扫描