mirror of
https://github.com/NousResearch/hermes-agent.git
synced 2026-04-25 00:51:20 +00:00
Merge 5857f5bbd2 into fd10463069
This commit is contained in:
commit
6acfc5d31b
2 changed files with 60 additions and 0 deletions
|
|
@ -1507,6 +1507,38 @@ def _hermes_home_for_target_user(target_home_dir: str) -> str:
|
|||
return str(current_hermes)
|
||||
|
||||
|
||||
def _login_shell_hermes_home(username: str) -> str | None:
|
||||
"""Best-effort lookup of ``HERMES_HOME`` from ``username``'s login shell.
|
||||
|
||||
This helps ``sudo hermes gateway install --system`` preserve a custom
|
||||
``HERMES_HOME`` that exists in the target user's login environment even
|
||||
when sudo sanitizes it out of the root process environment.
|
||||
"""
|
||||
username = (username or "").strip()
|
||||
if not username or username == "root":
|
||||
return None
|
||||
|
||||
try:
|
||||
result = subprocess.run(
|
||||
["su", "-l", username, "-s", "/bin/sh", "-c", 'printf %s "$HERMES_HOME"'],
|
||||
capture_output=True,
|
||||
text=True,
|
||||
check=False,
|
||||
timeout=10,
|
||||
)
|
||||
except (FileNotFoundError, subprocess.TimeoutExpired, PermissionError, OSError):
|
||||
return None
|
||||
|
||||
if result.returncode != 0:
|
||||
return None
|
||||
|
||||
value = (result.stdout or "").strip()
|
||||
if not value:
|
||||
return None
|
||||
|
||||
return str(Path(value).expanduser())
|
||||
|
||||
|
||||
def generate_systemd_unit(system: bool = False, run_as_user: str | None = None) -> str:
|
||||
python_path = get_python_path()
|
||||
working_dir = str(PROJECT_ROOT)
|
||||
|
|
@ -1535,6 +1567,13 @@ def generate_systemd_unit(system: bool = False, run_as_user: str | None = None)
|
|||
if system:
|
||||
username, group_name, home_dir = _system_service_identity(run_as_user)
|
||||
hermes_home = _hermes_home_for_target_user(home_dir)
|
||||
if (
|
||||
not os.getenv("HERMES_HOME", "").strip()
|
||||
and hermes_home == str(Path(home_dir) / ".hermes")
|
||||
):
|
||||
login_shell_home = _login_shell_hermes_home(username)
|
||||
if login_shell_home:
|
||||
hermes_home = login_shell_home
|
||||
profile_arg = _profile_arg(hermes_home)
|
||||
# Remap all paths that may resolve under the calling user's home
|
||||
# (e.g. /root/) to the target user's home so the service can
|
||||
|
|
|
|||
|
|
@ -891,6 +891,27 @@ class TestSystemUnitHermesHome:
|
|||
|
||||
assert 'HERMES_HOME=/opt/hermes-shared' in unit
|
||||
|
||||
def test_system_unit_uses_target_login_shell_hermes_home_when_sudo_drops_env(self, monkeypatch):
|
||||
monkeypatch.setattr(Path, "home", staticmethod(lambda: Path("/root")))
|
||||
monkeypatch.delenv("HERMES_HOME", raising=False)
|
||||
monkeypatch.setattr(
|
||||
gateway_cli, "_system_service_identity",
|
||||
lambda run_as_user=None: ("alice", "alice", "/home/alice"),
|
||||
)
|
||||
monkeypatch.setattr(
|
||||
gateway_cli, "_build_user_local_paths",
|
||||
lambda home, existing: [],
|
||||
)
|
||||
monkeypatch.setattr(
|
||||
gateway_cli,
|
||||
"_login_shell_hermes_home",
|
||||
lambda username: "/srv/hermes-shared",
|
||||
)
|
||||
|
||||
unit = gateway_cli.generate_systemd_unit(system=True, run_as_user="alice")
|
||||
|
||||
assert 'HERMES_HOME=/srv/hermes-shared' in unit
|
||||
|
||||
def test_user_unit_unaffected_by_change(self):
|
||||
# User-scope units should still use the calling user's HERMES_HOME
|
||||
unit = gateway_cli.generate_systemd_unit(system=False)
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue