Add todo mode and replace the plan with TODO.md

This commit is contained in:
Ian Gulliver
2026-10-15 07:23:17 -07:00
parent 60a1d221f4
commit 1f44bc6d91
25 changed files with 1259 additions and 637 deletions
+50
View File
@@ -13,9 +13,58 @@ import (
"g.fc.run/misc/byre/internal/git"
"g.fc.run/misc/byre/internal/mcp"
"g.fc.run/misc/byre/internal/store"
"g.fc.run/misc/byre/internal/todo"
)
func (m *Manager) CreateTask(ctx context.Context, project api.Project, title, createdBy, base string) (api.Task, error) {
return m.createTask(ctx, project, title, createdBy, base, nil)
}
func (m *Manager) StartTodo(ctx context.Context, project api.Project, creator api.User, title, model string) (api.Task, error) {
if creator.GitName == "" || creator.GitEmail == "" {
return api.Task{}, ErrNoGitIdentity
}
src, found, err := git.ReadFile(project.RepoPath, project.DefaultBranch, todo.File)
if err != nil {
return api.Task{}, err
}
if !found {
return api.Task{}, fmt.Errorf("%w: %s has no %s", store.ErrNotFound, project.DefaultBranch, todo.File)
}
item, found := todo.Find(todo.Parse(src), title)
if !found {
return api.Task{}, fmt.Errorf("%w: %s on %s has no item %q", store.ErrNotFound, todo.File, project.DefaultBranch, title)
}
tasks, err := m.store.ListTasks(ctx, project.Id)
if err != nil {
return api.Task{}, err
}
for _, t := range tasks {
if t.Status == api.TaskStatusActive && t.TodoItem != nil && *t.TodoItem == title {
return api.Task{}, fmt.Errorf("%w: task %s is already working on %q", ErrConflict, t.Id, title)
}
}
task, err := m.createTask(ctx, project, item.Title, creator.Login, project.DefaultBranch, &item.Title)
if err != nil {
return api.Task{}, err
}
_, err = m.create(ctx, task, creator, todoPrompt(item), model, creator.Login, nil)
if err != nil {
return api.Task{}, fmt.Errorf("task %s created, but its agent did not start: %w", task.Id, err)
}
return task, nil
}
func todoPrompt(item api.TodoItem) string {
return fmt.Sprintf("Work on this item from %[1]s at the repo root:\n\n%[2]s\n\nWhen the work is done, remove this item from %[1]s in this worktree, so the removal lands in the same merge as the work.",
todo.File, todo.Markdown(item))
}
func (m *Manager) createTask(ctx context.Context, project api.Project, title, createdBy, base string, todoItem *string) (api.Task, error) {
id := store.NewID()
t := api.Task{
Id: id,
@@ -27,6 +76,7 @@ func (m *Manager) CreateTask(ctx context.Context, project api.Project, title, cr
Status: api.TaskStatusActive,
CreatedBy: createdBy,
CreatedAt: time.Now().UTC(),
TodoItem: todoItem,
}
var err error