npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@99percentpeople/pi-todo

v1.2.5

Published

A minimal atomic todo tool with omission-based deletion, compaction-safe state, dependencies, and a read-only Pi widget

Readme

@99percentpeople/pi-todo

A minimal, atomic todo tool for the Pi coding agent. The model writes the complete task plan in one call instead of issuing one create call per task.

You see your plan as a live list above the input box: progress, active task, and dependencies update as the model works, and finished tasks roll off automatically. No commands to learn — just let the model maintain the plan.

The extension intentionally has no todo-specific slash commands, interactive manager, or user-editable todo interface. Todo state belongs to the model. A read-only list is rendered above Pi's input box.

Demo

The model creates the plan, works through it, and the widget tracks progress from 0/3 to 3/3 completed:

todo demo

Features

  • One-call creation of a complete plan
  • One-call completion and handoff to the next task
  • Omission-based deletion without retained cancelled or archived tasks
  • Stable task keys and key-based dependencies
  • Atomic validation with optional optimistic revisions
  • Branch- and compaction-aware state that survives /reload and /tree
  • Read-only collapsible list above the input box

Install

This extension registers the todo tool. Remove another extension that owns the same tool name before installing it:

pi remove npm:@juicesharp/rpiv-todo
pi install npm:@99percentpeople/pi-todo

During local development:

pi -e ./extensions/todo/index.ts

Tool schema

The todo tool accepts the complete authoritative list of tasks to retain. Existing tasks may omit unchanged fields; a new key requires subject and status. Any current key omitted from tasks is permanently deleted:

todo({
  baseRevision?: number,
  tasks: Array<{
    key: string,
    subject?: string,
    description?: string,
    status?: "pending" | "in_progress" | "completed",
    dependsOn?: string[],
  }>,
})

Example:

{
  "baseRevision": 0,
  "tasks": [
    {
      "key": "inspect",
      "subject": "Inspect the existing implementation",
      "status": "in_progress"
    },
    {
      "key": "implement",
      "subject": "Implement the optimized protocol",
      "status": "pending",
      "dependsOn": ["inspect"]
    },
    {
      "key": "verify",
      "subject": "Verify the implementation",
      "status": "pending",
      "dependsOn": ["implement"]
    }
  ]
}

To hand work off, include every current key but only send changed fields:

{
  "baseRevision": 1,
  "tasks": [
    { "key": "inspect", "status": "completed" },
    { "key": "implement", "status": "in_progress" },
    { "key": "verify" }
  ]
}

Subjects and dependencies are inherited from the previous snapshot. Both status changes commit atomically.

To cancel or otherwise delete work, omit its key from the next complete plan:

{
  "baseRevision": 2,
  "tasks": [
    { "key": "inspect" },
    { "key": "implement" }
  ]
}

Deletion is permanent state removal. The extension stores no cancelled status or archived task record. A completed task may retain a dependency only as history: when its completed prerequisite is omitted, that soft reference is automatically removed. A pending or in-progress task cannot retain a dependency on an omitted key.

Semantics

  • key is the task identity while that task remains in the plan.
  • Existing keys inherit omitted fields from their previous state.
  • New keys require subject and status.
  • description: "" and dependsOn: [] explicitly clear those fields.
  • Every key present in tasks remains in the plan; omitted current keys are permanently deleted.
  • Completed tasks remain visible for the current turn, then are automatically removed on the next turn. Completed tasks that still block pending or in-progress work are preserved.
  • tasks: [] clears the plan.
  • baseRevision, when provided, rejects stale writes.
  • Every dependency must refer to another key in the resulting snapshot, except completed-to-completed references are automatically pruned when the target is deleted.
  • Dependency cycles are rejected.
  • An in_progress or completed task requires all dependencies to be completed.
  • Validation is all-or-nothing; failed writes do not mutate state.
  • Multiple independent tasks may be in_progress concurrently.

Each successful result includes the current revision and complete retained plan. When next-turn cleanup changes the plan, the extension emits one hidden custom message containing the new revision and snapshot so the model never works from stale tool history.

State schema v2 removes internal numeric IDs, archived records, and the cancelled status. Valid v1 session state is migrated on replay; archived and cancelled legacy tasks are discarded, and one hidden v2 checkpoint updates the model on the next prompt.

Rendering

The task list is rendered in a read-only widget above Pi's input box. It follows Pi's standard tool-output expansion state (Ctrl+O by default):

  • collapsed: overall progress and a configurable number of tasks (three by default);
  • expanded: the complete todo list with status glyphs, task names, and resolved prerequisites.

While the model is streaming a todo call, the tool row updates in place and shows each task name and its compact dependency references as they are written instead of only showing a task count. Sparse updates reuse the current task name and status until their changed fields arrive. Fields that are not yet known are omitted: a new task appears after its subject is written, and its status glyph appears only after its status is available. This live preview uses the configured collapsed-item limit and shows all tasks when expanded. After a successful write, the result renderer stays empty because the completed tool call already contains the final list; validation errors are still displayed below the attempted list.

Tasks always keep their plan order. When collapsed, the widget selects a window around the first in_progress task where possible. If no task is active, it shows the first configured number of tasks. Once every task is completed, it shows the last configured number instead so the most recently finished work remains visible. The expand/collapse hint is shown only when the complete list exceeds that limit.

in_progress task labels are rendered in bold in both the live tool call and widget. The model-facing result still includes keys, dependencies, and descriptions. In the user-facing display, dependency numbering can be shown or hidden. When shown, tasks participating in the dependency graph receive plan-order display numbers after their names, such as ○ Inspect #1 and ○ Implement #2 ← #1. Independent tasks stay unnumbered, multiple prerequisites use ← #1, #2, and stable task keys remain hidden. These numbers are display-only and may be reassigned when the plan changes. The shortcut respects the user's app.tools.expand keybinding.

Persistence

Normal writes are stored in tool-result details. Automatic next-turn removals are stored in hidden custom-message details; the same message also tells the model which snapshot and revision are current. On session_start, /reload, and /tree navigation, the extension restores the latest valid state entry from the active branch.

After compaction, the extension stores an exact schema-v2 checkpoint outside the model context. It injects that snapshot as one hidden model-facing message on the next prompt, or immediately as steering context when overflow recovery or an already queued continuation proceeds without a new prompt. This preserves exact keys, dependencies, and revision numbers without triggering an extra model turn.

Shared settings

Use the shared /99settings menu to choose how many Todo items are shown while the widget and streaming tool call are collapsed, and whether display-only dependency numbers are shown. Collapsed-item presets are 1, 2, 3, 5, 8, and 10; the default remains 3. Dependency numbers default to shown. Values are stored under the todo namespace in ~/.pi/agent/99extensions.json.

License

MIT