# Fabric User Guide

Fabric is an open-source framework for **augmenting humans using AI**. Instead of scattering useful prompts across dozens of chat apps and notes, Fabric collects them as reusable, version-controlled **Patterns** (Markdown prompt files) and lets you apply them to any text from your command line, a web app, or a REST API. Pipe in an article, a YouTube transcript, a web page, or a code base, choose a Pattern like `summarize` or `extract_wisdom`, and get a focused, repeatable result from the AI provider of your choice.

This guide covers everything you need to install Fabric, configure an AI provider, run Patterns, and use Fabric's advanced features — strategies, sessions, contexts, template variables, extensions, the web interface, and the helper tools `to_pdf`, `code2context`, and `generate_changelog`.

> [!NOTE]
> Fabric is written in Go. There is **no Python runtime** in the current version. If you used the older Python Fabric, see [Migrating from the Python Version](#10-migrating-from-the-python-version).

---

## 1. Quick Start

Three commands take you from zero to your first AI-augmented result.

```bash
# 1. Install (Unix/Linux/macOS)
curl -fsSL https://raw.githubusercontent.com/danielmiessler/fabric/main/scripts/installer/install.sh | bash

# 2. Configure a provider, patterns, and a default model (interactive)
fabric --setup

# 3. Run your first Pattern
echo "Fabric organizes AI prompts as reusable patterns." | fabric --pattern summarize
```

Expected result: the AI provider you configured returns a summary printed to your terminal.

```text
# ONE SENTENCE SUMMARY:
Fabric is a framework that turns reusable AI prompts (patterns) into a command-line workflow.

# MAIN POINTS:
1. Patterns are reusable, Markdown-based prompts.
...
```

> [!TIP]
> Add `--stream` (`-s`) to see output appear token-by-token as the model generates it, instead of waiting for the full response.

```bash
echo "Long article text..." | fabric --stream --pattern summarize
```

---

## 2. Installation

Fabric ships as a single self-contained binary. Choose the method that fits your platform. After installing, continue to [Setup](#3-setup-fabric---setup).

### 2.1 One-line install (recommended)

=== "Unix / Linux / macOS"

    ```bash
    curl -fsSL https://raw.githubusercontent.com/danielmiessler/fabric/main/scripts/installer/install.sh | bash
    ```

=== "Windows (PowerShell)"

    ```powershell
    iwr -useb https://raw.githubusercontent.com/danielmiessler/fabric/main/scripts/installer/install.ps1 | iex
    ```

### 2.2 Package managers

=== "macOS (Homebrew)"

    ```bash
    brew install fabric-ai
    ```

=== "Arch Linux (AUR)"

    ```bash
    yay -S fabric-ai
    ```

=== "Windows (winget)"

    ```powershell
    winget install danielmiessler.Fabric
    ```

=== "Windows (Scoop)"

    ```powershell
    scoop install fabric-ai
    ```

> [!IMPORTANT]
> Homebrew and the Arch AUR install the binary as **`fabric-ai`**, not `fabric`. Add this alias to your shell startup file so the rest of this guide's commands work as written:
>
> ```bash
> alias fabric='fabric-ai'
> ```

### 2.3 From source

Requires [Go](https://go.dev/doc/install) (the project targets a recent Go toolchain).

```bash
go install github.com/danielmiessler/fabric/cmd/fabric@latest
```

This places the `fabric` binary in `$GOPATH/bin` (usually `~/go/bin`). Make sure that directory is on your `PATH` (see [Environment Variables](#22-path-environment-variables-from-source-installs)).

### 2.4 Docker

Pre-built images are published to Docker Hub and GHCR.

```bash
# Check the version
docker run --rm -it kayvan/fabric:latest --version

# First-time setup (persists config to a host directory)
mkdir -p $HOME/.fabric-config
docker run --rm -it -v $HOME/.fabric-config:/home/appuser/.config/fabric kayvan/fabric:latest --setup

# Run a pattern
docker run --rm -it -v $HOME/.fabric-config:/home/appuser/.config/fabric kayvan/fabric:latest -p summarize

# Run the REST API server on port 8080
docker run --rm -it -p 8080:8080 -v $HOME/.fabric-config:/home/appuser/.config/fabric kayvan/fabric:latest --serve
```

> [!NOTE]
> Images: `kayvan/fabric` (Docker Hub) and `ghcr.io/ksylvan/fabric` (GHCR). The `-v` mount keeps your keys and patterns between runs.

### 2.5 PATH environment variables (from-source installs)

If you installed with `go install`, add Go's binary directory to your `PATH`. Add the following to `~/.bashrc` (Linux) or `~/.zshrc` (macOS).

=== "Intel macOS / Linux"

    ```bash
    export GOROOT=/usr/local/go
    export GOPATH=$HOME/go
    export PATH=$GOPATH/bin:$GOROOT/bin:$HOME/.local/bin:$PATH
    ```

=== "Apple Silicon macOS"

    ```bash
    export GOROOT=$(brew --prefix go)/libexec
    export GOPATH=$HOME/go
    export PATH=$GOPATH/bin:$GOROOT/bin:$HOME/.local/bin:$PATH
    ```

### 2.6 Verify the install

```bash
fabric --version
```

```text
v1.4.452
```

If you see a version string, Fabric is installed. If the command is not found, revisit your `PATH` settings.

---

## 3. Setup (`fabric --setup`)

Before Fabric can talk to an AI model you must configure at least one provider, download the built-in Patterns, and pick a default model. The interactive setup wizard does all three.

```bash
fabric --setup
```

On a **first run**, the wizard automatically:

1. Downloads the built-in **Patterns** into `~/.config/fabric/patterns`.
2. Downloads the prompt **Strategies** into `~/.config/fabric/strategies`.
3. Prompts you to configure an **AI provider** (enter the number of the provider, then supply its API key or URL).
4. Asks you to choose a **default vendor and model**.

When setup finishes it prints a validation summary:

```text
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
Setup Validation
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
  ✓ AI provider configured
  ✓ Default model set (OpenAI / gpt-4o)
  ✓ Patterns installed
  ✓ Strategies installed
```

Running `fabric --setup` again later opens a **menu** where you can configure additional providers and optional tools (YouTube, Jina, Spotify, Language, Custom Patterns) one at a time.

> [!TIP]
> To reset a stored value during setup, type `reset` at the prompt. To accept the current value, press Enter on an empty line.

Configuration is written to `~/.config/fabric/.env`. The config directory layout is:

```text
~/.config/fabric/
├── .env                 # API keys, default model, tool config
├── config.yaml          # optional YAML defaults (see §8.3)
├── patterns/            # built-in + downloaded patterns
├── strategies/          # prompt strategy JSON files
├── contexts/            # saved contexts
├── sessions/            # saved chat sessions
└── extensions/          # registered extensions + extensions.yaml
```

### 3.1 Supported AI providers

Fabric supports a wide range of providers. The native integrations have first-class clients; the OpenAI-compatible providers are reached through a shared client.

| Native integrations | OpenAI-compatible providers |
|---|---|
| OpenAI | Abacus, AIML, Cerebras |
| OpenAI Codex (ChatGPT/Codex subscription) | DeepSeek, DigitalOcean |
| Anthropic (Claude) | GitHub Models, GrokAI, Groq |
| Google Gemini | Langdock, LiteLLM, MiniMax |
| Ollama (local models) | Mistral, Novita AI |
| Azure OpenAI | OpenRouter, SiliconCloud |
| Amazon Bedrock | Together, Venice AI, Z AI |
| Vertex AI, LM Studio, Perplexity | |

List everything Fabric can see in your install:

```bash
fabric --listvendors      # configured + available vendors
fabric --listmodels       # all models, grouped by vendor
```

> [!NOTE]
> You only need **one** provider to use Fabric. Configure more later with `fabric --setup` whenever you want to switch between them.

---

## 4. Core Usage

Fabric reads input from **stdin** (a pipe) and/or a **command-line message argument**, applies an optional Pattern, sends the result to a model, and prints the response.

### 4.1 The three ways to give Fabric input

```bash
# 1. Pipe via stdin
pbpaste | fabric --pattern summarize

# 2. Direct message argument
fabric --pattern summarize "Summarize the theory of relativity"

# 3. Both — the argument and the piped text are combined
echo "extra context" | fabric -p summarize "Focus on the key risks"
```

> [!TIP]
> On macOS, `pbpaste` pipes your clipboard. On Windows use `Get-Clipboard`; on Linux use `xclip -selection clipboard -o`. See [Clipboard helpers](#126-clipboard-pbpaste-equivalents).

### 4.2 Running a Pattern

A **Pattern** is a named prompt. Apply one with `-p`/`--pattern`:

```bash
pbpaste | fabric --pattern extract_wisdom
```

```text
# SUMMARY
A 12-minute talk on...

# IDEAS
- ...
```

List all available Patterns:

```bash
fabric --listpatterns
```

Read a Pattern's raw prompt text without running it:

```bash
fabric --readpattern summarize
```

Show the most recently added Patterns:

```bash
fabric --latest 10        # the 10 newest patterns
```

### 4.3 Choosing a model and vendor

By default Fabric uses the default model from setup. Override per-command:

```bash
# Pick a model by name (Fabric finds the vendor automatically)
pbpaste | fabric -p summarize -m gpt-4o

# Disambiguate when multiple vendors offer the same model name
fabric -p summarize -V "LM Studio" -m openai/gpt-oss-20b

# Vendor-prefixed model names also work
fabric -p summarize -m ollama/llama3
```

> [!NOTE]
> Model names are matched case-insensitively. If a model is offered by more than one vendor and you don't pass `-V`, Fabric picks the first match and prints a warning telling you to specify `--vendor`.

### 4.4 Streaming, copying, and saving output

```bash
# Stream tokens as they arrive
pbpaste | fabric -sp summarize

# Copy the result to your clipboard
pbpaste | fabric -p summarize --copy

# Write the result to a file (will NOT overwrite an existing file)
pbpaste | fabric -p summarize -o summary.md
```

> [!WARNING]
> `-o`/`--output` refuses to overwrite an existing file and errors with `File "summary.md" already exists. Not overwriting it.` Choose a new filename or remove the old one first.

### 4.5 Tuning the model

These flags control generation parameters (where the provider supports them):

```bash
fabric -p summarize -t 0.3            # lower temperature = more deterministic
fabric -p summarize --seed 42         # reproducible output (if supported)
fabric -p summarize --thinking high   # more reasoning effort on reasoning models
fabric -p summarize --raw             # send no chat options; use model defaults
```

> [!NOTE]
> `--raw` only affects OpenAI-compatible providers. Anthropic models always use smart parameter selection to comply with model-specific requirements.

---

## 5. Common Tasks (Recipes)

Concrete, copy-paste-ready examples for the things people use Fabric for most.

### 5.1 Summarize an article from your clipboard

```bash
pbpaste | fabric --pattern summarize
```

### 5.2 Extract the key insights from a YouTube video

Fabric can pull a video's transcript (and optionally comments, metadata, or visual frames) and feed it to a Pattern.

```bash
fabric -y "https://youtube.com/watch?v=uXs-zPc63kM" --stream --pattern extract_wisdom
```

| Goal | Command |
|---|---|
| Transcript → pattern | `fabric -y "URL" -p extract_wisdom` |
| Transcript with timestamps | `fabric -y "URL" --transcript-with-timestamps -p summarize` |
| Comments too | `fabric -y "URL" --comments -p analyze_comments` |
| Video metadata | `fabric -y "URL" --metadata` |
| Whole playlist | `fabric -y "PLAYLIST_URL" --playlist -o out.md` |
| Visual frames (OCR) | `fabric -y "URL" --visual -p summarize` |

> [!NOTE]
> YouTube transcript extraction works without an API key. Fetching **metadata** and **comments** requires a YouTube Data API key configured via `fabric --setup` → YouTube. Visual extraction requires `yt-dlp` and `ffmpeg` installed.

You can pass extra flags to the underlying `yt-dlp`:

```bash
fabric -y "URL" --yt-dlp-args "--cookies-from-browser brave" -p extract_wisdom
```

### 5.3 Analyze a web page

Fabric scrapes a URL to clean Markdown (via Jina AI) before sending it to the model.

```bash
fabric -u https://example.com/post -p analyze_claims
```

Search the web for an answer with Jina:

```bash
fabric -q "What changed in HTTP/3?" -p summarize
```

> [!NOTE]
> `-u`/`--scrape_url` and `-q`/`--scrape_question` require Jina configured via `fabric --setup`. If not configured you'll see `Jina is not configured`.

### 5.4 Clean up messy HTML before processing

```bash
cat page.html | fabric --readability -p summarize
```

`--readability` converts raw HTML into a clean, readable view first.

### 5.5 Attach an image (vision models)

```bash
fabric -a ./diagram.png -m gpt-4o "Describe what this diagram shows"
```

`-a`/`--attachment` accepts a file path or a URL and can be repeated for multiple attachments.

### 5.6 Generate an image

```bash
fabric "A watercolor fox in a misty forest" -m gpt-image-1 --image-file fox.png
```

| Flag | Purpose | Allowed values |
|---|---|---|
| `--image-file` | Output path (extension sets format) | `.png`, `.jpg`/`.jpeg`, `.webp` |
| `--image-size` | Dimensions | `1024x1024`, `1536x1024`, `1024x1536`, `auto` |
| `--image-quality` | Quality | `low`, `medium`, `high`, `auto` |
| `--image-compression` | 0–100 (JPEG/WebP only) | integer 0–100 |
| `--image-background` | Background | `opaque`, `transparent` (PNG/WebP only) |

> [!WARNING]
> `--image-file` will not overwrite an existing file. Compression is only valid for JPEG/WebP; a transparent background is only valid for PNG/WebP. Image flags require `--image-file` to also be set.

### 5.7 Transcribe audio or video

```bash
fabric --transcribe-file talk.mp3 --transcribe-model whisper-1 -p summarize
```

For files larger than 25 MB, split them automatically (requires `ffmpeg`):

```bash
fabric --transcribe-file long.mp4 --transcribe-model whisper-1 --split-media-file
```

List transcription models:

```bash
fabric --list-transcription-models
```

```text
Available transcription models:
  whisper-1
  gpt-4o-mini-transcribe
  gpt-4o-transcribe
```

### 5.8 Generate speech (text-to-speech)

Use a TTS-capable model and an audio output file:

```bash
echo "Welcome to Fabric." | fabric -m gpt-4o-mini-tts --voice Kore -o welcome.wav
```

List available Gemini TTS voices:

```bash
fabric --list-gemini-voices
```

> [!NOTE]
> The output file extension must be an audio type (`.wav`, `.mp3`, `.m4a`, `.aac`, `.ogg`, `.flac`). Fabric requires a TTS model when the output is audio, and rejects a TTS model when the output is not audio.

### 5.9 Get a desktop notification when a long job finishes

```bash
pbpaste | fabric -p analyze_paper --notification
```

Use a custom notification command instead of the built-in one (it receives the title as `$1` and message as `$2`):

```bash
fabric -p summarize --notification-command 'notify-send "$1" "$2"'
```

### 5.10 Read a podcast's metadata from Spotify

```bash
fabric --spotify "https://open.spotify.com/episode/XXXX" -p summarize
```

Requires Spotify configured via `fabric --setup`.

### 5.11 Turn every Pattern into a shell command (aliases)

Add this to `~/.zshrc` or `~/.bashrc` to call `summarize` directly instead of `fabric --pattern summarize` (PowerShell equivalent is in the project README):

```bash
for pattern_file in $HOME/.config/fabric/patterns/*; do
    pattern_name="$(basename "$pattern_file")"
    alias_name="${FABRIC_ALIAS_PREFIX:-}${pattern_name}"
    alias "$alias_name"="fabric --pattern $pattern_name"
done

# Convenience function for YouTube
yt() {
    transcript_flag="--transcript"
    if [ "$1" = "-t" ] || [ "$1" = "--timestamps" ]; then
        transcript_flag="--transcript-with-timestamps"; shift
    fi
    fabric -y "$1" $transcript_flag
}
```

```bash
pbpaste | summarize
yt -t "https://www.youtube.com/watch?v=4b0iet22VIk"
```

> [!TIP]
> Set `FABRIC_ALIAS_PREFIX` before the loop if you want all aliases to share a prefix (e.g. `f_summarize`). A PowerShell equivalent is in the project README.

---

## 6. Workflows

Combine Fabric's features for repeatable, multi-step results.

### 6.1 Stack a prompt strategy on top of a Pattern

A **strategy** prepends a reasoning instruction (like Chain-of-Thought) to the system prompt.

```bash
echo "Analyze this code" | fabric --strategy cot -p analyze_code
```

List strategies:

```bash
fabric --liststrategies
```

| Strategy | Name | What it does |
|---|---|---|
| `cot` | Chain-of-Thought | Step-by-step reasoning |
| `cod` | Chain-of-Draft | Iterative drafting, ≤5 words per step |
| `tot` | Tree-of-Thought | Multiple reasoning paths, pick the best |
| `aot` | Atom-of-Thought | Break into smallest independent sub-problems |
| `ltm` | Least-to-Most | Solve from easiest to hardest sub-problem |
| `self-consistent` | Self-Consistency | Multiple paths, choose most consistent |
| `self-refine` | Self-Refinement | Answer, critique, refine |
| `reflexion` | Reflexion | Answer, brief critique, refined answer |
| `standard` | Standard | Direct answer, no explanation |

The strategy text is combined with your Pattern as: **strategy → context → pattern → your input**.

### 6.2 Multi-turn conversations with sessions

A **session** persists the conversation history so follow-up messages have memory.

```bash
fabric --session research "What is differential privacy?"
fabric --session research "Now give me three real-world examples."   # remembers the first turn

fabric --listsessions                 # list saved sessions
fabric --printsession research        # print a session's contents
fabric --wipesession research         # delete a session
```

### 6.3 Reusable background with contexts

A **context** is reusable text prepended to your prompt — handy for a persona or standing instructions.

```bash
# Create a context file at ~/.config/fabric/contexts/security
echo "You are a senior application security engineer. Be terse and cite CWE IDs." \
  > ~/.config/fabric/contexts/security

fabric --context security -p analyze_risk "Review this design doc"

fabric --listcontexts                 # list contexts
fabric --printcontext security        # print a context
fabric --wipecontext security         # delete a context
```

### 6.4 Generate a PDF from a Pattern's output

The `write_latex` Pattern plus the `to_pdf` helper produces a finished PDF:

```bash
echo "ai security primer" | fabric --pattern write_latex | to_pdf
```

This writes `output.pdf` in the current directory. See [Helper Apps](#123-to_pdf).

### 6.5 Have AI edit your code (`create_coding_feature`)

Use the `code2context` helper to package a code directory, then ask Fabric to implement a change. When you run the `create_coding_feature` Pattern, Fabric parses the model's file-change block and applies the create/update operations to your working directory.

```bash
code2context ./src "Add input validation to all user inputs" | fabric -p create_coding_feature
```

```text
...summary of changes...
✓ File changes applied successfully.
Review changes with: git diff
```

> [!CAUTION]
> `create_coding_feature` writes files to disk in your current project. Run it inside a git repository and review with `git diff` before committing. Fabric rejects paths containing `..` and files larger than 10 MB as a safety measure.

### 6.6 Preview a prompt without spending tokens (dry run)

```bash
echo "test input" | fabric --dry-run -p summarize
```

`--dry-run` prints exactly what would be sent to the model without making an API call — ideal for debugging Patterns and verifying input formatting.

---

## 7. Patterns, Variables, and Extensions

This section explains how Patterns work and how to make them dynamic.

### 7.1 What a Pattern is

A Pattern is a directory under `~/.config/fabric/patterns/<name>/` containing a `system.md` file (the system prompt). Fabric ships hundreds of them — for example `summarize`, `extract_wisdom`, `analyze_claims`, `write_essay`, `create_coding_feature`, `explain_code`, `improve_writing`, and many more. Browse them in the [`data/patterns`](https://github.com/danielmiessler/fabric/tree/main/data/patterns) directory of the project.

> [!TIP]
> Even without the CLI, the Patterns are useful on their own — copy any `system.md` into ChatGPT or another tool.

Update the built-in Patterns to the latest versions at any time:

```bash
fabric --updatepatterns
```

### 7.2 Custom Patterns

Keep your own Patterns separate from the built-in ones so updates never overwrite them.

1. Run `fabric --setup`, choose **Custom Patterns**, and enter a directory (e.g. `~/my-custom-patterns`).
2. Create a Pattern:

   ```bash
   mkdir -p ~/my-custom-patterns/my-analyzer
   echo "You are an expert analyzer of ..." > ~/my-custom-patterns/my-analyzer/system.md
   ```

3. Use it:

   ```bash
   fabric --pattern my-analyzer "analyze this text"
   ```

How it behaves:

- **Priority** — a custom Pattern overrides a built-in one with the same name.
- **Integrated** — custom Patterns appear in `fabric --listpatterns`.
- **Update-safe** — `fabric --updatepatterns` never touches your custom directory.

### 7.3 Pattern variables

Patterns can contain `{{variable}}` placeholders. Supply values with `-v`/`--variable` using the `#name:value` form:

```bash
fabric -p my_pattern -v=#role:expert -v=#points:30 "input text"
```

The special variable `{{input}}` is replaced with your message/stdin. Related flags:

| Flag | Effect |
|---|---|
| `--input-has-vars` | Also expand `{{variable}}` placeholders found in **your input** (not just the Pattern) |
| `--no-variable-replacement` | Disable all Pattern variable replacement |

> [!WARNING]
> If a Pattern references a variable you didn't supply, Fabric stops with `missing required variable: <name>`. Provide every variable the Pattern uses, or use `--no-variable-replacement`.

### 7.4 Built-in template plugins

Inside a Pattern you can call built-in helpers with `{{plugin:NAMESPACE:OPERATION:VALUE}}`. They are resolved before the prompt is sent.

| Namespace | Operations | Example |
|---|---|---|
| `text` | `upper`, `lower`, `title`, `trim` | `{{plugin:text:upper:hello}}` → `HELLO` |
| `datetime` | `now`, `time`, `unix`, `today`, `full`, `month`, `year`, `startofweek`, `endofweek`, `startofmonth`, `endofmonth`, `startofhour`, `endofhour`, `rel:<offset>` | `{{plugin:datetime:today}}` → `2026-06-05` |
| `file` | `read:PATH`, `tail:PATH\|N`, `exists:PATH`, `size:PATH`, `modified:PATH` | `{{plugin:file:read:~/notes.md}}` |
| `fetch` | `get:URL` (text content, ≤1 MB) | `{{plugin:fetch:get:https://example.com/data.json}}` |
| `sys` | `hostname`, `user`, `os`, `arch`, `env:VAR`, `pwd`, `home` | `{{plugin:sys:os}}` → `linux` |

Relative datetime examples: `{{plugin:datetime:rel:-1h}}` (RFC3339, one hour ago), `{{plugin:datetime:rel:-2d}}` (date two days ago), `{{plugin:datetime:rel:1w}}`, `{{plugin:datetime:rel:3m}}`, `{{plugin:datetime:rel:1y}}`.

> [!NOTE]
> The `file` and `fetch` plugins enforce safety limits: no `..` path traversal, a 1 MB size cap, and `fetch` only accepts text-like content types (text/*, JSON, XML, YAML).

### 7.5 Extensions

Extensions let a Pattern call an external program via `{{ext:NAME:OPERATION:VALUE}}`. They are defined in a YAML file and registered with Fabric, which records a hash of both the config and the executable so a tampered binary is detected at run time.

```bash
fabric --addextension ./my-extension.yaml   # register
fabric --listextensions                      # list registered extensions
fabric --rmextension my-extension            # remove by name
```

A minimal extension definition:

```yaml
name: word-count
executable: /usr/bin/wc
type: executable
timeout: 30s
description: "Count words"
version: "1.0.0"
operations:
  count:
    cmd_template: "{{executable}} -w {{value}}"
config:
  output:
    method: stdout
```

Use it inside a Pattern's `system.md`:

```text
The input file has {{ext:word-count:count:/path/to/file.txt}} words.
```

> [!IMPORTANT]
> Extensions only work **within Pattern files**, not via direct stdin. Multiple `|`-separated values become numbered variables (`{{1}}`, `{{2}}`, …) inside the command template. See the project's [Extension Guide](https://github.com/danielmiessler/fabric/blob/main/internal/plugins/template/Examples/README.md).

> [!CAUTION]
> Extensions run shell commands on your machine. Only register extensions whose config and executable you trust.

---

## 8. Configuration for Day-to-Day Use

You mostly configure Fabric through `fabric --setup`, but a few options are worth knowing.

### 8.1 Per-pattern model mapping

Pin a specific vendor/model to a Pattern with an environment variable named `FABRIC_MODEL_<PATTERN_NAME>` (uppercase, hyphens become underscores), valued `vendor|model`:

```bash
export FABRIC_MODEL_SUMMARIZE="Anthropic|claude-opus-4-5"
export FABRIC_MODEL_ANALYZE_CODE="OpenAI|gpt-4o"
```

Now `fabric -p summarize` uses Claude unless you override `-m` on the command line. Put these in your shell startup file to make them permanent.

### 8.2 Change the default model

```bash
fabric --changeDefaultModel
```

### 8.3 YAML config file

Any flag with a YAML name can be set in `~/.config/fabric/config.yaml` (or a custom path via `--config`). CLI flags always override YAML values.

```yaml
# ~/.config/fabric/config.yaml
pattern: summarize
model: gpt-4o
vendor: OpenAI
temperature: 0.7
topp: 0.9
stream: true
suppressThink: false
modelContextLength: 2048
```

```bash
fabric --config ~/.config/fabric/config.yaml "summarize this"
```

### 8.4 Suppressing model "thinking" output

Reasoning models sometimes emit `<think>…</think>` blocks. Hide them:

```bash
fabric -p summarize --suppress-think
fabric -p summarize --suppress-think --think-start-tag "[[t]]" --think-end-tag "[[/t]]"
```

### 8.5 Web search and metadata

```bash
fabric -p analyze_claims --search                              # enable web search (Anthropic/OpenAI/Gemini/Grok)
fabric -p summarize --search --search-location "America/Los_Angeles"
fabric -p summarize --show-metadata                            # print token usage to stderr
```

---

## 9. The Web Interface and REST API (for users)

Beyond the CLI, Fabric can run as a server with a built-in REST API and an optional web app.

### 9.1 Start the server

```bash
fabric --serve
```

By default it binds `:8080`. Secure it with an API key:

```bash
fabric --serve --api-key "my-secret-key" --address ":9000"
```

> [!WARNING]
> If you start the server without `--api-key`, **all routes are unauthenticated**. Always set an API key when the server is reachable by anyone but you.

Once running, send a chat request (responses stream as Server-Sent Events). Pass the key in the `X-API-Key` header:

```bash
curl -N http://localhost:8080/chat \
  -H "Content-Type: application/json" \
  -H "X-API-Key: my-secret-key" \
  -d '{"prompts":[{"userInput":"Summarize fabric","patternName":"summarize"}]}'
```

Interactive API docs (Swagger UI) are served at `http://localhost:8080/swagger/index.html` and need no API key.

### 9.2 Use Fabric as an Ollama replacement

```bash
fabric --serve --serveOllama
```

This adds Ollama-compatible endpoints (`GET /api/tags`, `POST /api/chat`, `GET /api/version`). Tools configured to talk to Ollama can point at Fabric instead; your Patterns appear as models named like `summarize:latest`.

> [!TIP]
> For the full endpoint reference, authentication details, and architecture, see the companion **Admin Guide**.

### 9.3 The Fabric Web App

The repository includes a SvelteKit web application (in `web/`) that provides a graphical chat interface over the REST API, with pattern selection, model selection, sessions, and a pattern/strategy browser. Run the API server (`fabric --serve`), then build and run the web app from the `web/` directory per the project's web instructions. Configuration deployment and build details are covered in the Admin Guide.

---

## 10. Migrating from the Python Version

If you have the legacy Python Fabric, switch to the Go version in two steps.

```bash
# 1. Uninstall the Python version
pipx uninstall fabric
#    (also remove old fabric aliases from your .bashrc / .zshrc)

# 2. Install the Go version and re-run setup
go install github.com/danielmiessler/fabric/cmd/fabric@latest
fabric --setup
```

Then set your `PATH` as shown in [§2.5](#25-path-environment-variables-from-source-installs). Re-running setup matters because directory layouts and configuration changed.

### Upgrading the Go version

Re-run the install command — it always fetches the latest release:

```bash
go install github.com/danielmiessler/fabric/cmd/fabric@latest
```

---

## 11. Shell Completions

Fabric provides tab completion for Zsh, Bash, and Fish.

Quick install (no clone required):

```bash
curl -fsSL https://raw.githubusercontent.com/danielmiessler/Fabric/refs/heads/main/completions/setup-completions.sh | sh
```

=== "Zsh"

    ```bash
    mkdir -p ~/.zsh/completions
    cp completions/_fabric ~/.zsh/completions/
    echo 'fpath=(~/.zsh/completions $fpath)' >> ~/.zshrc
    echo 'autoload -Uz compinit && compinit' >> ~/.zshrc
    ```

=== "Bash"

    ```bash
    echo 'source /path/to/fabric/completions/fabric.bash' >> ~/.bashrc
    # or system-wide:
    sudo cp completions/fabric.bash /etc/bash_completion.d/
    ```

=== "Fish"

    ```bash
    mkdir -p ~/.config/fish/completions
    cp completions/fabric.fish ~/.config/fish/completions/
    ```

---

## 12. Helper Apps

### 12.1 Overview

Fabric ships three companion command-line tools. Install each like Fabric, with a different repo path.

| Tool | Purpose |
|---|---|
| `to_pdf` | Convert LaTeX (or `write_latex` output) to PDF |
| `code2context` | Package a code directory as JSON for `create_coding_feature` |
| `generate_changelog` | Build changelogs from git history + GitHub PRs |

### 12.3 `to_pdf`

Converts LaTeX files to PDF. Requires a LaTeX distribution (TeX Live or MiKTeX) with `pdflatex` on your `PATH`.

```bash
go install github.com/danielmiessler/fabric/cmd/to_pdf@latest
```

```bash
to_pdf input.tex                 # writes input.pdf
echo "ai security primer" | fabric -p write_latex | to_pdf   # writes output.pdf
```

Usage forms:

| Invocation | Behavior |
|---|---|
| `to_pdf` | Read stdin → `output.pdf` |
| `to_pdf doc.tex` | `doc.tex` → `doc.pdf` |
| `to_pdf report` | stdin → `report.pdf` |
| `to_pdf input output` | `input` (tries `input.tex`) → `output.pdf` |

### 12.4 `code2context`

Generates a JSON representation of a code directory to feed `create_coding_feature`.

```bash
go install github.com/danielmiessler/fabric/cmd/code2context@latest
```

```bash
# Directory mode
code2context . "Add input validation to all user inputs"

# With options
code2context -depth 4 -out project.json ./src "Implement error handling"

# Stdin mode (a file list piped in)
find . -name '*.go' | code2context "Refactor error handling"
git ls-files '*.py' | code2context "Add type hints"
```

| Option | Default | Meaning |
|---|---|---|
| `-depth` | `3` | Maximum directory depth to scan |
| `-ignore` | `.git,node_modules,vendor` | Comma-separated patterns to skip |
| `-out` | stdout | Output file |

### 12.5 `generate_changelog`

Builds Markdown changelogs from git history and GitHub PRs, with SQLite caching for fast incremental updates and optional AI-enhanced summaries via Fabric.

```bash
go install github.com/danielmiessler/fabric/cmd/generate_changelog@latest
generate_changelog --help
```

| Flag | Default | Purpose |
|---|---|---|
| `-r, --repo` | `.` | Repository path |
| `-o, --output` | stdout | Output file |
| `-l, --limit` | `0` (all) | Limit number of versions |
| `-v, --version` | — | Changelog for a specific version |
| `--ai-summarize` | off | AI-enhanced summaries via Fabric |
| `--no-cache` / `--rebuild-cache` | — | Cache control |
| `--token` | — | GitHub token (or `GITHUB_TOKEN`) |

### 12.6 Clipboard (pbpaste equivalents)

The examples use macOS `pbpaste`. On other platforms:

=== "Windows (PowerShell)"

    ```powershell
    Set-Alias pbpaste Get-Clipboard
    ```

=== "Linux"

    ```bash
    sudo apt install xclip -y
    alias pbpaste='xclip -selection clipboard -o'
    ```

---

## 13. Troubleshooting

Each entry lists the exact message, the cause, the fix, and how to avoid it.

### Error: `could not find vendor`

- **Cause:** Fabric can't match your requested/default model to a configured vendor — usually no default model is set, or the model name doesn't belong to the named vendor.
- **Solution:** Run `fabric --setup` and set a default vendor + model, or pass an explicit `-V <vendor> -m <model>`. Verify with `fabric --listmodels`.
- **Prevention:** Keep a valid default model configured; confirm a model exists with `fabric --listmodels` before using it.

### Error: `Requested Model = … Default Model = … Default Vendor = …` followed by a "run setup" hint

- **Cause:** No usable default model/vendor is configured.
- **Solution:** `fabric --setup`, choose a provider, then set defaults.
- **Prevention:** Don't clear required setup values with `reset` unless you re-set them.

### Error: `pattern '<binary-name>' not found`

- **Cause:** No pattern was specified, and Fabric fell back to using the program's own name as a pattern (this happens with broken aliases or symlinks).
- **Solution:** Pass a real pattern with `-p <name>`, e.g. `fabric -p summarize`. Check your aliases (see §5.11).
- **Prevention:** Ensure aliases map to `fabric --pattern <name>`, not a bare invocation.

### Message: `No patterns found` / patterns guidance banner

- **Cause:** Patterns haven't been downloaded yet.
- **Solution:** Run `fabric --setup` (downloads patterns automatically) or `fabric --updatepatterns`.
- **Prevention:** Complete setup before first use.

### Error: `missing required variable: <name>`

- **Cause:** The Pattern uses a `{{variable}}` you didn't provide.
- **Solution:** Add `-v=#<name>:<value>` for each variable, or run with `--no-variable-replacement`.
- **Prevention:** Check a Pattern's variables with `fabric --readpattern <name>` first.

### Error: `File "<name>" already exists. Not overwriting it.`

- **Cause:** `-o`/`--output` (or `--image-file`) points at an existing file.
- **Solution:** Choose a new filename or remove the existing file.
- **Prevention:** Use unique output names (e.g. include a date stamp).

### Error: `YouTube is not configured` / `Jina is not configured` / `Spotify is not configured`

- **Cause:** The relevant tool needs an API key.
- **Solution:** Run `fabric --setup` and configure YouTube / Jina / Spotify. (Transcript-only YouTube use needs no key, but metadata/comments do.)
- **Prevention:** Configure optional tools before using their flags.

### Error: image-related validation messages

- `invalid image file extension` — use `.png`, `.jpg`, `.jpeg`, or `.webp`.
- `invalid image size` — use `1024x1024`, `1536x1024`, `1024x1536`, or `auto`.
- `image compression can only be used with JPEG and WebP formats` — drop `--image-compression` for PNG.
- `transparent background can only be used with PNG and WebP formats` — use PNG/WebP, or `opaque`.
- `image parameters … can only be used with --image-file` — add `--image-file`.

### Error: `temperature` deprecated / model rejects parameters

- **Cause:** Some newer reasoning models reject classic sampling parameters.
- **Solution:** Add `--raw` to send model defaults, or omit `-t`/`-T`/`-P`/`-F`. (Anthropic models auto-select compliant parameters.)
- **Prevention:** Use `--raw` with models that don't accept sampling parameters.

### Error: streaming/empty response (`empty response`)

- **Cause:** The model returned nothing — sometimes provider-side, sometimes a misconfigured local server.
- **Solution:** Retry; check provider status; for OpenAI-compatible local servers (e.g. llama-server) add `--disable-responses-api`.
- **Prevention:** For local OpenAI-compatible servers, set `disableResponsesAPI: true` in `config.yaml`.

### Issue: `yt()` alias / `yt` example broken

- **Cause:** Some older README `yt` examples drifted across releases.
- **Solution:** Use the alias function in §5.11, or call `fabric -y "URL" --transcript -p <pattern>` directly.
- **Prevention:** Prefer explicit flags over copied one-liners.

### Diagnosing anything else: turn on debug

```bash
fabric -p summarize --debug 2 "test"
```

`--debug` levels: `0` off, `1` basic, `2` detailed, `3` trace, `4` wire (shows the exact messages exchanged with the model).

---

## 14. FAQ

**Q: Do I need an API key to use Fabric?**
You need access to at least one AI provider. That usually means an API key (OpenAI, Anthropic, Gemini, etc.), but you can also run fully local models via Ollama or LM Studio with no key.

**Q: Does Fabric require Python?**
No. The current Fabric is a single Go binary. The legacy Python version is deprecated — see [§10](#10-migrating-from-the-python-version).

**Q: Where are my keys and patterns stored?**
Under `~/.config/fabric/` — keys in `.env`, patterns in `patterns/`, strategies in `strategies/`, sessions and contexts in their own folders.

**Q: How do I switch models per command?**
Use `-m <model>` (and `-V <vendor>` to disambiguate). Set a per-pattern default with `FABRIC_MODEL_<PATTERN>=vendor|model`.

**Q: What's the difference between a context and a session?**
A **context** is static reusable text prepended to a prompt (e.g. a persona). A **session** stores conversation history so follow-up turns have memory.

**Q: What's the difference between a Pattern and a strategy?**
A **Pattern** is the task prompt (e.g. `summarize`). A **strategy** is a reasoning style (e.g. Chain-of-Thought) layered on top with `--strategy`.

**Q: Can I keep my own prompts private?**
Yes. Use a custom patterns directory (`fabric --setup` → Custom Patterns). They override built-ins, appear in `--listpatterns`, and survive `--updatepatterns`.

**Q: How do I update the built-in patterns?**
`fabric --updatepatterns`. Your custom patterns are never touched.

**Q: Can I see what will be sent before spending tokens?**
Yes — `--dry-run` prints the exact prompt without calling the model.

**Q: How do I use Fabric with a local model?**
Configure Ollama or LM Studio in `fabric --setup`, then select the model with `-m` (and `-V Ollama` / `-V "LM Studio"`). For Ollama, `--modelContextLength` tunes the context window.

**Q: Can other apps talk to Fabric?**
Yes. Run `fabric --serve` for the REST API, or `fabric --serve --serveOllama` to expose Ollama-compatible endpoints so Ollama clients can use any Fabric provider.

**Q: How do I get streaming output?**
Add `-s`/`--stream`.

**Q: How do I copy the result to my clipboard automatically?**
Add `-c`/`--copy`.

**Q: How do I make a YouTube transcript workflow?**
`fabric -y "URL" -p extract_wisdom` (add `--transcript-with-timestamps`, `--comments`, or `--metadata` as needed). Use the `yt` helper from §5.11.

**Q: Why am I getting "could not find vendor" even though my key is set?**
Your default model/vendor may be unset or mismatched. Run `fabric --setup`, set defaults, and confirm with `fabric --listmodels`.

**Q: Can Fabric generate images and audio?**
Yes — `--image-file` (with image-capable models) for images, and a TTS model with an audio `-o` file for speech.

**Q: How do I report a bug or request a feature?**
Open an issue at the project's GitHub repository: <https://github.com/danielmiessler/fabric>.

---

## 15. Command Reference

Complete list of CLI options.

### Core

| Short | Long | Default | Description |
|---|---|---|---|
| `-p` | `--pattern` | | Choose a pattern |
| `-v` | `--variable` | | Pattern variable, e.g. `-v=#role:expert` |
| `-C` | `--context` | | Choose a context |
| | `--session` | | Choose a session |
| `-a` | `--attachment` | | Attachment path or URL (repeatable) |
| `-m` | `--model` | | Choose model |
| `-V` | `--vendor` | | Specify vendor for the model |
| | `--modelContextLength` | | Context length (Ollama) |
| `-o` | `--output` | | Write output to file |
| | `--output-session` | | Write entire session to the output file |
| `-c` | `--copy` | | Copy result to clipboard |
| `-s` | `--stream` | | Stream output |
| `-g` | `--language` | | Language code, e.g. `-g=en` |

### Generation tuning

| Short | Long | Default | Description |
|---|---|---|---|
| `-t` | `--temperature` | `0.7` | Temperature |
| `-T` | `--topp` | `0.9` | Top-P |
| `-P` | `--presencepenalty` | `0.0` | Presence penalty |
| `-F` | `--frequencypenalty` | `0.0` | Frequency penalty |
| `-r` | `--raw` | | Use model defaults; send no chat options |
| `-e` | `--seed` | | Generation seed |
| | `--thinking` | | Reasoning level: `off`/`low`/`medium`/`high` or numeric tokens |
| | `--suppress-think` | | Hide `<think>` blocks |
| | `--think-start-tag` | `<think>` | Thinking start tag |
| | `--think-end-tag` | `</think>` | Thinking end tag |
| | `--disable-responses-api` | `false` | Disable OpenAI Responses API |
| | `--show-metadata` | | Print token usage to stderr |

### Listing

| Short | Long | Description |
|---|---|---|
| `-l` | `--listpatterns` | List all patterns |
| | `--readpattern` | Print a pattern's contents |
| `-n` | `--latest` | List the N newest patterns |
| `-L` | `--listmodels` | List all models |
| `-x` | `--listcontexts` | List all contexts |
| `-X` | `--listsessions` | List all sessions |
| | `--liststrategies` | List all strategies |
| | `--listvendors` | List all vendors |
| | `--list-gemini-voices` | List Gemini TTS voices |
| | `--list-transcription-models` | List transcription models |
| | `--shell-complete-list` | Raw list output (for completions) |

### Management & setup

| Short | Long | Description |
|---|---|---|
| `-S` | `--setup` | Run setup |
| `-d` | `--changeDefaultModel` | Change the default model |
| `-U` | `--updatepatterns` | Update built-in patterns |
| `-w` | `--wipecontext` | Delete a context |
| `-W` | `--wipesession` | Delete a session |
| | `--printcontext` | Print a context |
| | `--printsession` | Print a session |
| | `--config` | Path to YAML config |
| | `--version` | Print version |
| | `--addextension` / `--rmextension` / `--listextensions` | Manage extensions |
| | `--strategy` | Apply a prompt strategy |

### Input sources & tools

| Short | Long | Description |
|---|---|---|
| `-y` | `--youtube` | YouTube video/playlist URL |
| | `--playlist` | Prefer playlist over video |
| | `--transcript` | Grab transcript (default) |
| | `--transcript-with-timestamps` | Transcript with timestamps |
| | `--comments` | Grab comments |
| | `--metadata` | Output video metadata |
| | `--visual` / `--visual-sensitivity` / `--visual-fps` | Visual (OCR/FFmpeg) extraction |
| | `--yt-dlp-args` | Extra args for `yt-dlp` |
| `-u` | `--scrape_url` | Scrape a URL to Markdown (Jina) |
| `-q` | `--scrape_question` | Web search question (Jina) |
| | `--spotify` | Spotify episode/podcast URL |
| | `--readability` | Clean HTML into readable text |
| | `--input-has-vars` | Apply variables to input |
| | `--no-variable-replacement` | Disable variable replacement |
| | `--transcribe-file` / `--transcribe-model` / `--split-media-file` | Audio/video transcription |

### Images, audio & notifications

| Long | Description |
|---|---|
| `--image-file` | Output image path |
| `--image-size` / `--image-quality` / `--image-compression` / `--image-background` | Image parameters |
| `--voice` | TTS voice (default `Kore`) |
| `--notification` | Desktop notification on completion |
| `--notification-command` | Custom notification command (`$1`=title, `$2`=message) |

### Server & web

| Long | Default | Description |
|---|---|---|
| `--serve` | | Serve the REST API |
| `--serveOllama` | | Serve with Ollama-compatible endpoints |
| `--address` | `:8080` | Bind address |
| `--api-key` | | API key securing server routes |
| `--search` / `--search-location` | | Enable web search tool |

### Debugging

| Long | Default | Description |
|---|---|---|
| `--dry-run` | | Show what would be sent, don't send |
| `--debug` | `0` | Debug level 0–4 (off/basic/detailed/trace/wire) |

---

_Generated June 2026 from danielmiessler/Fabric at 29b32f9. AI-generated documentation. The library is checked by sampling (three repositories so far); this guide was not individually reviewed. Verify against the project before relying on it. Unofficial; not affiliated with or reviewed by the project._
