Skip to main content

Notion CLI built for coding agents. Compact JSON, structured errors, meaningful exit codes.

Project description

notionctl

CI codecov PyPI version Ruff License: MIT

Notion CLI built for coding agents. Compact JSON to stdout, structured errors to stderr, meaningful exit codes. Works with Claude Code, Codex, Mistral Vibe or standalone.

# Agent reads a spec from Notion, implements it, writes results back
SPEC=$(notion block get "$PAGE_ID" --markdown)
# ... agent does work ...
notion page create -p "$PAGE_ID" -t "Implementation Notes" -c @results.md
notion page update "$ROW_ID" --properties '{"Status":{"select":{"name":"Done"}}}'

Install

# Run without installing
uvx notionctl search "my page"

# Or install permanently
uv tool install notionctl   # installs both `notionctl` and `notion` commands
pip install notionctl

Authentication

OAuth (recommended)

notion auth login     # opens browser, stores token locally
notion auth status    # check current auth
notion auth logout    # revoke and delete token

When prompted, select all pages for full workspace access. Credentials are stored in ~/.config/notion-cli/ and persist across uvx runs.

API token (for CI or headless environments)

Get a token from https://www.notion.so/my-integrations:

export NOTION_API_KEY="secret_..."

Or pass per command with --token.

Commands

notion search <query>              Search pages and databases by title
notion page get <id>               Get page metadata (--full for blocks + comments)
notion page create                 Create a page with markdown content (--stdin for batch)
notion page update <id>            Update title, properties, icon, archive/unarchive
notion page move <id>              Move a page to a different parent (--stdin for batch)
notion page duplicate <id>         Duplicate a page (with optional content copy)
notion page edit <id>              Find and replace text across page content
notion page grep <id> <pattern>    Search page content with literal or regex patterns
notion db get <id>                 Get database schema
notion db query <id>               Query database rows (--where for human-friendly filters)
notion db create                   Create a database
notion db update <id>              Update database title or schema
notion block get <id>              Get page content as blocks or markdown
notion block append <id>           Append block objects (JSON) to a page
notion block update <id>           Update a block's content or properties
notion block delete <id>           Delete (archive) a block
notion api <METHOD> <path>         Raw API passthrough to any Notion endpoint
notion comment add <id>            Add a comment to a page (plain text or rich text)
notion comment reply <disc-id>     Reply to a comment thread
notion comment list <id>           List comments on a page
notion user list                   List workspace users
notion user get <id>               Get a specific user
notion user me                     Get the current bot user
notion team list                   List teamspaces
notion schema <command>            Introspect CLI command schemas (for agents)
notion auth login/logout/status    OAuth authentication

All IDs accept Notion URLs or raw UUIDs.

Examples

# Search
notion search "meeting notes"
notion search "roadmap" --type page --limit 5

# Read page content as markdown (with recursive nested blocks)
notion block get <page-id> --markdown
notion block get <page-id> --recursive --markdown
notion block get <page-id> --recursive --depth 2 --markdown

# Create a page with markdown (inline, from file, or stdin)
notion page create -p <parent-id> -t "New Page" -c $'# Hello\nWorld'
notion page create -p <parent-id> -t "Notes" -c @notes.md
notion page create -p <db-id> -t "Row" --parent-type database --icon "📝"

# Duplicate a page (with content and to a different parent)
notion page duplicate <page-id> --with-content
notion page duplicate <page-id> --destination <parent-id>
notion page duplicate <page-id> --destination <db-id> --destination-type database

# Find and replace across page content
notion page edit <page-id> --find "old name" --replace "new name"
notion page edit <page-id> --find "TODO" --replace "DONE" --dry-run

# Search page content (literal or regex)
notion page grep <page-id> "search term"
notion page grep <page-id> "\d{4}-\d{2}-\d{2}" --regex

# Get page with all content and comments in one call
notion page get <page-id> --full

# Query a database (human-friendly or raw JSON filter)
notion db query <db-id> --where "Status = Done"
notion db query <db-id> --where "Status = Done" --where "Priority > 3"
notion db query <db-id> --filter '{"property":"Status","select":{"equals":"Done"}}'

# Update a row
notion page update <row-id> --properties '{"Status":{"select":{"name":"Done"}}}'

# Block CRUD
notion block update <block-id> --body '{"paragraph":{"rich_text":[{"text":{"content":"new"}}]}}'
notion block delete <block-id>

# Raw API passthrough
notion api GET pages/<page-id>
notion api POST pages --body @payload.json

# Batch operations via NDJSON stdin
echo '{"parent":"abc","title":"A"}' | notion page create --stdin
cat moves.ndjson | notion page move --stdin

# Comments (plain text or rich text JSON)
notion comment add <page-id> --body "Looks good!"
notion comment reply <discussion-id> --rich-text '[{"text":{"content":"bold"},"annotations":{"bold":true}}]'

# Project output to specific fields
notion page get <page-id> --fields id,url,properties
notion db query <db-id> --fields id,properties --limit 10

Output

Compact JSON to stdout. Errors to stderr:

{"error_type":"not_found","message":"...","suggestion":"..."}

Exit codes: 0 ok · 1 error · 2 bad args · 3 not found · 4 permission denied · 5 rate limited

Global options

  • --fields, -f — Comma-separated list of fields to include in output (e.g. --fields id,url)
  • --dry-run — Show what would be sent to the API without making changes (mutating commands)
  • --output-format json|ndjson — Output format for list commands
  • --token — Notion API token (defaults to NOTION_API_KEY env var)
  • --timeout — Timeout per API request in seconds
  • --help — Show help for any command

Development

git clone https://github.com/jjovalle99/notion-cli.git
cd notion-cli
uv sync
uv run pytest
uv run ruff check src/ tests/
uv run ty check src/

See CONTRIBUTING.md for architecture, conventions, and how to add commands.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

notionctl-0.3.1.tar.gz (27.8 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

notionctl-0.3.1-py3-none-any.whl (39.1 kB view details)

Uploaded Python 3

File details

Details for the file notionctl-0.3.1.tar.gz.

File metadata

  • Download URL: notionctl-0.3.1.tar.gz
  • Upload date:
  • Size: 27.8 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: uv/0.10.11 {"installer":{"name":"uv","version":"0.10.11","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

File hashes

Hashes for notionctl-0.3.1.tar.gz
Algorithm Hash digest
SHA256 d7a8386d94be4b328f38cdc6993d42522833d1a3304092e952be017b0b13fc94
MD5 90c9ba3d0f7dd5fa0920d9d95fcf7541
BLAKE2b-256 24b4115f61cbfa4ca4b3706400cfef023720dffc2d82b2c16eaed18b97c5890d

See more details on using hashes here.

File details

Details for the file notionctl-0.3.1-py3-none-any.whl.

File metadata

  • Download URL: notionctl-0.3.1-py3-none-any.whl
  • Upload date:
  • Size: 39.1 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: uv/0.10.11 {"installer":{"name":"uv","version":"0.10.11","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

File hashes

Hashes for notionctl-0.3.1-py3-none-any.whl
Algorithm Hash digest
SHA256 03ae6221d51d3097a6e1f09b0066c1a69361ab53389792134aafc729be13889a
MD5 025dd9f5cd7e1669d029164486bd7be8
BLAKE2b-256 a5ef780f14a3fde7a851c391805e3220dd3cdec71c396a99a3f477ea96b800c7

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page