Agent Skills

Use this skill to query your Google NotebookLM notebooks directly from Claude Code for source-grounded, citation-backed answers from Gemini. Browser automation, library management, persistent auth. Drastically reduced hallucinations through document-only responses.

Install

npx skills add https://github.com/magicseek/nblm --skill nblm
SKILL.md

NotebookLM Quick Commands

Query Google NotebookLM for source-grounded, citation-backed answers.

Environment

All dependencies and authentication are handled automatically by run.py:

  • First run creates .venv and installs Python/Node.js dependencies
  • If Google auth is missing or expired, a browser window opens automatically
  • No manual pre-flight steps required

Usage

/nblm <command> [args]

Commands

Notebook Management

Command Description
login Authenticate with Google
status Show auth and library status
accounts List all Google accounts
accounts add Add a new Google account
accounts switch <id> Switch active account (by index or email)
accounts remove <id> Remove a Google account
accounts use <id> Set agent-specific active account (OpenClaw isolation)
accounts clear Clear agent-specific account override
local List notebooks in local library
remote List all notebooks from NotebookLM API
create <name> Create a new notebook
delete [--id ID] Delete a notebook
rename <name> [--id ID] Rename a notebook
summary [--id ID] Get AI-generated summary
describe [--id ID] Get description and suggested topics
add <url-or-id> Add notebook to local library (auto-detects URL vs notebook ID)
activate <id> Set active notebook

Source Management

Command Description
sources [--id ID] List sources in notebook
upload <file> Upload a single file
upload <folder> Sync a folder of files to NotebookLM
upload-zlib <url> Download from Z-Library and upload
upload-url <url> Add URL as source
upload-youtube <url> Add YouTube video as source
upload-text <title> [--content TEXT] Add text as source
source-text <source-id> Get full indexed text
source-guide <source-id> Get AI summary and keywords
source-rename <source-id> <name> Rename a source
source-refresh <source-id> Re-fetch URL content
source-delete <source-id> Delete a source

Upload options:

  • --use-active - Upload to the currently active notebook
  • --create-new - Create a new notebook named after the file/folder
  • --notebook-id <id> - Upload to a specific notebook
  • --dry-run - Show sync plan without executing (folder sync)
  • --rebuild - Force rebuild tracking file (folder sync)

Important: When user runs upload without specifying a target, ASK them first:

"Would you like to upload to the active notebook, or create a new notebook?" Then pass the appropriate flag (--use-active or --create-new).

Chat & Audio/Media

Command Description
ask <question> Query NotebookLM
podcast [--instructions TEXT] Generate audio podcast
podcast-status <task-id> Check podcast generation status
podcast-download [output-path] Download latest podcast
briefing [--instructions TEXT] Generate brief audio summary
debate [--instructions TEXT] Generate debate-style audio
slides [--instructions TEXT] Generate slide deck
slides-download [output-path] Download slide deck as PDF
infographic [--instructions TEXT] Generate infographic
infographic-download [output-path] Download infographic
media-list [--type TYPE] List generated media (audio/video/slides/infographic)
media-delete <id> Delete a generated media item

Command Routing

Based on $ARGUMENTS, execute the appropriate command:

