
Security News
/Research
Fake Corepack Site Distributes Infostealer and Proxyware to Developers
A fake corepack.org site is impersonating the Node.js tool and delivers an infostealer and proxyware to developers who download it.
notion-cli-agent
Advanced tools
The most powerful CLI for Notion — built for humans AND AI agents. Features smart queries, Obsidian sync, batch operations, validation, backups, and more.
The most powerful command-line interface for Notion — built for AI agents first, humans too.
notion-cli-agent is designed to be used by AI agents that need to read and write Notion workspaces — natural language queries, batch operations, --llm output mode, workspace introspection, and more. Works great for humans too.
npm install -g notion-cli-agent
export NOTION_TOKEN="ntn_your_token_here"
# Full quick reference (read this first)
notion quickstart
This repo ships AgentSkills-compatible skill files in the skills/ directory. Skills use progressive disclosure: the core SKILL.md is small enough to live in your agent's context window, and detailed reference files (filters.md, batch-patterns.md, workflows.md) are loaded on demand.
skills/
├── notion-onboarding/ ← run first: maps your workspace to a state file
└── notion-cli-agent/ ← core CLI skill + references
Recommended setup for agents:
skills/README.md)notion-onboarding skill once — it discovers your databases (tasks, projects, OKRs, home page) and saves them to ~/.config/notion/workspace.json--llm mode — compact, structured output optimized for agent consumptionnotion find — natural language → Notion filters in one commandnotion batch — multiple operations in a single shell call (minimize tool calls)notion ai prompt — generates a database-specific prompt for the agentnotion inspect context — full schema + examples + command reference in one shotnpm install -g notion-cli-agent
# Clone the repository
git clone https://github.com/Balneario-de-Cofrentes/notion-cli-agent.git
cd notion-cli-agent
# Install dependencies
pnpm install
# Build
pnpm build
# Link globally
pnpm link --global
ntn_ or secret_)# Option 1: Environment variable (recommended)
export NOTION_TOKEN="ntn_your_token_here"
# Option 2: Pass directly
notion --token "ntn_xxx" search "query"
Important: Your integration can only access pages explicitly shared with it.
Sync your workspace to use database names instead of UUIDs:
# Cache all accessible databases locally
notion sync
# List cached databases
notion list
notion list --json # For scripts
notion list --ids-only # One ID per line
# Now use names anywhere you'd use a database UUID
notion db query "Tasks" --limit 5
notion find "Tasks" "overdue assigned to me"
notion validate health "Projects"
notion stats overview "OKRs"
All database commands accept both UUIDs and names. Name resolution uses case-insensitive matching with substring fallback. If a name is ambiguous, the CLI shows candidates and asks you to be more specific.
# Search across workspace
notion search "project plan"
notion search "meeting" --type page
notion search "" --type database # List all databases
# Exact lookup in a known database (deterministic)
notion db query <db_id> --title "Known Page" --json
# Filtered search (best-effort — Notion search is fuzzy)
notion search "keyword" --db <db_id> --exact --first --json
notion search "task" --db <db_id> # Filter by parent database
# Get page info
notion page get <page_id>
notion page get <page_id> --content # Include blocks
# Create page in database
notion page create --parent <db_id> --title "New Task"
notion page create --parent <db_id> --title "Bug Fix" \
--prop "Status=Todo" \
--prop "Priority=High"
notion page create --parent <db_id> --title "Meeting Notes" --icon 📝
# Update page
notion page update <page_id> --prop "Status:status=Done"
notion page update <page_id> --title "New Title"
notion page update <page_id> --icon 🚀
notion page update <page_id> --clear-prop "Assignee" # Type-aware clear
# Archive page
notion page archive <page_id>
# Export database as CSV
notion db query <db_id> --csv > tasks.csv
# Tab-separated (paste into spreadsheets)
notion db query <db_id> --tsv | pbcopy
# Just IDs for piping into other commands
notion db query <db_id> --filter "Status=Done" --ids-only | \
xargs -I {} notion page archive {}
# Count search results
notion search "bugs" --ids-only | wc -l
| Flag | Commands | Description |
|---|---|---|
--json / -j | all | Raw JSON |
--llm | most | Compact agent-friendly output |
--csv | db query, find | CSV with headers |
--tsv | db query, find | Tab-separated |
--ids-only | db query, search, find | One ID per line |
Read, write, and surgically edit page content as Markdown.
# Read page content as Markdown
notion page read <page_id>
notion page read <page_id> --json # Raw block output
notion page read <page_id> -o page.md # Write to file
# Write Markdown content into a page
notion page write <page_id> -f content.md
echo "# Hello" | notion page write <page_id>
notion page write <page_id> -f doc.md --replace # Replace all content (destructive)
# Surgical block-level editing
notion page edit <page_id> --at 3 --delete 2 # Delete 2 blocks at index 3
notion page edit <page_id> --at 5 --markdown "New paragraph" # Insert at index 5
notion page edit <page_id> --at 0 --delete 1 --file new.md # Replace first block
notion page edit <page_id> --dry-run --at 3 --delete 1 # Preview without changes
findTranslate natural language into Notion filters:
# Find overdue tasks
notion find "overdue tasks" -d <db_id>
# Find unassigned items in progress
notion find "in progress unassigned" -d <db_id>
# Find high priority pending items
notion find "urgent pending" -d <db_id>
# See what filter was generated
notion find "tareas vencidas" -d <db_id> --explain
Supported patterns:
done, in progress, todo, pending, hecho, en marchaunassigned, sin asignaroverdue, vencidas, today, this weekurgent, high priority, importanteExecute multiple operations in one command — perfect for AI agents to minimize tool calls:
# Preview what would happen
notion batch --dry-run --data '[
{"op": "get", "type": "page", "id": "abc123"},
{"op": "create", "type": "page", "parent": "db_id", "data": {...}},
{"op": "update", "type": "page", "id": "xyz789", "data": {...}}
]'
# Execute with LLM-friendly output
notion batch --llm --data '[...]'
# Read from file
notion batch -f operations.json
Supported operations:
| Op | Types | Description |
|---|---|---|
get | page, database, block | Retrieve by ID |
create | page, database | Create new |
update | page, database, block | Modify |
delete | page, block | Archive/delete |
query | database | Query with filters |
append | block | Add children |
Create optimal prompts for AI agents to work with a specific database:
notion ai prompt <database_id>
Output includes:
Get concise summaries for quick understanding:
notion ai summarize <page_id>
# Output:
# Project Plan Q1
# Last edited: 2 days ago
# Blocks: 45
# Properties:
# - Status: In Progress
# - Owner: Juan
# Sections:
# - Overview
# - Timeline
# - Resources
# Todos: 8/12 completed
Pull specific data points from page content:
notion ai extract <page_id> --schema "email,phone,company,date"
# Output:
{
"email": "contact@example.com",
"phone": "+34 612 345 678",
"company": "Acme Corp",
"date": "2024-03-15"
}
Get command suggestions based on natural language:
notion ai suggest <db_id> "quiero ver las tareas completadas esta semana"
# Outputs:
# notion find "hecho" -d <db_id>
# notion db query <db_id> --filter-prop "Status" --filter-value "Hecho" --filter-prop-type status
Export a single page:
notion export page <page_id> --obsidian -o my-note.md
Export entire database to vault:
notion export db <database_id> --vault ~/obsidian-vault --folder notion-tasks
With full page content:
notion export db <db_id> --vault ~/vault --content
Exported files include:
---
notion_id: "abc123..."
notion_url: "https://notion.so/..."
created: 2024-01-15
updated: 2024-02-01
status: "In Progress"
priority: "High"
tags:
- "project"
- "q1"
---
# Page Title
Content here...
Import vault to database:
notion import obsidian ~/my-vault --to <database_id>
notion import obsidian ~/my-vault --to <db_id> --folder specific-folder
notion import obsidian ~/my-vault --to <db_id> --content # Include page content
Import CSV:
notion import csv data.csv --to <database_id>
notion import csv tasks.csv --to <db_id> --title-column "Task Name"
Import Markdown file:
notion import markdown document.md --to <page_id>
notion import markdown doc.md --to <page_id> --replace # Replace existing content
notion stats overview <database_id>
# Output:
# 📊 Database: Tasks
# Total entries: 342
#
# Status:
# Done 124 (36%) ████████
# In Progress 89 (26%) ██████
# Todo 78 (23%) █████
# Blocked 51 (15%) ███
#
# Priority:
# High 45 (13%) ███
# Medium 187 (55%) ███████████
# Low 110 (32%) ███████
notion stats timeline <database_id> --days 14
# 2024-02-01 (Thu) 12 ████████████
# 2024-01-31 (Wed) 8 ████████
# 2024-01-30 (Tue) 15 ███████████████
# ...
notion validate check <database_id> \
--required "Assignee,Deadline" \
--check-dates \
--check-stale 30 \
--fix
# Output:
# ⚠️ MISSING REQUIRED (23)
# - Task ABC: Missing required property: Assignee
# - Task XYZ: Missing required property: Deadline
# Fix: notion page update <id> --prop "Assignee=..."
#
# ⚠️ OVERDUE (8)
# - Old task: Overdue: deadline was 2024-01-15
#
# ℹ️ STALE (5)
# - Stuck item: Not updated in 45 days (status: In Progress)
#
# 📊 Health Score: 72/100
notion validate lint <database_id>
# ✅ Empty titles: OK
# ⚠️ "In Progress" for >30 days: 5 found
# Total issues: 5
notion validate health <database_id>
# 📊 Health Report: Tasks
# ════════════════════════════════════════
# Health Score: 78/100 🟡
# ════════════════════════════════════════
#
# 📈 Activity (last 7 days): 34/100 entries (34%)
# ✅ Completion rate: 65%
# 📝 Average fill rate: 82%
#
# Property fill rates:
# ✅ Title ██████████ 100%
# ✅ Status ██████████ 100%
# ⚠️ Assignee ████████░░ 77%
# ❌ Tags ██░░░░░░░░ 15%
# Backup to JSON
notion backup <database_id> -o ./backups/tasks
# Backup to Markdown
notion backup <db_id> -o ./backups --format markdown
# Include page content
notion backup <db_id> -o ./backups --content
# Incremental backup (only changed entries)
notion backup <db_id> -o ./backups --incremental
Output structure:
backups/
├── schema.json # Database schema
├── index.json # Entry index
├── .backup-meta.json # Backup metadata
└── pages/
├── Task_One_abc123.json
├── Task_Two_def456.json
└── ...
# Find duplicate pages by title
notion dedup <db_id>
# Include near-duplicates (strips copy/draft suffixes)
notion dedup <db_id> --fuzzy
# Archive duplicates, keep the page with most content
notion dedup <db_id> --fix --strategy keep-largest --yes
# Keep newest or oldest
notion dedup <db_id> --fix --strategy keep-newest --yes
notion dedup <db_id> --fix --strategy keep-oldest --yes
# Preview first (default when --fix without --yes)
notion dedup <db_id> --fix --strategy keep-largest
Discover what pages link to a specific page:
notion relations backlinks <page_id>
# 📎 Direct Relations:
# Project Alpha
# └─ via property: Related Tasks
#
# Sprint 23
# └─ via property: Tasks
#
# 📝 Potential Mentions:
# Meeting Notes Jan 15
# Weekly Report
# Create relation
notion relations link <source_id> <target_id> --property "Related"
# Bidirectional linking
notion relations link <page1> <page2> --property "Related" --bidirectional
# Remove relation
notion relations unlink <source_id> <target_id> --property "Related"
# Text format
notion relations graph <page_id> --depth 2
# DOT format (for Graphviz)
notion relations graph <page_id> --format dot > graph.dot
dot -Tpng graph.dot -o graph.png
# JSON format
notion relations graph <page_id> --format json
notion template save <page_id> --name "weekly-report" --description "Weekly team report"
notion template list
# 📄 weekly-report
# Blocks: 15
# Description: Weekly team report
#
# 📄 meeting-notes
# Blocks: 8
notion template use "weekly-report" --parent <db_id> --title "Report Week 5"
notion template show "weekly-report" # View details
notion template delete "weekly-report" # Remove
Update multiple entries at once:
# Preview first
notion bulk update <db_id> --where "Status=Todo" --set "Status=In Progress" --dry-run
# Execute
notion bulk update <db_id> --where "Status=Todo" --set "Status=In Progress" --yes
Archive entries matching a condition:
# Archive completed items older than 2024
notion bulk archive <db_id> --where "Status=Done" --dry-run
notion bulk archive <db_id> --where "Status=Done" --yes
Where clause syntax:
Property=ValueStatus=Done,Priority=Lownotion inspect workspace
notion inspect ws --compact # Just names and IDs
notion inspect schema <database_id>
notion inspect schema <db_id> --llm # Optimized for AI consumption
notion inspect context <database_id>
# Outputs comprehensive context including:
# - Schema with all properties and valid values
# - Example entries
# - Quick command reference
For operations not covered by other commands:
# GET request
notion api GET "pages/<page_id>"
# POST with body
notion api POST "search" --data '{"query": "test"}'
# With query parameters
notion api GET "users" --query "page_size=5"
When setting properties with --prop, the CLI auto-detects types:
| Value Format | Detected Type | Example |
|---|---|---|
| Plain text | select | --prop "Status=Done" |
true/false | checkbox | --prop "Active=true" |
| Numbers | number | --prop "Count=42" |
YYYY-MM-DD | date | --prop "Due=2024-12-31" |
| URL | url | --prop "Link=https://..." |
--prop "Contact=a@b.com" | ||
| Comma-separated | multi_select | --prop "Tags=bug,urgent" |
Type hints — Force a specific property type with Key:type=Value:
# Status properties (vs auto-detected select)
notion page update <id> --prop "Status:status=Done"
# Rich text instead of select
notion page update <id> --prop "Notes:rich_text=Some notes"
# People by user ID
notion page update <id> --prop "Assignee:people=user-id-here"
For database queries with non-select properties:
notion db query <db_id> \
--filter-prop "Status" \
--filter-type equals \
--filter-value "Done" \
--filter-prop-type status # Required for status type
Run as an MCP tool server for agent frameworks (Claude Code, Cursor, VS Code):
notion --mcp
Configure in Claude Code (settings.json):
{
"mcpServers": {
"notion": {
"command": "notion",
"args": ["--mcp"],
"env": { "NOTION_TOKEN": "ntn_your_token" }
}
}
}
Exposes 14 tools: search, page_get, page_create, page_update, db_query, db_schema, block_children, block_append, find, batch, inspect_workspace, comment_create, validate_health, dedup.
| Category | Commands |
|---|---|
| Search | search |
| Pages | page get, page create, page update, page archive, page read, page write, page edit, page property |
| Databases | db get, db query, db create, db update |
| Blocks | block get, block list, block append, block update, block delete |
| Comments | comment list, comment create, comment get |
| Users | user me, user list, user get |
| Export | export page, export db |
| Import | import obsidian, import csv, import markdown |
| AI | ai summarize, ai extract, ai prompt, ai suggest |
| Find | find |
| Bulk | bulk update, bulk archive |
| Validate | validate check, validate lint, validate health |
| Stats | stats overview, stats timeline |
| Backup | backup |
| Templates | template list, template save, template use, template show, template delete |
| Duplicate | duplicate page, duplicate schema, duplicate db |
| Relations | relations backlinks, relations link, relations unlink, relations graph |
| Inspect | inspect workspace, inspect schema, inspect context |
| Dedup | dedup |
| Batch | batch |
| Quickstart | quickstart |
| API | api |
The skills/ directory contains AgentSkills-compatible packages for use with OpenClaw, Claude Code, Cursor, and other agent frameworks.
skills/
├── README.md # Installation & overview
├── notion-onboarding/
│ ├── SKILL.md # Workspace discovery workflow
│ └── references/
│ └── state-schema.md # ~/.config/notion/workspace.json schema
└── notion-cli-agent/
├── SKILL.md # Core CLI usage
└── references/
├── filters.md # Property types × filter operators
├── batch-patterns.md # Multi-op batch patterns
└── workflows.md # Agent workflow recipes
Skills load in three layers to keep context usage efficient:
| Layer | Content | When loaded |
|---|---|---|
| Metadata | name + description | Always — triggers the skill |
| Core | SKILL.md body | When skill activates |
| Reference | references/*.md | On demand, as needed |
The main SKILL.md for each skill is kept under 150 lines. Deep reference material lives in separate files that the agent reads only when that topic comes up.
# OpenClaw
cp -r skills/notion-cli-agent ~/.local/share/openclaw/skills/
cp -r skills/notion-onboarding ~/.local/share/openclaw/skills/
# See skills/README.md for other frameworks
Contributions are welcome! Please open an issue first to discuss what you would like to change.
MIT © Balneario de Cofrentes - The largest longevity clinic in the world.
Built with:
FAQs
The most powerful CLI for Notion — built for humans AND AI agents. Features smart queries, Obsidian sync, batch operations, validation, backups, and more.
The npm package notion-cli-agent receives a total of 40 weekly downloads. As such, notion-cli-agent popularity was classified as not popular.
We found that notion-cli-agent demonstrated a healthy version release cadence and project activity because the last version was released less than a year ago. It has 1 open source maintainer collaborating on the project.
Did you know?

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Security News
/Research
A fake corepack.org site is impersonating the Node.js tool and delivers an infostealer and proxyware to developers who download it.

Research
/Security News
A large-scale campaign abused GitHub Actions in compromised repositories to exploit CVE-2026-41940 in cPanel and WHM and steal server credentials.

Security News
Five frontier LLMs generated the same nonexistent package names, leaving 53 available for potential slopsquatting across PyPI and npm.