## Summary: NotebookLM Auth Research & Recovery Implementation ### What I Did 1. **Deep code analysis** of the full auth stack: - `core/auth.py` — AuthManager, Profile serialization, `check_auth()` with live/heuristic paths - `utils/cdp.py` — CDP WebSocket protocol, cookie extraction, `run_headless_auth()`, Chrome lifecycle - `core/base.py` — `_refresh_auth_tokens()`, CSRF auto-extraction, `_try_reload_or_headless_auth()` recovery chain - `core/cookie_rotation.py` — `RotateCookies` endpoint call for short-lived `*PSIDTS` cookie refresh - `mcp/tools/auth.py` — `refresh_auth` and `save_auth_tokens` MCP tools - `services/auth.py` — Service layer for auth orchestration 2. **Diagnosed the exact failure mode**: - Chrome headless was running (port 9223) with a valid profile containing 52 cookies - But Google session cookies (`SID`, `HSID`, `SSID`, etc.) had expired and Google redirected to login - `check_auth()` correctly returned `valid=False, reason='network_error: ClientAuthenticationError'` - The `RotateCookies` endpoint returned 401 — the long-lived session was also dead - **Root cause:** The persisted Chrome profile (`Default/Cookies` SQLite) had stale session cookies that no longer authenticate. Headless can't render the interactive login page. 3. **Ran the revive workflow successfully**: - `revive_notebooklm_auth.sh` killed stale Chrome → relaunched → waited for CDP readiness - `notebooklm_refresh.py` connected via CDP → navigated to NotebookLM → extracted 52 fresh cookies + CSRF token + build label → saved to profile - **Auth is now VALID** — confirmed with `check_auth(live=True)` returning `valid=True` 4. **Created comprehensive SOP** at `/opt/ai-os/products/ceo/company_kb/notebooklm_auth_guide.md` (~21KB) covering: - Full architectural breakdown with data flow diagrams - Root cause analysis for the current failure - Optimal strategy: persistent headless Chrome + profile-based auth with cron maintenance - Detailed setup SOP (one-time tunnel + interactive login) - Recovery SOP (automated revive → interactive tunnel → emergency cookie import) - Technical deep-dive of all auth code paths (`check_auth`, `_refresh_auth_tokens`, `run_headless_auth`, CDP communication) - Troubleshooting reference (9 common errors with causes + fixes) - Monitoring & alerting schedule with expected log output 5. **Created recovery infrastructure**: - `/opt/ai-os/products/ceo/scripts/notebooklm_refresh.py` — Primary extraction tool (takes `--port` and `--profile` args, validates, extracts, saves, verifies) - `/opt/ai-os/products/ceo/scripts/revive_notebooklm_auth.sh` — Kill → relaunch → refresh one-shot script - `/opt/ai-os/products/ceo/scripts/auth_refresh.py` — Cron-friendly 6-hourly maintenance (check → rotate → revive if needed → log) - `/opt/ai-os/products/ceo/scripts/check_chrome_alive.sh` — 15-minute health monitor - `/etc/cron.d/notebooklm-auth` — Cron job installed (6h auth refresh + 15min chrome health) ### Key Findings - **Cookies have hierarchical expiry:** `SID`/`HSID`/`SSID`/`APISID`/`SAPISID` (weeks) vs `*PSIDTS`/`SIDCC` (hours-days). The `RotateCookies` endpoint can refresh short-lived ones, but only if the long-lived session is still valid. - **The auth code has multiple recovery layers:** disk reload → headless auth → CSRF auto-refresh on each request. The weakest link is the Chrome profile's `Default/Cookies` SQLite DB going stale after process death. - **Persistent headless Chrome is the right strategy.** Running it continuously keeps cookies fresh via in-browser session management. The cron scripts ensure it stays alive and the CLI profile stays in sync. - **If the Google session itself expires (happens after ~2 weeks or password change), interactive login via SSH tunnel is unavoidable.** The SOP documents this clearly. [NOTE: subagent modified files the parent previously read — re-read before editing: /opt/ai-os/products/ceo/scripts/notebooklm_refresh.py]