Files
wehub-resource-sync 09e9f3545f
Test / Code Quality (push) Has been cancelled
Test / Test (macos-latest, Python 3.10) (push) Has been cancelled
Test / Test (macos-latest, Python 3.11) (push) Has been cancelled
Test / Test (macos-latest, Python 3.12) (push) Has been cancelled
Test / Test (macos-latest, Python 3.13) (push) Has been cancelled
Test / Test (macos-latest, Python 3.14) (push) Has been cancelled
Test / Test (ubuntu-latest, Python 3.10) (push) Has been cancelled
Test / Test (ubuntu-latest, Python 3.11) (push) Has been cancelled
Test / Test (ubuntu-latest, Python 3.12) (push) Has been cancelled
Test / Test (ubuntu-latest, Python 3.13) (push) Has been cancelled
Test / Test (ubuntu-latest, Python 3.14) (push) Has been cancelled
Test / Test (windows-latest, Python 3.10) (push) Has been cancelled
Test / Test (windows-latest, Python 3.11) (push) Has been cancelled
Test / Test (windows-latest, Python 3.12) (push) Has been cancelled
Test / Test (windows-latest, Python 3.13) (push) Has been cancelled
Test / Test (windows-latest, Python 3.14) (push) Has been cancelled
CodeQL / Analyze (push) Has been cancelled
dependency-audit / pip-audit (push) Has been cancelled
chore: import upstream snapshot with attribution
2026-07-13 13:30:13 +08:00

109 lines
4.6 KiB
Python

"""Canonical :class:`NotebookLMClient` shell construction helper for tests."""
from __future__ import annotations
from collections.abc import Awaitable, Callable
from pathlib import Path
from typing import TYPE_CHECKING, Any
import httpx
from notebooklm._client_assembly import _assemble_client
from notebooklm._runtime.config import (
DEFAULT_CHAT_RESPONSE_MAX_BYTES,
DEFAULT_CONNECT_TIMEOUT,
DEFAULT_KEEPALIVE_MIN_INTERVAL,
DEFAULT_MAX_CONCURRENT_RPCS,
DEFAULT_MAX_CONCURRENT_UPLOADS,
DEFAULT_TIMEOUT,
)
from notebooklm._runtime.lifecycle import CookieRotator, CookieSaver
from notebooklm.auth import AuthTokens
from notebooklm.client import NotebookLMClient
from notebooklm.types import RpcTelemetryEvent
if TYPE_CHECKING:
from notebooklm.types import ConnectionLimits
def build_client_shell_for_tests(
auth: AuthTokens,
timeout: float = DEFAULT_TIMEOUT,
connect_timeout: float = DEFAULT_CONNECT_TIMEOUT,
refresh_callback: Callable[[], Awaitable[AuthTokens]] | None = None,
refresh_retry_delay: float = 0.2,
keepalive: float | None = None,
keepalive_min_interval: float = DEFAULT_KEEPALIVE_MIN_INTERVAL,
keepalive_storage_path: Path | None = None,
rate_limit_max_retries: int = 3,
server_error_max_retries: int = 3,
limits: ConnectionLimits | None = None,
max_concurrent_uploads: int | None = DEFAULT_MAX_CONCURRENT_UPLOADS,
max_concurrent_rpcs: int | None = DEFAULT_MAX_CONCURRENT_RPCS,
on_rpc_event: Callable[[RpcTelemetryEvent], object] | None = None,
cookie_saver: CookieSaver | None = None,
cookie_rotator: CookieRotator | None = None,
chat_response_max_bytes: int | None = DEFAULT_CHAT_RESPONSE_MAX_BYTES,
*,
decode_response: Callable[..., Any] | None = None,
sleep: Callable[[float], Awaitable[Any]] | None = None,
is_auth_error: Callable[[Exception], bool] | None = None,
async_client_factory: Callable[..., httpx.AsyncClient] | None = None,
) -> NotebookLMClient:
"""Build a client shell through the production assembly seam.
The helper preserves the historical test-only seam kwargs without adding
them to :class:`NotebookLMClient`'s public constructor: it creates an
uninitialized instance and runs the same
:func:`notebooklm._client_assembly._assemble_client` function that
``NotebookLMClient.__init__`` delegates to, forwarding the seam kwargs
that only exist on the assembly function.
Because the wiring is the production function itself, a constructor
refactor can no longer strand this factory the way issues #1196
(open-time upload-semaphore loop reset needed ``_source_uploader``)
and #1225 (open-time ChatAPI conversation-lock reset needed ``chat``)
did when this helper still hand-wired private attributes against
``NotebookLMClient.__new__``. The shell therefore carries the full
production attribute surface (feature APIs included) — pinned by
``tests/_guardrails/test_client_factory_parity.py``.
Shell-specific defaults (unchanged from the historical helper):
- ``refresh_callback=None`` — no auth-refresh coordination unless a
test injects one (production wires ``client.refresh_auth``).
- ``keepalive_storage_path`` — passed through verbatim, bypassing the
production canonicalization (``expanduser().resolve()``) of
``auth.storage_path``; an explicit ``None`` still falls through to
``compose_client_internals``' own raw ``auth.storage_path``
fallback, as it always did.
- The client is returned **unopened**: loop binding still happens at
``open()`` time (via ``__aenter__``), exactly as in production.
"""
client = NotebookLMClient.__new__(NotebookLMClient)
_assemble_client(
client,
auth=auth,
timeout=timeout,
connect_timeout=connect_timeout,
refresh_callback=refresh_callback,
refresh_retry_delay=refresh_retry_delay,
keepalive=keepalive,
keepalive_min_interval=keepalive_min_interval,
keepalive_storage_path=keepalive_storage_path,
rate_limit_max_retries=rate_limit_max_retries,
server_error_max_retries=server_error_max_retries,
limits=limits,
max_concurrent_uploads=max_concurrent_uploads,
max_concurrent_rpcs=max_concurrent_rpcs,
on_rpc_event=on_rpc_event,
cookie_saver=cookie_saver,
cookie_rotator=cookie_rotator,
chat_response_max_bytes=chat_response_max_bytes,
decode_response=decode_response,
sleep=sleep,
is_auth_error=is_auth_error,
async_client_factory=async_client_factory,
)
return client