todoer GitHub

pre-1.0for people and AI agents

Todos and pull requests, as plain files in your git repo.

todoer is one binary. Agents and people claim todos, work in git worktrees, and review the pull requests on the command line. No database, no server, no account.

~/code/my-project
todo3
fix-the-login-crash you .todoer/todos/fix-the-login-crash.md authavailable
write-the-api-docs .todoer/todos/write-the-api-docs.md docsavailable
add-rate-limiting .todoer/todos/add-rate-limiting.md authblocked
in-progress0
pull request0
done0
main 83f9b44 Plan the auth work
agent 1writes the code, submits and updates the pull request agent 2reviews the pull request with you and adds your comments youyou run it, or ask an agent to. Agents run commands as you: todoer and git use your git email   the todo is assigned to you, and agent 1 writes the code
// everything is a file

Nothing to host. It is all in git.

A todo is a file in .todoer/todos/. Its name is its id. A pull request is a folder in .todoer/prs/, committed on the branch that it goes into. There is no settings file. A person and an agent can read every file, and git history keeps every change.

.todoer/todos/fix-the-login-crash.md

A todo. The file name is its id and its title. todoer claim sets the assignee and commits the file, so you can push the claim at once. The front matter is optional.

---
assignee: you@example.com
labels: [auth]
---

Steps to reproduce: sign in with an expired token.
The app stops after the third retry.
// the board

Plan the work, do the work, review the work.

Each step uses git and the files above. The help text, todoer help, shows every command on one screen.

plan3

A todo is a file with a name

add writes .todoer/todos/<name>.md. The text can come on stdin. show prints all the data of a todo. done removes the file. check reports bad todos.

todoer add fix-the-login-crash -l auth

Dependencies, never a cycle

dep add refuses a cycle. A todo can wait for one todo or for all the todos of a label. ls --available lists the todos that can start now, and dep show prints the tree.

todoer dep add new-login-page -l auth-backend-refactor

Labels show the progress

A label groups related todos. progress shows which are in progress, in a pull request or not started. A label rule tells the agent in plain words which todos get the label.

$ todoer progress auth
auth  1 in progress, 0 in a pull request, 1 not started  [=-]
work3

Any branch, your commits

todoer knows no main branch. claim commits the todo on your branch, so you can push it at once. Claim one todo, a list or a whole --label. A claim refuses a todo of another person or a blocked todo.

Agents work in worktrees

One command for the agent: pr submit --branch main -n <name> squashes every commit since the work started from main into one, and commits the pull request on main. There is nothing to push and no hosting service.

One command makes it a skill

skill --init writes the workflow as a SKILL.md for Claude Code, Codex and Cursor, in the repository, or outside a repository in your home folder. todoer skill prints it.

review4

A pull request is a patch

The pull request lands on your branch, so you review and merge it there. pr merge applies the patch and removes the pull request and its todos, in one commit: todoer: merge <name>. On a conflict, nothing changes.

A merge is the approval

There is no approve and no verdict. A committed review asks for changes. pr submit -n <pr> --update writes the whole pull request again and removes the review. pr merge stops while the review has a comment.

Try a pull request of anyone

On a branch of your own, pr apply <pr> puts the patch in your working tree, with no commit. Run the code, or change it and update the pull request with -n <pr> --update.

Code areas in the summary

Name the parts of the code in .todoer/areas, such as security or e2e-tests. pr summary shows how many files and lines each area changes. -a security shows only these files. -x unit-tests hides the tests.

// review in the terminal

Comment on a line, a file, a folder or the whole thing.

Ask a second agent, not the one that wrote the code, to explain the patch and to add your comments. It runs pr details and pr comment. Or read it yourself with todoer pr review <pr>. When the review is done, commit review.md. Select a target:

A target can also name a file that the pull request does not change, to point to code that must change too.

$ todoer pr comment fix-the-login-crash src/auth.rs:2 "Add a test for the retry path."
// the workflow

From a todo to a merge.

You plan and decide. Agents claim, write the code, submit and update. Every step is a commit on your branch, so you can push it at any time.

$ cd ~/code/my-project
$ todoer skill --init
wrote .agents/skills/todoer/SKILL.md  (Codex, Cursor)
wrote .claude/skills/todoer/SKILL.md  (Claude Code, Cursor)
$ todoer add fix-the-login-crash -l auth "Steps to reproduce: ..."
.todoer/todos/fix-the-login-crash.md

Step by step, with what to tell your agent: read the guide.

  1. ClaimTell your agent: “claim fix-the-login-crash”, a list of todos, or a label. todoer claim assigns the todos to you and commits them on your branch. Push the commit when you want.
  2. Implement in a worktree“Implement it in a worktree.” The agent makes a new branch from your branch, writes the code and commits.
  3. Submit into your branchOne command: todoer pr submit --branch main -n <name>. It squashes every commit since the work started from main into one, and commits the pull request on main. Name any branch.
  4. ReviewAsk another agent to explain the patch and to add your comments with todoer pr comment. Then commit the review.
  5. UpdateAsk an agent to do the comments. It restores the patch in a new worktree, so the first branch can be gone. Then it runs todoer pr submit --branch main -n <pr> --update, which writes the whole pull request again and removes the review.
  6. Mergetodoer pr merge <pr>. There is no approve: a merge accepts the pull request. It adds one commit, todoer: merge <pr>, and stops while the review has comments.

Install

curl -fsSL sobanieca.github.io/todoer/install.sh | bash

The script installs todoer to /usr/local/bin, for all users. If that folder is not writable, the script stops with an error. Then run it with sudo:

curl -fsSL sobanieca.github.io/todoer/install.sh | sudo bash

Or pick your own folder with INSTALL_DIR. It must be a folder on your PATH:

curl -fsSL sobanieca.github.io/todoer/install.sh | INSTALL_DIR=~/.local/bin bash

A single binary for Linux and macOS (x64 and arm64), no runtime needed. Update it any time with todoer update. Run todoer help to see every command. todoer is not released yet: until version 1.0.0, any part of it can change.