# pi-watch

A [pi](https://github.com/badlogic/pi) extension that watches files for AI comments and sends them to the agent.

> Inspired by [aider's watch mode](https://aider.chat/docs/usage/watch.html).

## Installation

```bash
pi install npm:pi-watch
```

## Usage

Install the extension and use it from an active Pi session. The installed workflow is preferred because Pi's integrated `/` commands are more powerful and flexible than running the package ad hoc with `pi -e`.

Start Pi with watch mode enabled:

```bash
pi --watch
```

Or control the watcher from an active Pi session with visible `/watch:*` commands. This is the preferred workflow because it is more powerful and flexible than one-off `pi -e` usage: you can start, stop, inspect, expand, shrink, and tune watched paths without restarting Pi.

```text
/watch              # show all watch commands
/watch:start [dir]  # start watching cwd, or a specific directory
/watch:stop         # stop watching and clear pending comments
/watch:status       # show active paths, pause state, pending count, and ignores
/watch:list         # list pending AI comments grouped by file
/watch:add <dir>    # add another directory to the active watch set
/watch:remove <dir> # remove a directory from the active watch set
/watch:ignore <re>  # add a runtime regex ignore pattern
```

When watch mode is active, pi-watch scans saved files for one-line AI markers in these comment styles:

- `#` shell/Python style
- `//` JavaScript/TypeScript style
- `--` SQL style
- `<!-- -->` only for the `AI-` ignore-file marker

## AI Markers

| Marker | Behavior                                                                                                                   |
| ------ | -------------------------------------------------------------------------------------------------------------------------- |
| `AI`   | Collects the comment as pending context. No message is sent yet.                                                           |
| `AI!`  | Sends all pending AI comments as edit instructions, removes processed AI comments from code, then clears pending comments. |
| `AI?`  | Sends all pending AI comments as a question, removes processed AI comments from code, then clears pending comments.        |
| `AI-`  | Ignores the entire file. No `AI`, `AI!`, or `AI?` comments in that file are collected or triggered.                        |

Markers are case-insensitive and can appear at the start or end of a supported one-line comment.

## Examples

The examples below escape the marker with a backslash so this README is safe to keep in a watched repo. Remove the backslash when using the marker in real code.

### Trigger an edit with `AI!`

```typescript
// \AI! Add error handling to this function
function process(data) {
  return data.map((d) => d.value);
}
```

### Collect context with `AI`

```python
# Extract this logic into a helper function \AI
def calculate_total(items):
    total = 0
    for item in items:
        total += item.price
    return total
```

### Ask a question with `AI?`

```typescript
// Why can this return undefined? \AI?
function findUser(id: string) {
  return users.find((user) => user.id === id);
}
```

### Ignore a whole file with `AI-`

```typescript
// \AI-
// This file can contain documentation examples without triggering pi-watch.
```

Markdown files can use an HTML comment for the same purpose:

```markdown
<!-- \AI- -->
```

## Multi-file Comments

AI comments can span multiple files. Add `AI` comments as context in one or more files, then use either:

- `AI!` to request code changes with all pending context.
- `AI?` to ask a question with all pending context.

After `AI!` or `AI?` dispatches, every AI comment included in that request is removed from its source file and pending comments are cleared.

## Multi-line Comments

Consecutive lines with AI markers are grouped together and sent as one comment block.

```javascript
// This function needs work \AI
// fix the race condition \AI!
function process(data) {
  return data.map((d) => d.value);
}
```

## Excluding Files

### `.piwatchignore`

Create a `.piwatchignore` file in the watcher cwd to exclude any file or pattern before AI parsing.

```gitignore
README.md
docs/**
*.md
src/generated/**/*.ts
package-lock.json
```

If a file matches `.piwatchignore`, pi-watch does not collect context, trigger edits, or trigger questions from that file.

### `AI-`

Use `AI-` inside a file to exclude the whole file. This also prevents normal `AI` context collection in the same file.

Supported forms:

```text
// AI-
# AI-
-- AI-
<!-- AI- -->
```

Exclusion priority is:

1. `.piwatchignore`
2. `AI-`
3. `AI!`
4. `AI?`
5. `AI`

Ignored files only clear pending comments for that same file. Pending comments from other files are preserved.

## Development

```bash
# Run tests
npm test

# Check code with Biome (lint + format)
npm run check

# Auto-fix Biome issues
npm run check:fix

# Format code with Biome
npm run format
```

## License

MIT
