package askcli import ( "context" "fmt" "io" ) type Runner interface { Run(ctx context.Context, args []string, stdin io.Reader, stdout, stderr io.Writer) (int, error) } type Dispatcher struct { runner Runner } func NewDispatcher(runner Runner) *Dispatcher { if runner == nil { e := NewExecutor("ask") runner = &e } return &Dispatcher{runner: runner} } func (d Dispatcher) Dispatch(ctx context.Context, args []string, stdin io.Reader, stdout, stderr io.Writer) (int, error) { if len(args) == 0 { return d.help(stdout) } subcommand := args[0] switch subcommand { case "add", "list", "info", "dep", "urgency", "export": return d.runner.Run(ctx, args, stdin, stdout, stderr) case "annotate": return d.handleAnnotate(ctx, args, stdout, stderr) case "start": return d.handleStart(ctx, args, stdout, stderr) case "stop": return d.handleStop(ctx, args, stdout, stderr) case "done": return d.handleDone(ctx, args, stdout, stderr) case "priority": return d.handlePriority(ctx, args, stdout, stderr) case "tag": return d.handleTag(ctx, args, stdout, stderr) case "modify": return d.handleModify(ctx, args, stdout, stderr) case "denotate": return d.handleDenotate(ctx, args, stdout, stderr) case "delete": return d.handleDelete(ctx, args, stdout, stderr) default: return d.unknownCommand(stderr, subcommand) } } func (d Dispatcher) help(w io.Writer) (int, error) { io.WriteString(w, "ask - task management CLI\n") io.WriteString(w, "\nSubcommands:\n") io.WriteString(w, " ask add \"description\" Create a new task\n") io.WriteString(w, " ask list [filters] List tasks (UUID-only output)\n") io.WriteString(w, " ask info Show task details\n") io.WriteString(w, " ask annotate \"note\" Add annotation to task\n") io.WriteString(w, " ask start Start working on task\n") io.WriteString(w, " ask stop Stop working on task\n") io.WriteString(w, " ask done Mark task complete\n") io.WriteString(w, " ask priority

Set priority (H/M/L)\n") io.WriteString(w, " ask tag +/- Add or remove tag\n") io.WriteString(w, " ask dep add Add dependency\n") io.WriteString(w, " ask dep rm Remove dependency\n") io.WriteString(w, " ask dep list List dependencies\n") io.WriteString(w, " ask urgency List tasks sorted by urgency\n") io.WriteString(w, " ask modify Modify task fields\n") io.WriteString(w, " ask denotate \"text\" Remove annotation\n") io.WriteString(w, " ask delete Delete task\n") io.WriteString(w, " ask export Raw JSON export\n") io.WriteString(w, "\nFilters:\n") io.WriteString(w, " +READY +BLOCKED + started limit:N sort:priority-,urgency-\n") return 0, nil } func (d Dispatcher) unknownCommand(w io.Writer, subcommand string) (int, error) { fmt.Fprintf(w, "ask: unknown subcommand %q\n", subcommand) return 1, nil }