Spaces:
Paused
Paused
| """Tests for /personality none — clearing personality overlay.""" | |
| import pytest | |
| from unittest.mock import MagicMock, patch, mock_open | |
| import yaml | |
| # ── CLI tests ────────────────────────────────────────────────────────────── | |
| class TestCLIPersonalityNone: | |
| def _make_cli(self, personalities=None): | |
| from cli import HermesCLI | |
| cli = HermesCLI.__new__(HermesCLI) | |
| cli.personalities = personalities or { | |
| "helpful": "You are helpful.", | |
| "concise": "You are concise.", | |
| } | |
| cli.system_prompt = "You are kawaii~" | |
| cli.agent = MagicMock() | |
| cli.console = MagicMock() | |
| return cli | |
| def test_none_clears_system_prompt(self): | |
| cli = self._make_cli() | |
| with patch("cli.save_config_value", return_value=True): | |
| cli._handle_personality_command("/personality none") | |
| assert cli.system_prompt == "" | |
| def test_default_clears_system_prompt(self): | |
| cli = self._make_cli() | |
| with patch("cli.save_config_value", return_value=True): | |
| cli._handle_personality_command("/personality default") | |
| assert cli.system_prompt == "" | |
| def test_neutral_clears_system_prompt(self): | |
| cli = self._make_cli() | |
| with patch("cli.save_config_value", return_value=True): | |
| cli._handle_personality_command("/personality neutral") | |
| assert cli.system_prompt == "" | |
| def test_none_forces_agent_reinit(self): | |
| cli = self._make_cli() | |
| with patch("cli.save_config_value", return_value=True): | |
| cli._handle_personality_command("/personality none") | |
| assert cli.agent is None | |
| def test_none_saves_to_config(self): | |
| cli = self._make_cli() | |
| with patch("cli.save_config_value", return_value=True) as mock_save: | |
| cli._handle_personality_command("/personality none") | |
| mock_save.assert_called_once_with("agent.system_prompt", "") | |
| def test_known_personality_still_works(self): | |
| cli = self._make_cli() | |
| with patch("cli.save_config_value", return_value=True): | |
| cli._handle_personality_command("/personality helpful") | |
| assert cli.system_prompt == "You are helpful." | |
| def test_unknown_personality_shows_none_in_available(self, capsys): | |
| cli = self._make_cli() | |
| cli._handle_personality_command("/personality nonexistent") | |
| output = capsys.readouterr().out | |
| assert "none" in output.lower() | |
| def test_list_shows_none_option(self): | |
| cli = self._make_cli() | |
| with patch("builtins.print") as mock_print: | |
| cli._handle_personality_command("/personality") | |
| output = " ".join(str(c) for c in mock_print.call_args_list) | |
| assert "none" in output.lower() | |
| # ── Gateway tests ────────────────────────────────────────────────────────── | |
| class TestGatewayPersonalityNone: | |
| def _make_event(self, args=""): | |
| event = MagicMock() | |
| event.get_command.return_value = "personality" | |
| event.get_command_args.return_value = args | |
| return event | |
| def _make_runner(self, personalities=None): | |
| from gateway.run import GatewayRunner | |
| runner = GatewayRunner.__new__(GatewayRunner) | |
| runner._ephemeral_system_prompt = "You are kawaii~" | |
| runner.config = { | |
| "agent": { | |
| "personalities": personalities or {"helpful": "You are helpful."} | |
| } | |
| } | |
| return runner | |
| async def test_none_clears_ephemeral_prompt(self, tmp_path): | |
| runner = self._make_runner() | |
| config_data = {"agent": {"personalities": {"helpful": "You are helpful."}, "system_prompt": "kawaii"}} | |
| config_file = tmp_path / "config.yaml" | |
| config_file.write_text(yaml.dump(config_data)) | |
| with patch("gateway.run._hermes_home", tmp_path): | |
| event = self._make_event("none") | |
| result = await runner._handle_personality_command(event) | |
| assert runner._ephemeral_system_prompt == "" | |
| assert "cleared" in result.lower() | |
| async def test_default_clears_ephemeral_prompt(self, tmp_path): | |
| runner = self._make_runner() | |
| config_data = {"agent": {"personalities": {"helpful": "You are helpful."}}} | |
| config_file = tmp_path / "config.yaml" | |
| config_file.write_text(yaml.dump(config_data)) | |
| with patch("gateway.run._hermes_home", tmp_path): | |
| event = self._make_event("default") | |
| result = await runner._handle_personality_command(event) | |
| assert runner._ephemeral_system_prompt == "" | |
| async def test_list_includes_none(self, tmp_path): | |
| runner = self._make_runner() | |
| config_data = {"agent": {"personalities": {"helpful": "You are helpful."}}} | |
| config_file = tmp_path / "config.yaml" | |
| config_file.write_text(yaml.dump(config_data)) | |
| with patch("gateway.run._hermes_home", tmp_path): | |
| event = self._make_event("") | |
| result = await runner._handle_personality_command(event) | |
| assert "none" in result.lower() | |
| async def test_unknown_shows_none_in_available(self, tmp_path): | |
| runner = self._make_runner() | |
| config_data = {"agent": {"personalities": {"helpful": "You are helpful."}}} | |
| config_file = tmp_path / "config.yaml" | |
| config_file.write_text(yaml.dump(config_data)) | |
| with patch("gateway.run._hermes_home", tmp_path): | |
| event = self._make_event("nonexistent") | |
| result = await runner._handle_personality_command(event) | |
| assert "none" in result.lower() | |
| class TestPersonalityDictFormat: | |
| """Test dict-format custom personalities with description, tone, style.""" | |
| def _make_cli(self, personalities): | |
| from cli import HermesCLI | |
| cli = HermesCLI.__new__(HermesCLI) | |
| cli.personalities = personalities | |
| cli.system_prompt = "" | |
| cli.agent = None | |
| cli.console = MagicMock() | |
| return cli | |
| def test_dict_personality_uses_system_prompt(self): | |
| cli = self._make_cli({ | |
| "coder": { | |
| "description": "Expert programmer", | |
| "system_prompt": "You are an expert programmer.", | |
| "tone": "technical", | |
| "style": "concise", | |
| } | |
| }) | |
| with patch("cli.save_config_value", return_value=True): | |
| cli._handle_personality_command("/personality coder") | |
| assert "You are an expert programmer." in cli.system_prompt | |
| def test_dict_personality_includes_tone(self): | |
| cli = self._make_cli({ | |
| "coder": { | |
| "system_prompt": "You are an expert programmer.", | |
| "tone": "technical and precise", | |
| } | |
| }) | |
| with patch("cli.save_config_value", return_value=True): | |
| cli._handle_personality_command("/personality coder") | |
| assert "Tone: technical and precise" in cli.system_prompt | |
| def test_dict_personality_includes_style(self): | |
| cli = self._make_cli({ | |
| "coder": { | |
| "system_prompt": "You are an expert programmer.", | |
| "style": "use code examples", | |
| } | |
| }) | |
| with patch("cli.save_config_value", return_value=True): | |
| cli._handle_personality_command("/personality coder") | |
| assert "Style: use code examples" in cli.system_prompt | |
| def test_string_personality_still_works(self): | |
| cli = self._make_cli({"helper": "You are helpful."}) | |
| with patch("cli.save_config_value", return_value=True): | |
| cli._handle_personality_command("/personality helper") | |
| assert cli.system_prompt == "You are helpful." | |
| def test_resolve_prompt_dict_no_tone_no_style(self): | |
| from cli import HermesCLI | |
| result = HermesCLI._resolve_personality_prompt({ | |
| "description": "A helper", | |
| "system_prompt": "You are helpful.", | |
| }) | |
| assert result == "You are helpful." | |
| def test_resolve_prompt_string(self): | |
| from cli import HermesCLI | |
| result = HermesCLI._resolve_personality_prompt("You are helpful.") | |
| assert result == "You are helpful." | |