@junovy/bookstack-cli
Version:
A CLI for viewing, searching, importing, and exporting BookStack content.
520 lines (359 loc) • 12.4 kB
Markdown
# BookStack CLI
[](https://github.com/Junovy-Hosting/bookstack-cli/actions/workflows/ci.yml)
[](https://github.com/Junovy-Hosting/bookstack-cli/actions/workflows/release.yml)
[](https://www.npmjs.com/package/@junovy/bookstack-cli)
[](https://www.npmjs.com/package/@junovy/bookstack-cli)
An Automated CLI for viewing, managing, importing, and exporting content for [BookStack](https://www.bookstackapp.com/), the open-source documentation platform.
## Quick Install / One‑Liners
Use the CLI immediately without installing globally:
- bunx
```bash
bunx @junovy/bookstack-cli books list
```
- npx
```bash
npx @junovy/bookstack-cli books list
```
- pnpm (dlx)
```bash
pnpx @junovy/bookstack-cli books list
```
Note: The published CLI binary uses Node to run. Ensure Node 18+ (or 20+) is available when using bunx/npx/pnpm dlx.
## Global Install
Install the CLI globally so `bookstack` is available on your PATH:
- npm
```bash
npm i -g @junovy/bookstack-cli
bookstack --help
```
- pnpm
```bash
pnpm add -g @junovy/bookstack-cli
bookstack --help
```
- bun
```bash
bun add -g @junovy/bookstack-cli
bookstack --help
```
(Requires Node on the system since the CLI shim uses Node.)
## Configuration
Before using the CLI, you need to configure your BookStack credentials:
1. Initialize a config file (optional if you prefer env vars):
```bash
bookstack config init
```
2. Edit the created `bookstack-config.json` file with your BookStack instance details:
```json
{
"url": "https://your-bookstack-instance.com",
"tokenId": "your-token-id",
"tokenSecret": "your-token-secret"
}
```
You can also provide credentials via environment variables, a .env file, or other standard config formats.
### Supported Config Sources (highest priority first)
- CLI flags: `--url`, `--token-id`, `--token-secret`
- Environment variables: `BOOKSTACK_URL`, `BOOKSTACK_TOKEN_ID`, `BOOKSTACK_TOKEN_SECRET`
- .env files in project root: `.env`, `.env.local`
- Config files (first found):
- `bookstack-config.json` (existing default)
- `bookstack.config.(json|yaml|yml|toml)`
- `.bookstackrc[.(json|yaml|yml|toml)]` or `.bookstackrc`
- `package.json` field `"bookstack": { ... }`
Example `.env`:
```bash
BOOKSTACK_URL=https://your-bookstack-instance.com
BOOKSTACK_TOKEN_ID=your-token-id
BOOKSTACK_TOKEN_SECRET=your-token-secret
```
To point at a specific config file format/path:
```bash
bookstack -- --config ./bookstack.config.yaml list books
```
## Usage
### Import Commands
Import a single file:
```bash
bookstack import path/to/file.md --book "My Book"
```
Import a directory (first-level folders become chapters; files become pages):
```bash
bookstack import path/to/directory --book "My Book"
```
Import with specific format:
```bash
bookstack import content.html --book "Documentation" --format html
```
Dry run to see what would be imported:
```bash
bookstack import content/ --book "Test" --dry-run
```
### List Commands
Books:
```bash
bookstack books list
```
Chapters (requires a book ID, name, or slug):
```bash
bookstack chapters list --book <id|name|slug>
```
Pages (optionally filter by book):
```bash
bookstack pages list
bookstack pages list --book <id|name|slug>
All list commands support `--json` for machine-readable output.
```
### Configuration Commands
Initialize config file:
```bash
bookstack config init
```
Show current configuration:
```bash
bookstack config show
```
### Options
Global options:
- `-u, --url <url>`: BookStack base URL
- `-i, --token-id <id>`: BookStack API token ID
- `-s, --token-secret <secret>`: BookStack API token secret
- `-c, --config <path>`: Config file path (auto-detected if omitted)
Import options:
- `-b, --book <name>`: Target book name or ID
- `-f, --format <format>`: Source format (markdown, html, json) - default: markdown
- `--dry-run`: Show what would be imported without making changes
For list commands, `--book` accepts ID, name, or slug.
## Supported File Formats
- Markdown (`.md`, `.markdown`)
- HTML (`.html`, `.htm`)
- Plain text (`.txt`)
## Directory Import Behavior
- Files in the root of the directory become pages directly within the target book.
- Each first-level subdirectory becomes a chapter in the book.
- Files within a subdirectory (and its nested folders) become pages inside that chapter. Nested folders are flattened into their chapter.
- Use `--flatten` to ignore chapters and import all files directly into the book.
### Book Metadata (.book-metadata.json)
Place an optional `.book-metadata.json` at the root of the directory to set the book’s name and description:
```json
{
"name": "Human Readable Book Name",
"description": "Optional description shown in BookStack"
}
```
Precedence for the book name is: CLI `--book` > `.book-metadata.json` > directory name.
### Chapter Metadata (.chapter-metadata.json)
Place an optional `.chapter-metadata.json` file inside any subdirectory to customize the chapter’s details:
```json
{
"name": "Human Readable Chapter Name",
"description": "Optional description shown in BookStack"
}
```
If no metadata is present, chapter names are derived by `--chapter-from`:
- `dir` (default): use the directory name
- `readme`: use the first Markdown heading (or first non-empty line) from `README.md`/`index.md` in that folder
### Import Options
- `--max-depth <n>`: Max recursion depth inside subdirectories (default: 10). Deeper nested folders are still flattened into their chapter.
- `--chapter-from <dir|readme>`: Source for chapter names when no metadata file is found.
- `--flatten`: Import everything directly into the book (no chapters).
## BookStack API Setup
To use this CLI, you need to:
1. Enable API access in your BookStack instance
2. Create an API token in your BookStack user settings
3. Get the Token ID and Token Secret from BookStack
## Development
Run in development mode:
```bash
bookstack <command>
```
Build for production:
```bash
bun run build
bun start <command>
```
## Global CLI
You can use a single `bookstack` command without `bun run`:
- Option A (recommended): build a standalone binary and put it on your PATH
```bash
bun run build
bun build src/bookstack-cli.ts --compile --outfile dist/bookstack
sudo install -m 0755 dist/bookstack /usr/local/bin/bookstack
bookstack --help
```
Using the provided Makefile instead:
```bash
make cli # builds dist/bookstack
sudo make install # installs to /usr/local/bin/bookstack
bookstack --help
```
- Option B: use the bundled wrapper without installing
```bash
./bin/bookstack --help
```
Tip: add the repo bin to PATH for convenience in this shell:
```bash
export PATH="$PWD/bin:$PATH"
bookstack --help
```
- Option C: global install via Bun (may depend on Bun version)
```bash
# If you hit a lockfile parse error, remove bun.lock and retry
rm -f bun.lock && bun install && bun install -g .
# Then
bookstack --help
```
## Uninstall
- If installed via Makefile:
```bash
sudo make uninstall # removes /usr/local/bin/bookstack
```
- If you manually installed the binary:
```bash
sudo rm -f /usr/local/bin/bookstack
```
- If installed globally by Bun:
```bash
# Bun usually places shims under ~/.bun/bin
rm -f ~/.bun/bin/bookstack
```
## Examples
Import a documentation directory:
```bash
bookstack import ./docs --book "API Documentation" --format markdown
```
Import a single HTML file:
```bash
bookstack import ./manual.html --book "User Manual" --format html
```
Test connection and list books:
```bash
bookstack books list
```
> Note: This project has migrated from npm to Bun. Use `bun install`, `bun run build`, and `bun start` for all tasks.
### Book Commands
Show details and contents of a book:
```bash
bookstack book show <id|name|slug>
# or if installed: bookstack book show <id|name|slug>
```
Export a book in various formats:
```bash
# markdown (to stdout)
bookstack book export <id|name|slug> --format markdown --stdout
# html to file
bookstack book export <id|name|slug> --format html --out ./book.html
# plaintext to default filename
bookstack book export <id|name|slug> --format plaintext
# pdf to file
bookstack book export <id|name|slug> --format pdf --out ./book.pdf
Note: PDF export can take longer to generate.
```
Show a book’s chapter/page tree:
```bash
bookstack book tree <id|name|slug>
# include IDs
bookstack book tree <id|name|slug> --ids
# only chapters or only pages
bookstack book tree <id|name|slug> --type chapter
bookstack book tree <id|name|slug> --type page
Output modes:
- `--ids` to include IDs in pretty output
- `--plain` to use simple bullets instead of tree glyphs
- `--json` to return a JSON structure of pages/chapters
```
Export a book's contents to a folder structure:
```bash
# write markdown files under ./<book-slug>/
bookstack book export-contents <id|name|slug> --format markdown
# choose directory and format
bookstack book export-contents <id|name|slug> --format html --dir ./out
# preview without writing
bookstack book export-contents <id|name|slug> --dry-run
```
### Search
Search across books/chapters/pages:
```bash
# free text
bookstack search "your query" --limit 50
# with filters (combined)
bookstack search cloud --type page,chapter --in-name intro --updated-after 2024-01-01 \
--tag docs --tag-kv topic=storage --sort-by last_commented
# json output
bookstack search cloud --type page --json
Global output flags:
- `--no-color` disable colors
- `-q, --quiet` suppress spinners and non-essential logs
```
Available filters (mapped to BookStack search syntax):
- `--type <list>` → `{type:page|chapter|book}`
- `--in-name <text>` → `{in_name:"text"}`
- `--in-body <text>` → `{in_body:"text"}`
- `--created-by <slug|me>` → `{created_by:...}`
- `--updated-by <slug|me>` → `{updated_by:...}`
- `--owned-by <slug|me>` → `{owned_by:...}`
- `--created-after <YYYY-MM-DD>` → `{created_after:...}`
- `--created-before <YYYY-MM-DD>` → `{created_before:...}`
- `--updated-after <YYYY-MM-DD>` → `{updated_after:...}`
- `--updated-before <YYYY-MM-DD>` → `{updated_before:...}`
- `--is-restricted` → `{is_restricted}`
- `--is-template` → `{is_template}`
- `--viewed-by-me` → `{viewed_by_me}`
- `--not-viewed-by-me` → `{not_viewed_by_me}`
- `--sort-by last_commented` → `{sort_by:last_commented}`
- `--tag <name>` → `[name]` (repeatable)
- `--tag-kv <name=value>` → `[name=value]` (repeatable)
### Shelves
List shelves:
````bash
bookstack shelves list
Show shelf with books:
```bash
bookstack shelves show <id|name|slug>
````
```
Show shelf and its books:
```
bookstack shelves show <id|name|slug>
````
### Chapter/Page Export
Export a chapter:
```bash
# markdown to stdout
bookstack chapter export <id|name|slug> --format markdown --stdout
# html to file
bookstack chapter export <id|name|slug> --format html --out ./chapter.html
# plaintext (default filename)
bookstack chapter export <id|name|slug> --format plaintext
# pdf
bookstack chapter export <id|name|slug> --format pdf --out ./chapter.pdf
````
PDF export warning: generation can take longer than text formats.
```bash
```
Export a page:
```bash
bookstack page export <id|name|slug> --format markdown --stdout
bookstack page export <id|name|slug> --format html --out ./page.html
bookstack page export <id|name|slug> --format plaintext
bookstack page export <id|name|slug> --format pdf --out ./page.pdf
```
### Chapter/Page Show & Find IDs
Inspect a chapter or page and find IDs for exports/automation:
```bash
# show chapter with its pages
bookstack chapter show <id|name|slug>
# show page details
bookstack page show <id|name|slug>
# find IDs (fuzzy search)
bookstack find "intro" --type page,chapter
```
### Help / Man Page
Show a concise CLI reference:
```bash
bookstack help
# or if installed: bookstack help
```
### Global Flags
- `--no-color` disable colors
- `-q, --quiet` suppress non-essential output