# ws_mod Error Handling

## Template (Errors)

### Error Chain (required)

1. Trigger Condition
2. Detection Signal
3. Recovery Steps
4. Success Criteria
5. Escalation Path (optional)

## Error Classification

| Stage   | Error Code                | Description                              | Solution                                                           |
| ------- | ------------------------- | ---------------------------------------- | ------------------------------------------------------------------ |
| prepare | `PATH_REQUIRED`           | File path is missing                     | Provide a non-empty relative file path                             |
| prepare | `INVALID_ARGS`            | Tool arguments are invalid               | Fix the argument shape shown in the error message                  |
| prepare | `INVALID_PATH`            | Path is outside rtws or otherwise bad    | Use a normalized relative path inside rtws                         |
| prepare | `INVALID_FORMAT`          | Modification format is invalid           | Use the documented format for the selected prepare tool            |
| prepare | `FILE_NOT_FOUND`          | File does not exist                      | Use `create=true` parameter or create file first                   |
| prepare | `CONTENT_REQUIRED`        | Content empty but tool requires content  | Provide `content` for insert/append/block_replace                  |
| prepare | `INVALID_HUNK_ID`         | hunkId is invalid                        | Use a non-empty hunkId without line breaks                         |
| prepare | `WRONG_MODE`              | Existing hunkId belongs to another mode  | Choose a new hunkId or use the same prepare mode                   |
| prepare | `HUNK_ID_CONFLICT`        | hunkId collides with an active hunk      | Choose a unique hunkId                                             |
| prepare | `ANCHOR_NOT_FOUND`        | Anchor line not found                    | Check anchor text correctness, or use `ripgrep_snippets` to locate |
| prepare | `ANCHOR_AMBIGUOUS`        | Anchor has multiple matches              | Specify `occurrence` parameter to identify which match             |
| prepare | `OCCURRENCE_OUT_OF_RANGE` | occurrence out of range                  | Check if occurrence value is within `1~candidates_count` range     |
| apply   | `HUNK_NOT_FOUND`          | Hunk expired/applied/does not exist      | Re-run prepare to generate new hunk                                |
| apply   | `WRONG_OWNER`             | Hunk planned by different member         | Hunk must be generated by current member                           |
| apply   | `WRONG_MODE`              | hunkId belongs to another mode           | Apply the matching hunk mode, or re-run prepare                    |
| apply   | `FILE_NOT_FOUND`          | File does not exist at apply time        | Check if file was deleted or moved                                 |
| apply   | `CONTENT_CHANGED`         | File content drifted after prepare       | Re-run prepare against the latest file                             |
| apply   | `AMBIGUOUS_MATCH`         | Apply-time anchor became ambiguous       | Re-run prepare with a narrower anchor or occurrence                |
| apply   | `APPLY_REJECTED_*`        | Apply-time safety check rejected hunk    | Read the rejection suffix and re-run prepare with stronger context |
| write   | `ACCESS_DENIED`           | Reserved rtws path is hard-denied        | Use the dedicated tool/path listed in the error message            |
| write   | `FILE_EXISTS`             | File already exists (create_new_file)    | Use different path or delete existing file first                   |
| write   | `NOT_A_FILE`              | Target path exists but is not a file     | Choose a different path or remove the non-file entry first         |
| write   | `STATS_MISMATCH`          | Whole-file overwrite snapshot mismatches | Re-read the file and retry with the latest snapshot                |
| write   | `SUSPICIOUS_DIFF`         | Diff/patch-looking content is undeclared | Declare `content_format`, or use prepare/apply tools               |
| write   | `FAILED`                  | Filesystem or runtime failure            | Inspect the error text and fix the underlying condition            |

## Common Error Scenarios & Troubleshooting

### 1. Anchor-Related Errors

**ANCHOR_NOT_FOUND**

- Cause: Anchor text does not exist in file
- Troubleshooting: Use `ripgrep_snippets` to confirm anchor exists
- Note: Anchor matching is case-sensitive unless using `match: "contains"` (default)

**ANCHOR_AMBIGUOUS**

- Cause: Anchor appears multiple times in file
- Troubleshooting: Use `ripgrep_snippets` to see all match positions
- Solution: Add `occurrence` parameter (e.g., `occurrence: 2` for second match)

**OCCURRENCE_OUT_OF_RANGE**

- Cause: Specified occurrence greater than actual match count
- Solution: Change occurrence value to a valid range number

### 2. Hunk-Related Errors

**HUNK_NOT_FOUND**

- Cause 1: Hunk expired (TTL=1h)
- Cause 2: Process restarted, hunk in memory lost
- Solution: Re-run prepare to generate new hunk

**WRONG_OWNER**

- Cause: Trying to apply someone else's hunk
- Solution: Can only apply hunks generated by yourself

**`CONTENT_CHANGED` / `AMBIGUOUS_MATCH` / `APPLY_REJECTED_*`**

- Cause: File changed after prepare, or the apply-time anchor check no longer has a single safe target
- Solution: Re-read the file and re-run prepare with current content, narrower anchors, or an explicit occurrence

### 3. Content Format Errors

**Default Reject Diff/Patch**

- Cause: Using `overwrite_entire_file`, body looks like diff/patch format but not declared
- Solution:
  - Option 1: Use `prepare_*` + `apply_file_modification`
  - Option 2: Explicitly declare `content_format: "diff"` or `content_format: "patch"`

**STATS_MISMATCH**

- Cause: Whole-file overwrite used a stale snapshot
- Solution: Re-read the file and retry with the latest file stats/content

### 4. Permission Errors

**FAILED**

- Cause: Filesystem or runtime failure, including OS-level permission errors
- Solution: Inspect the error text, fix the underlying condition, then retry

**ACCESS_DENIED**

- Cause: Target path is a reserved rtws boundary such as `.minds/**`, root `.dialogs/**`, or `*.tsk/`
- Solution: For `.minds/**`, use `team_mgmt_*` tools when configured; for dialog debugging, reproduce under a nested rtws such as `ux-rtws/.dialogs/**`; do not edit `*.tsk/` packages through generic ws_mod tools

### 5. Path Errors

**FILE_NOT_FOUND**

- Cause: File path does not exist
- Solution:
  - If appending: use `create: true` parameter
  - Other cases: Create file first or check if path is correct

**NOT_A_FILE**

- Cause: Target path exists but points to a directory, symlink, or another non-file entry
- Solution: Use a different file path, or remove/rename the existing non-file entry before creating the file

## Error Prevention Tips

1. **prepare → apply must be two messages**: Parallel execution in same message may cause apply to not see hunk

2. **Read before write**: Call `read_file` first to get old file snapshot before using `overwrite_entire_file`

3. **Use unique anchors**: Avoid using too generic text as anchors; use `occurrence` to be explicit when needed

4. **Apply promptly**: Hunks have 1 hour TTL, apply as soon as possible after generation

5. **Check output fields**: Especially `normalized.*` fields to confirm write behavior is as expected
