feat: add discord.reactions config option to disable message reactions (#4199)

Adds a 'reactions' key under the discord config section (default: true).
When set to false, the bot no longer adds 👀// reactions to messages
during processing. The config maps to DISCORD_REACTIONS env var following
the same pattern as require_mention and auto_thread.

Files changed:
- hermes_cli/config.py: Add reactions default to DEFAULT_CONFIG
- gateway/config.py: Map discord.reactions to DISCORD_REACTIONS env var
- gateway/platforms/discord.py: Gate on_processing_start/complete hooks
- tests/gateway/test_discord_reactions.py: 3 new tests for config gate
This commit is contained in:
Teknium
2026-03-31 01:24:48 -07:00
committed by GitHub
parent 491e79bca9
commit ff78ad4c81
4 changed files with 75 additions and 0 deletions

View File

@@ -168,3 +168,67 @@ async def test_reaction_helper_failures_do_not_break_message_flow(adapter):
await adapter._process_message_background(event, build_session_key(event.source))
adapter.send.assert_awaited_once()
@pytest.mark.asyncio
async def test_reactions_disabled_via_env(adapter, monkeypatch):
"""When DISCORD_REACTIONS=false, no reactions should be added."""
monkeypatch.setenv("DISCORD_REACTIONS", "false")
raw_message = SimpleNamespace(
add_reaction=AsyncMock(),
remove_reaction=AsyncMock(),
)
async def handler(_event):
await asyncio.sleep(0)
return "ack"
async def hold_typing(_chat_id, interval=2.0, metadata=None):
await asyncio.Event().wait()
adapter.set_message_handler(handler)
adapter.send = AsyncMock(return_value=SendResult(success=True, message_id="999"))
adapter._keep_typing = hold_typing
event = _make_event("4", raw_message)
await adapter._process_message_background(event, build_session_key(event.source))
raw_message.add_reaction.assert_not_awaited()
raw_message.remove_reaction.assert_not_awaited()
# Response should still be sent
adapter.send.assert_awaited_once()
@pytest.mark.asyncio
async def test_reactions_disabled_via_env_zero(adapter, monkeypatch):
"""DISCORD_REACTIONS=0 should also disable reactions."""
monkeypatch.setenv("DISCORD_REACTIONS", "0")
raw_message = SimpleNamespace(
add_reaction=AsyncMock(),
remove_reaction=AsyncMock(),
)
event = _make_event("5", raw_message)
await adapter.on_processing_start(event)
await adapter.on_processing_complete(event, success=True)
raw_message.add_reaction.assert_not_awaited()
raw_message.remove_reaction.assert_not_awaited()
@pytest.mark.asyncio
async def test_reactions_enabled_by_default(adapter, monkeypatch):
"""When DISCORD_REACTIONS is unset, reactions should still work (default: true)."""
monkeypatch.delenv("DISCORD_REACTIONS", raising=False)
raw_message = SimpleNamespace(
add_reaction=AsyncMock(),
remove_reaction=AsyncMock(),
)
event = _make_event("6", raw_message)
await adapter.on_processing_start(event)
raw_message.add_reaction.assert_awaited_once_with("👀")