docs: rewrite README and update CHANGELOG for v0.2.0

This commit is contained in:
kryptomrx 2026-05-17 00:38:19 +02:00
parent 8576cc83a2
commit 38bf1f75c8
2 changed files with 267 additions and 53 deletions

View file

@ -1,26 +1,81 @@
# Changelog
All notable changes to noz-cli are documented here.
Format: [Keep a Changelog](https://keepachangelog.com/en/1.1.0/) — versioning follows [Semantic Versioning](https://semver.org/).
Format: [Keep a Changelog](https://keepachangelog.com/en/1.1.0/) · Versioning: [Semantic Versioning](https://semver.org/).
---
## [Unreleased]
## [0.2.0] — 2026-05-17
### Added
**REPL commands**
- `mv <old> <new>` — rename a note and atomically rewrite all inbound wikilinks and markdown links
- `mkdir <name>` — create a folder by writing a `_index.md`; navigates into the new folder immediately
- `link <source> <target>` — add a wikilink to the "Siehe auch" section (or create it); `--both` for bidirectional
- `search <query>` — full-text search via Meilisearch; context-aware (defaults to current topic); `--topic`, `--limit` flags
- `templates` — list available server-side note templates
- `new --template <name> <slug>` — create a note from a template with `{{title}}`, `{{date}}`, `{{topic}}` placeholders
- `cat --raw <slug>` — print raw markdown (default now renders via MarkdownRenderer)
- `clear` — clear the terminal screen
**PowerShell module**
- `Get-NozGraph` — all wikilink edges as `NozGraphEdge` objects; filterable by `-Source` / `-Target`
- `Find-NozNote` — Meilisearch full-text search; `-Topic`, `-Limit`
- `Measure-NozGarden` — garden-wide statistics: note counts by status/topic/lang, link count, orphan count
- `Set-NozNoteStatus` — patch the `status:` frontmatter field in place; `SupportsShouldProcess`
- `Get-NozOrphans` — notes with no incoming wikilinks; `-Topic` filter
- `Rename-NozNote` — wraps `NoteRenamer` for pipeline use; `-PassThru`, `-WhatIf`
- `Get-NozTemplate` — list server-side templates
- `Add-NozLink` — add wikilinks between notes; `-Both`, `-Section`
**Server API routes** (noz Next.js app)
- `GET /api/cli/graph` — full wikilink adjacency list from pre-built index
- `GET /api/cli/search` — Meilisearch / local-search with `?q`, `?topic`, `?limit`
- `PUT /api/cli/folders/[...path]` — create `_index.md` for a folder
- `GET /api/cli/templates` — list templates from `_templates/`
- `GET /api/cli/templates/[name]` — fetch a single template body
- `PUT /api/cli/templates/[name]` — create or update a template
**Core library**
- `NoteRenamer` — fetches inbound edges, creates new note, rewrites links, deletes old slug
- `NoteLinkHelper``AddLink()` inserts wikilinks into existing sections or appends new ones; `ApplyPlaceholders()` for template rendering
- `NozApiClient.GetGraphAsync()`, `SearchAsync()`, `GetTemplatesAsync()`, `GetTemplateAsync()`, `PutFolderIndexAsync()`
**Templates**
- Four sample templates in `content/noosphere/_templates/`: `rezept`, `buch-notiz`, `konzept`, `meeting`
### Fixed
- `walkNotes` now skips directories with `_` prefix (previously only filenames were checked — `_templates/` content was indexed as regular notes)
- Notes listing API now includes the `date` field
---
## [0.1.0] — 2026-05-16
### Added
- Interactive REPL with topic-based navigation (`cd`, `ls`, `ls -la`, `tree`)
- `cat` — print raw markdown of a note
- `edit` — open note in terminal editor (nano/vim) or VS Code (`-c` flag)
- `new` — create a new note from a template
- `rm` — delete a note
- `sync` — pull notes from server to local directory (parallel, hash-diffed)
- `push` — push local markdown files to server
- `search` — full-text search via Meilisearch
- `config` — view and set editor preferences
- `version` — show version and git hash
- JSON note cache (`~/.cache/noz/notes.json`) for instant startup + background refresh
- Cache timestamp displayed in startup stats line
- `cat` — render a note with MarkdownRenderer (headings, blockquotes, code blocks, inline formatting)
- `edit` — open note in terminal editor (nano/vim) or VS Code / Zed / Sublime (`-c`)
- `new` — create a note with frontmatter template, open in editor
- `rm` — delete a note from server
- `sync` — pull notes from server to local directory (parallel downloads, SHA-256 hash diffing, `--all`, `--dry-run`)
- `push` — push local `.md` files to server with slug validation
- `status` — diff between a local folder and the server
- `config` — view and set `editor` / `code_editor` preferences
- `version` — print version and git hash
- `help` — list all commands with usage
- `exit` / `quit` / `q` — quit the REPL
- JSON note cache (`~/.cache/noz/notes.json`) — instant startup, background refresh, `chmod 600`, atomic write
- Cache age shown in startup stats line ("vor 5 Min.")
- Ctrl+C: idle → exit REPL; during command → cancel command only
- Native AOT binary for macOS arm64 (~7.6 MB, no runtime required)
- Tab completion for commands, slugs and folder segments
- Tab completion for commands, slugs, and folder segments
- `SlugGuard` — path traversal prevention for all slug inputs and file operations
- `MarkdownRenderer` — segment-based inline escaping (prevents Spectre markup injection from note content)
- PowerShell module `Noz` with `Get-NozNote`, `Get-NozNoteContent`, `Set-NozNote`, `New-NozNote`, `Remove-NozNote`
- xUnit test suite (52 tests): `SlugGuardTests`, `ReplContextTests`, `NotesCacheTests`, `NoteRenamerTests`, `NoteLinkHelperTests`
- Forgejo Actions CI pipeline (`.forgejo/workflows/ci.yml`): build + test on every push/PR
- Version string from `AssemblyInformationalVersion` with embedded git short hash

239
README.md
View file

@ -1,79 +1,214 @@
# noz-cli
A terminal REPL for [noz](https://github.com/kryptomrx/noz) — a self-hosted digital garden built with Next.js.
A terminal REPL and PowerShell module for [noz](https://git.kryptomrx.de/krypto/noz) — a self-hosted digital garden built with Next.js.
Navigate, read, and edit your notes from the command line. Native AOT binary, no .NET runtime required.
Navigate, create, and manage your notes from the command line. Ships as a Native AOT binary (~7.6 MB, no .NET runtime required) and a PowerShell module for scripting and automation.
---
## Install
Download the latest binary from [Releases](../../releases) and place it on your PATH:
### macOS / Linux — binary
Download from [Releases](../../releases) and place on your PATH:
```bash
# macOS (Apple Silicon)
curl -L https://github.com/kryptomrx/noz-cli/releases/latest/download/noz-osx-arm64 -o /usr/local/bin/noz
chmod +x /usr/local/bin/noz
# macOS Apple Silicon
curl -L https://git.kryptomrx.de/krypto/noz-cli/releases/latest/download/noz-osx-arm64 \
-o /usr/local/bin/noz && chmod +x /usr/local/bin/noz
```
### PowerShell module
Requires PowerShell 7.2+ and .NET 8.
```powershell
git clone https://git.kryptomrx.de/krypto/noz-cli
cd noz-cli
./Noz.PowerShell/Install-NozModule.ps1
```
---
## Setup
```bash
noz init https://your-noz-instance.com your-api-token
```
This writes `~/.config/noz/config.json`.
Writes `~/.config/noz/config.json`. The token is the CLI token configured in your `noosphere.toml` under `[cli]`.
## Usage
---
```
## REPL
```bash
noz
```
Starts the interactive REPL. Type `help` for a list of commands.
Starts the interactive REPL. A local note cache (`~/.cache/noz/notes.json`) is used for instant startup; a background refresh runs silently.
### Navigation
```
~ » ls # list topics
~ » cd psychologie # enter a topic
~/psychologie » ls -la # detailed view with status, date, title
~/psychologie » tree # full hierarchy as a tree
~/psychologie » cd .. # go up
```
| Command | Description |
|---------|-------------|
| `ls` | List topics (at root) or notes in the current folder |
| `ls -la` | Detailed list with status, date, language |
| `cd <topic>` | Enter a topic or sub-folder |
| `cd ..` | Go up one level |
| `tree` | Full hierarchy as a tree |
### Notes
```
~ » cat psychologie/flow-theorie # print raw markdown
~ » edit flow-theorie # open in terminal editor
~ » edit -c flow-theorie # open in VS Code
~ » new meine-neue-notiz # create note from template
~ » rm alte-notiz # delete a note
```
| Command | Description |
|---------|-------------|
| `cat <slug>` | Print a note (rendered markdown) |
| `cat --raw <slug>` | Print raw markdown |
| `new <name>` | Create a note and open in editor |
| `new -c <name>` | Create a note and open in VS Code |
| `new --template <name> <slug>` | Create from a template |
| `edit <slug>` | Edit a note in terminal editor |
| `edit -c <slug>` | Edit in VS Code |
| `mv <old> <new>` | Rename a note — rewrites all inbound wikilinks |
| `rm <slug>` | Delete a note |
| `search <query>` | Full-text search (Meilisearch) |
| `search <query> --topic <topic>` | Search within a topic |
### Folders
| Command | Description |
|---------|-------------|
| `mkdir <name>` | Create a folder (writes `_index.md`, navigates in) |
### Linking
| Command | Description |
|---------|-------------|
| `link <source> <target>` | Add a wikilink from source to target |
| `link <source> <target> --both` | Bidirectional link |
### Templates
| Command | Description |
|---------|-------------|
| `templates` | List available templates |
| `new --template <name> <slug>` | Create a note from a template |
Templates live in `content/noosphere/_templates/<name>.md` on the server. Placeholders: `{{title}}`, `{{topic}}`, `{{date}}`, `{{status}}`, `{{lang}}`.
### Sync
```
~ » sync ~/vault # pull changed notes to local folder
~ » sync ~/vault --all # pull everything (ignore local hashes)
~ » sync ~/vault --dry-run # preview what would be downloaded
~ » push ~/vault # push local .md files to server
```
| Command | Description |
|---------|-------------|
| `sync <local-path>` | Pull changed notes from server to local folder |
| `sync <local-path> --all` | Pull everything (ignore local hashes) |
| `sync <local-path> --dry-run` | Preview what would be downloaded |
| `push <local-path>` | Push local `.md` files to server |
| `status <local-path>` | Show diff between local folder and server |
### Other
| Command | Description |
|---------|-------------|
| `version` | Show version and git hash |
| `config` | Show editor settings |
| `config editor <name>` | Set terminal editor |
| `config code-editor <name>` | Set GUI editor |
| `clear` | Clear the screen |
| `help` | List all commands |
| `exit` | Quit |
**Ctrl+C** while idle exits the REPL. During a command it cancels only that command.
---
## PowerShell Module
After installing, import with:
```powershell
Import-Module Noz
```
~ » version # show version + git hash
~ » config # show editor settings
~ » config editor nano # set terminal editor
~ » config code-editor code # set GUI editor
~ » exit
### Note commands
```powershell
# List and filter notes
Get-NozNote
Get-NozNote -Topic psychologie
Get-NozNote -Status evergreen
Get-NozNote -Lang de
# Read content
Get-NozNoteContent -Slug psychologie/flow-theorie
# Create / update / delete
New-NozNote -Slug kochen/pasta -Title "Pasta Carbonara" -Topic kochen
Set-NozNote -Slug psychologie/flow-theorie -Markdown $content
Remove-NozNote -Slug alte-notiz
# Rename (rewrites all inbound links)
Rename-NozNote -Slug psychologie/old -NewSlug psychologie/new
# Change status
Set-NozNoteStatus -Slug psychologie/flow-theorie -Status evergreen
```
### Search
```powershell
Find-NozNote "flow"
Find-NozNote "hydroponik" -Topic biosysteme -Limit 5
```
### Graph & analysis
```powershell
# All wikilink edges
Get-NozGraph
Get-NozGraph -Source psychologie/flow
# Notes with no incoming links
Get-NozOrphans
Get-NozOrphans -Topic psychologie
# Garden-wide statistics
Measure-NozGarden
# Link two notes
Add-NozLink -Source psychologie/flow -Target biosysteme/brs-konzept
Add-NozLink -Source a -Target b -Both
```
### Templates
```powershell
Get-NozTemplate
Get-NozTemplate rezept
```
### Pipeline examples
```powershell
# Promote all seed notes in a topic to budding
Get-NozNote -Topic psychologie -Status seed |
Set-NozNoteStatus -Status budding -WhatIf
# Export all evergreen notes as markdown files
Get-NozNote -Status evergreen |
ForEach-Object { Get-NozNoteContent $_.Slug } |
ForEach-Object { Set-Content "$($_.Slug).md" $_.Markdown }
# Find orphans and link them to a topic overview
Get-NozOrphans -Topic biosysteme |
Add-NozLink -Target biosysteme/uebersicht
```
---
## Configuration
Editor preferences are stored in `~/.config/noz/config.json`:
`~/.config/noz/config.json`:
```json
{
@ -84,19 +219,41 @@ Editor preferences are stored in `~/.config/noz/config.json`:
}
```
Editor is auto-detected from `$EDITOR` if not set. VS Code, Zed, and Sublime Text are detected automatically for `-c` mode.
---
## Server-side setup
The CLI needs the `[cli]` block in your `noosphere.toml`:
```toml
[cli]
token = "your-secret-token"
allow_push = true
allow_delete = true
allow_vault = false
allow_rebuild = false
```
---
## Building from source
Requires [.NET 10 SDK](https://dotnet.microsoft.com/download) and `clang`.
```bash
git clone https://github.com/kryptomrx/noz-cli
git clone https://git.kryptomrx.de/krypto/noz-cli
cd noz-cli
# Run (no AOT)
# Run without AOT
dotnet run --project NozCli
# Native AOT binary (macOS arm64)
# Native AOT binary — macOS Apple Silicon
dotnet publish NozCli/NozCli.csproj -r osx-arm64 -c Release
# Run tests
dotnet test NozCli.Tests/NozCli.Tests.csproj -c Release
```
On macOS, AOT linking requires OpenSSL via Homebrew:
@ -105,7 +262,9 @@ On macOS, AOT linking requires OpenSSL via Homebrew:
brew install openssl
```
---
## License
[Polyform Noncommercial 1.0.0](LICENSE) — free for personal and non-commercial use.
For commercial licensing, contact [Bruno Deanoz](mailto:bruno.deanoz1@gmail.com).
Commercial licensing: [bruno.deanoz1@gmail.com](mailto:bruno.deanoz1@gmail.com).