fix(gateway): preserve case-sensitive chat IDs in DeliveryTarget.parse
Fixes NousResearch/hermes-agent#11768 Root cause: target.strip().lower() was lowercasing the entire target string, corrupting case-sensitive chat IDs like Slack C123ABC and Matrix !RoomABC. Fix: Only lowercase the platform prefix for case-insensitive matching; preserve the original case for chat_id and thread_id values.
This commit is contained in:
parent
2b3923ff13
commit
5cdc39e29a
@ -53,9 +53,10 @@ class DeliveryTarget:
|
||||
- "telegram" → Telegram home channel
|
||||
- "telegram:123456" → specific Telegram chat
|
||||
"""
|
||||
target = target.strip().lower()
|
||||
target_stripped = target.strip()
|
||||
target_lower = target_stripped.lower()
|
||||
|
||||
if target == "origin":
|
||||
if target_lower == "origin":
|
||||
if origin:
|
||||
return cls(
|
||||
platform=origin.platform,
|
||||
@ -67,13 +68,14 @@ class DeliveryTarget:
|
||||
# Fallback to local if no origin
|
||||
return cls(platform=Platform.LOCAL, is_origin=True)
|
||||
|
||||
if target == "local":
|
||||
if target_lower == "local":
|
||||
return cls(platform=Platform.LOCAL)
|
||||
|
||||
# Check for platform:chat_id or platform:chat_id:thread_id format
|
||||
if ":" in target:
|
||||
parts = target.split(":", 2)
|
||||
platform_str = parts[0]
|
||||
# Use the original case for chat_id/thread_id to preserve case-sensitive IDs
|
||||
if ":" in target_stripped:
|
||||
parts = target_stripped.split(":", 2)
|
||||
platform_str = parts[0].lower() # Platform names are case-insensitive
|
||||
chat_id = parts[1] if len(parts) > 1 else None
|
||||
thread_id = parts[2] if len(parts) > 2 else None
|
||||
try:
|
||||
@ -85,7 +87,7 @@ class DeliveryTarget:
|
||||
|
||||
# Just a platform name (use home channel)
|
||||
try:
|
||||
platform = Platform(target)
|
||||
platform = Platform(target_lower)
|
||||
return cls(platform=platform)
|
||||
except ValueError:
|
||||
# Unknown platform, treat as local
|
||||
|
||||
@ -65,4 +65,62 @@ class TestTargetToStringRoundtrip:
|
||||
assert reparsed.chat_id == "999"
|
||||
|
||||
|
||||
class TestCaseSensitiveChatIdParsing:
|
||||
"""Test that chat IDs preserve their original case (issue #11768)."""
|
||||
|
||||
def test_slack_uppercase_chat_id_preserved(self):
|
||||
"""Slack channel IDs like C123ABC should preserve case."""
|
||||
target = DeliveryTarget.parse("slack:C123ABC")
|
||||
assert target.platform == Platform.SLACK
|
||||
assert target.chat_id == "C123ABC" # Should NOT be lowercased to c123abc
|
||||
assert target.is_explicit is True
|
||||
|
||||
def test_slack_chat_id_with_thread_preserved(self):
|
||||
"""Slack channel:thread IDs should preserve case."""
|
||||
target = DeliveryTarget.parse("slack:C123ABC:thread123")
|
||||
assert target.platform == Platform.SLACK
|
||||
assert target.chat_id == "C123ABC"
|
||||
assert target.thread_id == "thread123"
|
||||
|
||||
def test_matrix_room_id_preserved(self):
|
||||
"""Matrix room IDs like !RoomABC:example.org should preserve case.
|
||||
|
||||
Note: Matrix room IDs contain colons (e.g., !RoomABC:example.org).
|
||||
Due to the platform:chat_id:thread_id format, these are parsed as
|
||||
chat_id=!RoomABC and thread_id=example.org. This is a known limitation
|
||||
of the current format. The fix preserves case but doesn't change the
|
||||
parsing structure.
|
||||
"""
|
||||
target = DeliveryTarget.parse("matrix:!RoomABC:example.org")
|
||||
assert target.platform == Platform.MATRIX
|
||||
# The room ID is split at the first colon after the platform prefix
|
||||
# This is a format limitation - the case is preserved but the structure is split
|
||||
assert target.chat_id == "!RoomABC"
|
||||
assert target.thread_id == "example.org"
|
||||
|
||||
def test_mixed_case_chat_id_roundtrip(self):
|
||||
"""Mixed-case chat IDs should survive parse-to_string roundtrip."""
|
||||
original = "telegram:ChatId123ABC"
|
||||
target = DeliveryTarget.parse(original)
|
||||
s = target.to_string()
|
||||
reparsed = DeliveryTarget.parse(s)
|
||||
assert reparsed.chat_id == "ChatId123ABC"
|
||||
|
||||
|
||||
class TestPlatformNameCaseInsensitivity:
|
||||
"""Test that platform names are case-insensitive."""
|
||||
|
||||
def test_uppercase_platform_name(self):
|
||||
"""Platform names should be case-insensitive."""
|
||||
target = DeliveryTarget.parse("TELEGRAM:12345")
|
||||
assert target.platform == Platform.TELEGRAM
|
||||
assert target.chat_id == "12345"
|
||||
|
||||
def test_mixed_case_platform_name(self):
|
||||
"""Mixed-case platform names should work."""
|
||||
target = DeliveryTarget.parse("TeleGram:12345")
|
||||
assert target.platform == Platform.TELEGRAM
|
||||
assert target.chat_id == "12345"
|
||||
|
||||
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user