# ClaudeDo.Data Shared data layer: models, repositories, SQLite infrastructure, and git operations. ## Models - **TaskEntity** — Id, ListId, Title, Description, Status (Manual|Queued|Running|Done|Failed), ScheduledFor, Result, LogPath, timestamps, CommitType - **ListEntity** — Id, Name, WorkingDir, DefaultCommitType, CreatedAt - **TagEntity** — Id (autoincrement), Name (unique) - **WorktreeEntity** — TaskId (PK, 1:1 with task), Path, BranchName, BaseCommit, HeadCommit, DiffStat, State (Active|Merged|Discarded|Kept) ## Repositories All repositories use EF Core LINQ queries via `ClaudeDoDbContext`. Exception: `TaskRepository.GetNextQueuedAgentTaskAsync` uses `FromSqlRaw` for atomic queue claim. - **TaskRepository** — CRUD, status transitions (`MarkRunningAsync`, `MarkDoneAsync`, `MarkFailedAsync`), `GetNextQueuedAgentTaskAsync` (queue polling), `GetEffectiveTagsAsync` (union of task + list tags), `FlipAllRunningToFailedAsync` - **ListRepository** — CRUD, tag junction management - **TagRepository** — `GetOrCreateAsync` (idempotent) - **WorktreeRepository** — CRUD, `UpdateHeadAsync`, `SetStateAsync` ## Infrastructure - **ClaudeDoDbContext** — EF Core DbContext; configured with WAL mode and foreign keys via `UseSqlite` options - **IDbContextFactory** — registered in DI; used by singleton consumers (e.g. Worker hosted service) - **Paths** — expands `~` and `%USERPROFILE%`, resolves relative paths. App root: `~/.todo-app` - **AppSettings** — loads `~/.todo-app/ui.config.json` (DbPath, SignalRUrl) ## Git - **GitService** — async wrapper around git CLI (ProcessStartInfo, no shell). Operations: worktree add/remove, add all, commit (stdin for message), merge ff-only, rev-parse, diff-stat, has-changes, is-git-repo ## Schema 6 tables: `lists`, `tasks`, `tags`, `list_tags`, `task_tags`, `worktrees`. Managed by EF Core migrations in the `Migrations/` folder. Seed data: tags "agent" and "manual". ## Conventions - Enum <-> string mapping via EF Core `ValueConverter` (configured in `IEntityTypeConfiguration`) - Entity configurations live in the `Configuration/` folder - Primary keys are `init`-only strings (GUIDs assigned at creation) - All methods are async with CancellationToken where applicable