# Default Agents — Design **Date:** 2026-04-23 **Status:** Approved ## Goal Ship ClaudeDo with a curated set of default agents so that users have useful agents available on first launch, without losing the file-based ownership model (user-editable, user-deletable). Provide a "Restore defaults" action to recover missing defaults on demand. ## Agents to Ship Six markdown agents covering the common stages of task execution plus one general-purpose agent: | File | Focus | |---|---| | `code-reviewer.md` | Review diff for bugs, logic errors, convention adherence. Flags only high-confidence issues. | | `test-writer.md` | Generate unit/integration tests for changed code. Follows existing test patterns. | | `debugger.md` | Systematic root-cause analysis — reproduce, isolate, hypothesize, verify. | | `security-reviewer.md` | OWASP-style audit focused on auth, SQL injection, input handling, secret exposure. | | `explorer.md` | Fast codebase navigation and answering "where/how" questions. Terse output. | | `researcher.md` | General-purpose research, doc summarization, analysis, investigation. Non-code. | Each file uses Claude Code's standard agent frontmatter: ```markdown --- name: description: --- ``` Content target: ~20–40 lines per file. Style matches the existing Claude Code agent conventions. ## Behavior **Seed on first launch, restore on demand:** 1. Bundled agents live alongside the Worker binary at `/DefaultAgents/*.md`. 2. At Worker startup, for each bundled file: if `~/.todo-app/agents/.md` does NOT exist, copy it in. If it exists, leave it alone — the user owns their copy. 3. A "Restore default agents" button in the settings modal re-runs the same check, restoring any that the user has deleted. The seed path and the restore path are the same code — only the invocation differs (startup vs. hub call). ## Components ### `DefaultAgents/*.md` (bundled content) Location: `src/ClaudeDo.Worker/DefaultAgents/` Packaging: `` in `ClaudeDo.Worker.csproj`. At runtime they land at `/DefaultAgents/*.md` next to the executable. ### `DefaultAgentSeeder` (new service) Location: `src/ClaudeDo.Worker/Services/DefaultAgentSeeder.cs` ``` public sealed class DefaultAgentSeeder { public DefaultAgentSeeder(string bundleDir, string targetDir); public Task SeedMissingAsync(CancellationToken ct = default); } public sealed record SeedResult(int Copied, int Skipped); ``` Behavior of `SeedMissingAsync`: - If `bundleDir` doesn't exist, log warning and return `(0, 0)`. - Enumerate `*.md` in `bundleDir`. - For each file, if the target path (`targetDir/`) is missing, copy it; else increment `Skipped`. - Create `targetDir` if missing (consistent with existing `AgentFileService.WriteAsync`). - Per-file exceptions are caught and logged; the seeder continues with the next file. The method itself does not throw for individual file failures. ### `Program.cs` wiring After `AgentFileService` registration and before `app.Run()`: ```csharp var bundleDir = Path.Combine(AppContext.BaseDirectory, "DefaultAgents"); var seeder = new DefaultAgentSeeder(bundleDir, agentsDir); await seeder.SeedMissingAsync(); builder.Services.AddSingleton(seeder); ``` The seeder is also registered as a singleton so the hub can invoke it for the restore flow. ### `WorkerHub.RestoreDefaultAgents` Location: add method to existing `src/ClaudeDo.Worker/Hub/WorkerHub.cs`. Signature: `public async Task RestoreDefaultAgents()` Behavior: - Calls `DefaultAgentSeeder.SeedMissingAsync()`. - Returns the `SeedResult` to the caller. - No separate broadcast — the UI will call `GetAgents` after the restore returns, reusing the existing refresh path. ### UI — Settings Modal Location: `src/ClaudeDo.Ui/Views/Modals/SettingsModalView.axaml` + `SettingsModalViewModel`. Add a "Restore default agents" button to the modal. On click: 1. Disable the button, show a spinner label. 2. Call `WorkerClient.RestoreDefaultAgentsAsync()`. 3. Show a brief inline confirmation: `"Restored {Copied} agent(s)"` or `"All defaults already present"`. 4. Trigger the existing agent list refresh so the new files appear immediately in the rest of the UI. ### `WorkerClient` method Add `Task RestoreDefaultAgentsAsync(CancellationToken ct = default)` to `WorkerClient` — thin wrapper that invokes the hub method. ## Data Flow **Startup:** ``` Worker starts → DefaultAgentSeeder.SeedMissingAsync() → copies missing files into ~/.todo-app/agents/ AgentFileService.ScanAsync() (on first GetAgents call) → sees the seeded files ``` **User restores:** ``` Settings modal button click → WorkerClient.RestoreDefaultAgentsAsync() → WorkerHub.RestoreDefaultAgents() → DefaultAgentSeeder.SeedMissingAsync() → returns SeedResult(copied, skipped) UI shows confirmation, triggers GetAgents refresh ``` ## Error Handling | Failure | Behavior | |---|---| | Missing `DefaultAgents/` bundle dir | Log warning, return `(0, 0)`. Startup proceeds. | | Individual file copy failure (disk, permissions) | Catch per-file, log, continue with the remaining files. | | Corrupt bundled markdown (no valid frontmatter) | Copied anyway — the `AgentFileService` frontmatter parser already falls back to filename-as-name. | | Startup seeder exception (unexpected) | Log as warning, do not crash the Worker. Agents can still be restored via the button. | | Hub `RestoreDefaultAgents` exception | Propagate to client as SignalR error; UI shows a generic "Restore failed" message. | ## Testing **Unit:** `tests/ClaudeDo.Worker.Tests/Services/DefaultAgentSeederTests.cs` - Seeds all files when target dir is empty. - Skips files that already exist. - Preserves existing user-modified files (file mtime / content unchanged). - Returns accurate `SeedResult` counts. - Handles missing bundle dir gracefully (returns `(0, 0)`, no throw). - Creates target dir if it doesn't exist. **Integration:** extend `tests/ClaudeDo.Worker.Tests/Hub/AgentSettingsHubTests.cs` - `RestoreDefaultAgents` invokes the seeder and returns the count. **No UI tests.** The project has no UI test harness; settings modal behavior is exercised manually. ## Build / Packaging `src/ClaudeDo.Worker/ClaudeDo.Worker.csproj` gains: ```xml PreserveNewest ``` No new NuGet dependencies. ## Out of Scope - Editing bundled agents in-place (user edits their copy under `~/.todo-app/agents/`; bundle is read-only by convention). - Versioning / updating user copies when the bundled version changes. If a bundled agent is improved in a later release, the user's copy is not overwritten. A future release may add a "diff / reset to bundled" flow, but not now. - Packaging as embedded resources. Content files copied to output are simpler, inspectable on disk, and consistent with the file-based agent model.