Просмотр исходного кода

Import vendored chattolib absolutely and fail loudly

vendor/ is already on sys.path and chattolib's own modules import each
other absolutely, so the additional relative ".vendor.chattolib" imports
loaded a second, distinct copy of every module — isinstance() checks
across the two copies would silently fail.

A failed import was previously only logged, deferring the failure to a
confusing NameError deep inside the adapter; re-raise instead.
Paul Klumpp 1 неделя назад
Родитель
Сommit
42a4c45c5f
2 измененных файлов с 19 добавлено и 12 удалено
  1. 13 8
      adapter.py
  2. 6 4
      platform_config.py

+ 13 - 8
adapter.py

@@ -52,29 +52,35 @@ from gateway.config import Platform, PlatformConfig
 # Using vendored chattolib from vendor/chattolib/
 # Using vendored chattolib from vendor/chattolib/
 # See vendor_chattolib.sh for how to update the vendored copy
 # See vendor_chattolib.sh for how to update the vendored copy
 
 
+# Absolute imports — vendor/ is on sys.path (see above) and chattolib's own
+# modules import each other absolutely. Mixing in relative ".vendor.chattolib"
+# imports would load a second, distinct copy of every module, so isinstance()
+# checks across the two copies would silently fail.
 try:
 try:
-    # Try vendored chattolib first
-    from .vendor.chattolib.client import (
+    from chattolib.client import (
         ChattoClient,
         ChattoClient,
     )
     )
-    from .vendor.chattolib.exceptions import (
+    from chattolib.exceptions import (
         ChattoAuthError,
         ChattoAuthError,
         ChattoError,
         ChattoError,
     )
     )
-    from .vendor.chattolib.realtime import (
+    from chattolib.realtime import (
         ChattoRealtimeError,
         ChattoRealtimeError,
         ChattoRealtimeCloseError, RealtimeEvent,
         ChattoRealtimeCloseError, RealtimeEvent,
         stream_events
         stream_events
     )
     )
-    from .vendor.chattolib.realtime_types import (
+    from chattolib.realtime_types import (
         MessagePostedPayload
         MessagePostedPayload
     )
     )
-    from .vendor.chattolib.types import (
+    from chattolib.types import (
         PresenceStatus, RoomKind, User
         PresenceStatus, RoomKind, User
     )
     )
 
 
 except ImportError as e:
 except ImportError as e:
+    # Fail loudly: continuing here only defers the failure to a confusing
+    # NameError somewhere deep in the adapter.
     logger.error("Chatto: failed to import vendored chattolib: %s", e)
     logger.error("Chatto: failed to import vendored chattolib: %s", e)
+    raise
 
 
 
 
 from .platform_config import (
 from .platform_config import (
@@ -1254,11 +1260,10 @@ def hermes_check_fn() -> bool:
     """Check if Chatto is configured and dependencies are available.
     """Check if Chatto is configured and dependencies are available.
     Add real logic?! Or just .. there are no dependencies.. always return true. Really. Docs suck."""
     Add real logic?! Or just .. there are no dependencies.. always return true. Really. Docs suck."""
     try:
     try:
-        from .vendor.chattolib.client import ChattoClient
+        import chattolib.client  # noqa: F401 — vendored dependency probe
         return True
         return True
     except ImportError:
     except ImportError:
         return False
         return False
-    return True
 
 
 
 
 # ---------------------------------------------------------------------------
 # ---------------------------------------------------------------------------

+ 6 - 4
platform_config.py

@@ -16,15 +16,17 @@ vendor_dir = current_dir / "vendor"
 if str(vendor_dir) not in sys.path:
 if str(vendor_dir) not in sys.path:
     sys.path.insert(0, str(vendor_dir))
     sys.path.insert(0, str(vendor_dir))
 
 
-from dataclasses import dataclass
 import logging
 import logging
-import os
-from typing import Any, Dict, Optional
+from typing import Any, Dict, Generic, Optional, TypeVar
 
 
 from gateway.config import PlatformConfig
 from gateway.config import PlatformConfig
 import utils
 import utils
 
 
-from .vendor.chattolib.client import ChattoClient
+# Absolute import — the vendor dir is on sys.path (see above) and chattolib's
+# own modules import each other absolutely ("from chattolib.x import y").
+# Importing it relatively as well would load a *second* copy of every module
+# under a different name, so isinstance() checks across the two would fail.
+from chattolib.client import ChattoClient
 
 
 logger = logging.getLogger(__name__)
 logger = logging.getLogger(__name__)