$IF($ARGUMENTS, Parse the command from: "$ARGUMENTS"

login → python scripts/run.py auth_manager.py setup --service google

accounts → python scripts/run.py auth_manager.py accounts list

accounts add → python scripts/run.py auth_manager.py accounts add

accounts switch → python scripts/run.py auth_manager.py accounts switch "<id>"

accounts remove → python scripts/run.py auth_manager.py accounts remove "<id>"

accounts use → python scripts/run.py auth_manager.py accounts use "<id>"

accounts clear → python scripts/run.py auth_manager.py accounts clear

status → Run both:

  • python scripts/run.py auth_manager.py status
  • python scripts/run.py notebook_manager.py list

local → python scripts/run.py notebook_manager.py list

remote → python scripts/run.py nblm_cli.py notebooks

create → python scripts/run.py nblm_cli.py create "<name>"

delete [--id ID] → python scripts/run.py nblm_cli.py delete <args>

rename [--id ID] → python scripts/run.py nblm_cli.py rename "<name>" <args>

summary [--id ID] → python scripts/run.py nblm_cli.py summary <args>

describe [--id ID] → python scripts/run.py nblm_cli.py describe <args>

add → Smart add workflow (auto-detects URL vs notebook ID)

activate → python scripts/run.py notebook_manager.py activate --id "<id>"

sources [--id ID] → python scripts/run.py nblm_cli.py sources <args>

upload → First ASK user: "Upload to active notebook or create new?" Then: - Active: python scripts/run.py source_manager.py add --file "<file>" --use-active - New: python scripts/run.py source_manager.py add --file "<file>" --create-new

upload → Sync a folder: - First ASK user: "Sync to active notebook, create new, or specify notebook?" - Active: python scripts/run.py source_manager.py sync "<folder>" --use-active - New: python scripts/run.py source_manager.py sync "<folder>" --create-new - Specific: python scripts/run.py source_manager.py sync "<folder>" --notebook-id ID - Dry-run: python scripts/run.py source_manager.py sync "<folder>" --dry-run - Rebuild: python scripts/run.py source_manager.py sync "<folder>" --rebuild

upload-zlib → First ASK user: "Upload to active notebook or create new?" Then: - Active: python scripts/run.py source_manager.py add --url "<url>" --use-active - New: python scripts/run.py source_manager.py add --url "<url>" --create-new

upload-url → python scripts/run.py nblm_cli.py upload-url "<url>"

upload-youtube → python scripts/run.py nblm_cli.py upload-youtube "<url>"

upload-text </strong> → <code>python scripts/run.py nblm_cli.py upload-text "<title>" <args></code></p> <p> <strong>source-text <id></strong> → <code>python scripts/run.py nblm_cli.py source-text "<id>"</code></p> <p> <strong>source-guide <id></strong> → <code>python scripts/run.py nblm_cli.py source-guide "<id>"</code></p> <p> <strong>source-rename <id> <name></strong> → <code>python scripts/run.py nblm_cli.py source-rename "<id>" "<name>"</code></p> <p> <strong>source-refresh <id></strong> → <code>python scripts/run.py nblm_cli.py source-refresh "<id>"</code></p> <p> <strong>source-delete <id></strong> → <code>python scripts/run.py nblm_cli.py source-delete "<id>"</code></p> <p> <strong>ask <question></strong> → <code>python scripts/run.py nblm_cli.py ask "<question>"</code></p> <p> <strong>podcast</strong> → <code>python scripts/run.py artifact_manager.py generate --format DEEP_DIVE <args></code></p> <p> <strong>podcast-status <task-id></strong> → <code>python scripts/run.py artifact_manager.py status --task-id "<task-id>"</code></p> <p> <strong>podcast-download [output-path]</strong> → <code>python scripts/run.py artifact_manager.py download "<output-path>"</code></p> <p> <strong>briefing</strong> → <code>python scripts/run.py artifact_manager.py generate --format BRIEF <args></code></p> <p> <strong>debate</strong> → <code>python scripts/run.py artifact_manager.py generate --format DEBATE <args></code></p> <p> <strong>slides</strong> → <code>python scripts/run.py artifact_manager.py generate-slides <args></code></p> <p> <strong>slides-download [output-path]</strong> → <code>python scripts/run.py artifact_manager.py download "<output-path>" --type slide-deck</code></p> <p> <strong>infographic</strong> → <code>python scripts/run.py artifact_manager.py generate-infographic <args></code></p> <p> <strong>infographic-download [output-path]</strong> → <code>python scripts/run.py artifact_manager.py download "<output-path>" --type infographic</code></p> <p> <strong>media-list [--type TYPE]</strong> → <code>python scripts/run.py artifact_manager.py list <args></code></p> <p> <strong>media-delete <id></strong> → <code>python scripts/run.py artifact_manager.py delete "<id>"</code></p> <p> If command not recognized, show usage help.,</p> <p> Show available commands with <code>/nblm</code> (no arguments) )</p> <h2>Podcast Options</h2> <pre><code>/nblm podcast --length DEFAULT --wait --output ./podcast.mp3 /nblm podcast --instructions "Focus on the key findings" /nblm briefing --wait --output ./summary.mp3 /nblm debate --instructions "Compare the two approaches" </code></pre> <table> <thead> <tr> <th>Option</th> <th>Values</th> </tr> </thead> <tbody><tr> <td><code>--length</code></td> <td><code>SHORT</code>, <code>DEFAULT</code>, <code>LONG</code></td> </tr> <tr> <td><code>--instructions</code></td> <td>Custom instructions for the content</td> </tr> <tr> <td><code>--wait</code></td> <td>Wait for generation to complete</td> </tr> <tr> <td><code>--output</code></td> <td>Download path (requires <code>--wait</code>)</td> </tr> </tbody></table> <h2>Slide Deck Options</h2> <pre><code>/nblm slides --format DETAILED_DECK --wait --output ./presentation.pdf /nblm slides --instructions "Focus on key diagrams" --format PRESENTER_SLIDES </code></pre> <table> <thead> <tr> <th>Option</th> <th>Values</th> </tr> </thead> <tbody><tr> <td><code>--format</code></td> <td><code>DETAILED_DECK</code>, <code>PRESENTER_SLIDES</code></td> </tr> <tr> <td><code>--length</code></td> <td><code>SHORT</code>, <code>DEFAULT</code></td> </tr> <tr> <td><code>--instructions</code></td> <td>Custom instructions for the content</td> </tr> <tr> <td><code>--wait</code></td> <td>Wait for generation to complete</td> </tr> <tr> <td><code>--output</code></td> <td>Download path (requires <code>--wait</code>)</td> </tr> </tbody></table> <h2>Infographic Options</h2> <pre><code>/nblm infographic --orientation LANDSCAPE --wait --output ./visual.png /nblm infographic --instructions "Highlight comparison" --detail-level DETAILED </code></pre> <table> <thead> <tr> <th>Option</th> <th>Values</th> </tr> </thead> <tbody><tr> <td><code>--orientation</code></td> <td><code>LANDSCAPE</code>, <code>PORTRAIT</code>, <code>SQUARE</code></td> </tr> <tr> <td><code>--detail-level</code></td> <td><code>CONCISE</code>, <code>STANDARD</code>, <code>DETAILED</code></td> </tr> <tr> <td><code>--instructions</code></td> <td>Custom instructions for the content</td> </tr> <tr> <td><code>--wait</code></td> <td>Wait for generation to complete</td> </tr> <tr> <td><code>--output</code></td> <td>Download path (requires <code>--wait</code>)</td> </tr> </tbody></table> <h2>Media Generation</h2> <table> <thead> <tr> <th>Command</th> <th>Description</th> <th>Output</th> </tr> </thead> <tbody><tr> <td><code>/nblm podcast</code></td> <td>Deep-dive audio discussion</td> <td>MP3</td> </tr> <tr> <td><code>/nblm briefing</code></td> <td>Brief audio summary</td> <td>MP3</td> </tr> <tr> <td><code>/nblm debate</code></td> <td>Debate-style audio</td> <td>MP3</td> </tr> <tr> <td><code>/nblm slides</code></td> <td>Slide deck presentation</td> <td>PDF</td> </tr> <tr> <td><code>/nblm infographic</code></td> <td>Visual infographic</td> <td>PNG</td> </tr> </tbody></table> <h3>Examples</h3> <pre><code>/nblm podcast --wait --output ./deep-dive.mp3 /nblm briefing --instructions "Focus on chapter 3" --wait /nblm debate --length LONG --wait --output ./debate.mp3 /nblm slides --instructions "Include key diagrams" --format DETAILED_DECK --wait --output ./presentation.pdf /nblm infographic --orientation LANDSCAPE --detail-level DETAILED --wait --output ./summary.png </code></pre> <h3>Download & Manage</h3> <pre><code>/nblm podcast-download ./my-podcast.mp3 /nblm slides-download ./presentation.pdf /nblm infographic-download ./visual.png /nblm media-list # List all generated media /nblm media-list --type audio # List only audio /nblm media-delete <id> # Delete a media item </code></pre> <hr> <h1>Extended Documentation</h1> <h2>When to Use This Skill</h2> <p>Trigger when user:</p> <ul> <li>Mentions NotebookLM explicitly</li> <li>Shares NotebookLM URL (<code>https://notebooklm.google.com/notebook/...</code>)</li> <li>Asks to query their notebooks/documentation</li> <li>Wants to add documentation to NotebookLM library</li> <li>Uses phrases like "ask my NotebookLM", "check my docs", "query my notebook"</li> </ul> <h2>⚠️ CRITICAL: Add Command - Smart Discovery</h2> <p>The add command now <strong>automatically discovers metadata</strong> from the notebook:</p> <pre><code class="language-bash"># Smart Add (auto-discovers name, description, topics) python scripts/run.py notebook_manager.py add <notebook-id-or-url> # With optional overrides python scripts/run.py notebook_manager.py add <id> --name "Custom Name" --topics "custom,topics" </code></pre> <p><strong>What Smart Add does:</strong></p> <ol> <li>Fetches notebook title from NotebookLM API</li> <li>Queries the notebook content to generate description and topics</li> <li>Adds to local library with discovered metadata</li> </ol> <p><strong>Supported input formats:</strong></p> <ul> <li>Notebook ID: <code>5fd9f36b-8000-401d-a7a0-7aa3f7832644</code></li> <li>Full URL: <code>https://notebooklm.google.com/notebook/5fd9f36b-8000-401d-a7a0-7aa3f7832644</code></li> </ul> <p>NEVER manually specify <code>--name</code>, <code>--description</code>, or <code>--topics</code> unless the user explicitly provides them.</p> <h2>Critical: Always Use run.py Wrapper</h2> <p><strong>NEVER call scripts directly. ALWAYS use <code>python scripts/run.py [script]</code>:</strong></p> <pre><code class="language-bash"># ✅ CORRECT - Always use run.py: python scripts/run.py auth_manager.py status python scripts/run.py notebook_manager.py list python scripts/run.py ask_question.py --question "..." # ❌ WRONG - Never call directly: python scripts/auth_manager.py status # Fails without venv! </code></pre> <p>The <code>run.py</code> wrapper automatically:</p> <ol> <li>Creates <code>.venv</code> if needed</li> <li>Installs all dependencies</li> <li>Activates environment</li> <li>Executes script properly</li> </ol> <h2>Core Workflow</h2> <h3>Step 1: Check Authentication Status</h3> <pre><code class="language-bash">python scripts/run.py auth_manager.py status </code></pre> <p>If not authenticated, proceed to setup.</p> <h3>Step 2: Authenticate (One-Time Setup)</h3> <pre><code class="language-bash"># Browser MUST be visible for manual Google login python scripts/run.py auth_manager.py setup </code></pre> <p><strong>Important:</strong></p> <ul> <li>Browser is VISIBLE for authentication</li> <li>Browser window opens automatically</li> <li>User must manually log in to Google</li> <li>Tell user: "A browser window will open for Google login"</li> </ul> <h3>Step 3: Manage Notebook Library</h3> <pre><code class="language-bash"># List all notebooks python scripts/run.py notebook_manager.py list # BEFORE ADDING: Ask user for metadata if unknown! # "What does this notebook contain?" # "What topics should I tag it with?" # Add notebook to library (ALL parameters are REQUIRED!) python scripts/run.py notebook_manager.py add \ --url "https://notebooklm.google.com/notebook/..." \ --name "Descriptive Name" \ --description "What this notebook contains" \ # REQUIRED - ASK USER IF UNKNOWN! --topics "topic1,topic2,topic3" # REQUIRED - ASK USER IF UNKNOWN! # Search notebooks by topic python scripts/run.py notebook_manager.py search --query "keyword" # Set active notebook python scripts/run.py notebook_manager.py activate --id notebook-id # Remove notebook python scripts/run.py notebook_manager.py remove --id notebook-id </code></pre> <h3>Quick Workflow</h3> <ol> <li>Check library: <code>python scripts/run.py notebook_manager.py list</code></li> <li>Ask question: <code>python scripts/run.py ask_question.py --question "..." --notebook-id ID</code></li> </ol> <h3>Step 4: Ask Questions</h3> <pre><code class="language-bash"># Basic query (uses active notebook if set) python scripts/run.py ask_question.py --question "Your question here" # Query specific notebook python scripts/run.py ask_question.py --question "..." --notebook-id notebook-id # Query with notebook URL directly python scripts/run.py ask_question.py --question "..." --notebook-url "https://..." # Show browser for debugging python scripts/run.py ask_question.py --question "..." --show-browser </code></pre> <h2>Follow-Up Mechanism (CRITICAL)</h2> <p>Every NotebookLM answer ends with: <strong>"EXTREMELY IMPORTANT: Is that ALL you need to know?"</strong></p> <p><strong>Required Claude Behavior:</strong></p> <ol> <li><strong>STOP</strong> - Do not immediately respond to user</li> <li><strong>ANALYZE</strong> - Compare answer to user's original request</li> <li><strong>IDENTIFY GAPS</strong> - Determine if more information needed</li> <li><strong>ASK FOLLOW-UP</strong> - If gaps exist, immediately ask:<pre><code class="language-bash">python scripts/run.py ask_question.py --question "Follow-up with context..." </code></pre> </li> <li><strong>REPEAT</strong> - Continue until information is complete</li> <li><strong>SYNTHESIZE</strong> - Combine all answers before responding to user</li> </ol> <h2>Z-Library Integration</h2> <h3>Triggers</h3> <ul> <li>User provides Z-Library URL (zlib.li, z-lib.org, zh.zlib.li)</li> <li>User says "download this book to NotebookLM"</li> <li>User says "add this book from Z-Library"</li> </ul> <h3>Setup (One-Time)</h3> <pre><code class="language-bash"># Authenticate with Z-Library python scripts/run.py auth_manager.py setup --service zlibrary </code></pre> <h3>Commands</h3> <pre><code class="language-bash"># Add book from Z-Library python scripts/run.py source_manager.py add --url "https://zh.zlib.li/book/..." # Check Z-Library auth status python scripts/run.py auth_manager.py status --service zlibrary </code></pre> <h2>Script Reference</h2> <h3>Authentication Management (<code>auth_manager.py</code>)</h3> <pre><code class="language-bash">python scripts/run.py auth_manager.py setup # Default: Google python scripts/run.py auth_manager.py setup --service google python scripts/run.py auth_manager.py setup --service zlibrary python scripts/run.py auth_manager.py status # Show all services python scripts/run.py auth_manager.py status --service zlibrary python scripts/run.py auth_manager.py clear --service zlibrary # Clear auth # Multi-Account Management (Google) python scripts/run.py auth_manager.py accounts list # List all accounts python scripts/run.py auth_manager.py accounts add # Add new account python scripts/run.py auth_manager.py accounts switch 1 # Switch by index python scripts/run.py auth_manager.py accounts switch user@gmail.com # Switch by email python scripts/run.py auth_manager.py accounts remove 2 # Remove account </code></pre> <h3>Notebook Management (<code>notebook_manager.py</code>)</h3> <pre><code class="language-bash">python scripts/run.py notebook_manager.py add --url URL --name NAME --description DESC --topics TOPICS # OR use notebook ID directly: python scripts/run.py notebook_manager.py add --notebook-id ID --name NAME --description DESC --topics TOPICS python scripts/run.py notebook_manager.py list python scripts/run.py notebook_manager.py search --query QUERY python scripts/run.py notebook_manager.py activate --id ID python scripts/run.py notebook_manager.py remove --id ID python scripts/run.py notebook_manager.py stats </code></pre> <h3>Question Interface (<code>ask_question.py</code>)</h3> <pre><code class="language-bash">python scripts/run.py ask_question.py --question "..." [--notebook-id ID] [--notebook-url URL] [--show-browser] </code></pre> <h3>Source Manager (<code>source_manager.py</code>)</h3> <pre><code class="language-bash"># Upload to active notebook python scripts/run.py source_manager.py add --file "/path/to/book.pdf" --use-active # Create new notebook for upload python scripts/run.py source_manager.py add --file "/path/to/book.pdf" --create-new # Upload to specific notebook python scripts/run.py source_manager.py add --file "/path/to/book.pdf" --notebook-id NOTEBOOK_ID # Z-Library download and upload python scripts/run.py source_manager.py add --url "https://zh.zlib.li/book/..." --use-active python scripts/run.py source_manager.py add --url "https://zh.zlib.li/book/..." --create-new # Sync a folder (new!) python scripts/run.py source_manager.py sync "/path/to/docs" --use-active python scripts/run.py source_manager.py sync "/path/to/docs" --create-new python scripts/run.py source_manager.py sync "/path/to/docs" --notebook-id NOTEBOOK_ID # Sync options (new!) python scripts/run.py source_manager.py sync "/path/to/docs" --dry-run # Preview only python scripts/run.py source_manager.py sync "/path/to/docs" --rebuild # Force re-hash all files </code></pre> <p><strong>Folder Sync:</strong></p> <ul> <li>Scans folder for supported types: PDF, TXT, MD, DOCX, HTML, EPUB</li> <li>Tracks sync state internally (no per-folder tracking file to manage)</li> <li>Sync strategy: add new, update modified (delete + re-upload), skip unchanged</li> <li>Multi-account aware (tracks which Google account was used) <strong>Note:</strong> One of <code>--use-active</code>, <code>--create-new</code>, or <code>--notebook-id</code> is REQUIRED. Uploads wait for NotebookLM processing and print progress as <code>Ready: N/T</code>. Press Ctrl+C to stop waiting. Local file uploads use browser automation and require Google authentication. If browser automation is unavailable, set <code>NOTEBOOKLM_UPLOAD_MODE=text</code> to upload extracted text instead (PDFs require <code>pypdf</code>).</li> </ul> <h3>Data Cleanup (<code>cleanup_manager.py</code>)</h3> <pre><code class="language-bash">python scripts/run.py cleanup_manager.py # Preview cleanup python scripts/run.py cleanup_manager.py --confirm # Execute cleanup python scripts/run.py cleanup_manager.py --preserve-library # Keep notebooks </code></pre> <h3>Watchdog Status (<code>auth_manager.py</code>)</h3> <pre><code class="language-bash">python scripts/run.py auth_manager.py watchdog-status </code></pre> <h2>Environment Management</h2> <p>The virtual environment is automatically managed:</p> <ul> <li>First run creates <code>.venv</code> automatically</li> <li>Dependencies install automatically</li> <li>Node.js dependencies install automatically</li> <li>agent-browser daemon starts on demand and keeps browser state in memory</li> <li>daemon stops after 10 minutes of inactivity (any agent-browser command resets the timer)</li> <li>set <code>AGENT_BROWSER_OWNER_PID</code> to auto-stop when the agent process exits</li> <li><code>scripts/run.py</code> sets <code>AGENT_BROWSER_OWNER_PID</code> to its parent PID by default</li> <li>Everything isolated in skill directory</li> </ul> <p>Manual setup (only if automatic fails):</p> <pre><code class="language-bash">python -m venv .venv source .venv/bin/activate # Linux/Mac pip install -r requirements.txt npm install npm run install-browsers </code></pre> <h2>Data Storage</h2> <p>All data stored in <code>~/.claude/skills/notebooklm/data/</code>:</p> <ul> <li><code>library.json</code> - Notebook metadata (with account associations)</li> <li><code>auth/google/</code> - Multi-account Google auth<ul> <li><code>index.json</code> - Account index (active account, list)</li> <li><code><n>-<email>.json</code> - Per-account credentials</li> </ul> </li> <li><code>auth/zlibrary.json</code> - Z-Library auth state</li> <li><code>agent_browser/session_id</code> - Current daemon session ID</li> <li><code>agent_browser/last_activity.json</code> - Last activity timestamp for idle shutdown</li> <li><code>agent_browser/watchdog.pid</code> - Idle watchdog process ID</li> </ul> <p><strong>Security:</strong> Protected by <code>.gitignore</code>, never commit to git.</p> <h2>Configuration</h2> <p>Optional <code>.env</code> file in skill directory:</p> <pre><code class="language-env">HEADLESS=false # Browser visibility SHOW_BROWSER=false # Default browser display STEALTH_ENABLED=true # Human-like behavior TYPING_WPM_MIN=160 # Typing speed TYPING_WPM_MAX=240 DEFAULT_NOTEBOOK_ID= # Default notebook </code></pre> <h2>Decision Flow</h2> <pre><code>User mentions NotebookLM ↓ Check auth → python scripts/run.py auth_manager.py status ↓ If not authenticated → python scripts/run.py auth_manager.py setup ↓ Check/Add notebook → python scripts/run.py notebook_manager.py list/add (with --description) ↓ Activate notebook → python scripts/run.py notebook_manager.py activate --id ID ↓ Ask question → python scripts/run.py ask_question.py --question "..." ↓ See "Is that ALL you need?" → Ask follow-ups until complete ↓ Synthesize and respond to user </code></pre> <h2>Troubleshooting</h2> <table> <thead> <tr> <th>Problem</th> <th>Solution</th> </tr> </thead> <tbody><tr> <td>ModuleNotFoundError</td> <td>Use <code>run.py</code> wrapper</td> </tr> <tr> <td>Authentication fails</td> <td>Browser must be visible for setup! --show-browser</td> </tr> <tr> <td>DAEMON_UNAVAILABLE</td> <td>Ensure Node.js/npm installed, run <code>npm install</code>, retry</td> </tr> <tr> <td>AUTH_REQUIRED</td> <td>Run <code>python scripts/run.py auth_manager.py setup</code></td> </tr> <tr> <td>ELEMENT_NOT_FOUND</td> <td>Verify notebook URL and re-run with fresh page load</td> </tr> <tr> <td>Rate limit (50/day)</td> <td>Wait or add another Google account with <code>accounts add</code></td> </tr> <tr> <td>Browser crashes</td> <td><code>python scripts/run.py cleanup_manager.py --preserve-library</code></td> </tr> <tr> <td>Notebook not found</td> <td>Check with <code>notebook_manager.py list</code></td> </tr> </tbody></table> <h2>Best Practices</h2> <ol> <li><strong>Always use run.py</strong> - Handles environment automatically</li> <li><strong>Check auth first</strong> - Before any operations</li> <li><strong>Follow-up questions</strong> - Don't stop at first answer</li> <li><strong>Browser visible for auth</strong> - Required for manual login</li> <li><strong>Include context</strong> - Each question is independent</li> <li><strong>Synthesize answers</strong> - Combine multiple responses</li> </ol> <h2>Limitations</h2> <ul> <li>No session persistence (each question = new browser)</li> <li>Rate limits on free Google accounts (50 queries/day per account; use multiple accounts to increase)</li> <li>Manual upload required (user must add docs to NotebookLM)</li> <li>Browser overhead (few seconds per question)</li> </ul> <h2>Resources (Skill Structure)</h2> <p><strong>Important directories and files:</strong></p> <ul> <li><code>scripts/</code> - All automation scripts (ask_question.py, notebook_manager.py, etc.)</li> <li><code>data/</code> - Local storage for authentication and notebook library</li> <li><code>references/</code> - Extended documentation:<ul> <li><code>api_reference.md</code> - Detailed API documentation for all scripts</li> <li><code>troubleshooting.md</code> - Common issues and solutions</li> <li><code>usage_patterns.md</code> - Best practices and workflow examples</li> </ul> </li> <li><code>.venv/</code> - Isolated Python environment (auto-created on first run)</li> <li><code>.gitignore</code> - Protects sensitive data from being committed</li> </ul>

Related skills

researchmattpocock575KInvestigate a question against high-trust primary sources and capture the findings as a Markdown file in the repo. Use when the user wants a topic researched, docs or API facts gathered, or reading legwork delegated to a background agent.paper-context-resolverlllllllama451KRigor Paper Context helper for README-first deep learning repo reproduction. Use only when the README and repository files leave a narrow reproduction-critical gap and the task is to resolve a specific paper detail such as dataset split, preprocessing, evaluation protocol, checkpoint mapping, or runtime assumption from primary paper sources while recording conflicts. Do not use for general paper summary, repo scanning, environment setup, command execution, title-only paper lookup, or replacing Renv-and-assets-bootstraplllllllama450KRigor Setup skill for README-first deep learning repo reproduction. Use when the task is specifically to prepare a conservative conda-first environment, checkpoint and dataset path assumptions, cache location hints, and setup notes before any run on a README-documented repository. Do not use for repo scanning, full orchestration, paper interpretation, final run reporting, or generic environment setup that is not tied to a specific reproduction target.ai-research-explorelllllllama311KRigor Explore compatible skill slug for meaningful and potentially novel deep learning research candidates. Use when the researcher has chosen the task family, dataset, benchmark, evaluation method, provided SOTA references, and wants candidate-only exploration on top of `current_research` with auditable repo understanding, idea gating, fair comparison, and governed experiments written to `explore_outputs/`. Do not use for README-first trusted reproduction, open-ended direction finding, narrow c

Search skills and MCP servers

Fuzzy search across 23,137 skills and servers