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

claude-taste

v0.3.0

Published

Learned coding preferences for Claude Code and OpenCode — captured from real signals, stored as markdown, shared over git.

Readme

taste

Learned coding preferences for Claude Code and OpenCode. Captured from real signals, stored as markdown you can read and delete, shared over git.

taste status                      # is learning on, what's stored, what's pending
taste show                        # what it thinks you prefer, and how sure it is
taste push --all                  # share with your team, over your own git repo

Why this exists

Command Code ships a feature called Taste, "powered by our meta neuro-symbolic AI model taste-1 with continuous reinforcement learning." Claude Code has no equivalent product — but it has every part needed to build one, and the honest version turns out to be small.

This is that version. Same shape (learn from your work, store as packages, push and pull), no claim of a per-user model that does not exist.

What Claude Code already gives you

| Capability | Claude Code | Gap this fills | | --- | --- | --- | | Persistent instructions | CLAUDE.md, .claude/rules/*.md | You write them by hand | | Reusable procedures | Skills, subagents | Not derived from your behavior | | Event capture | Hooks on 30+ lifecycle events | Nothing consumes them for preferences | | Sharing | Plugins + marketplaces (git repos) | Not per-preference, not merged | | Layered config | enterprise → local → project → user | — |

The gap is the loop: nothing watches what you actually do and turns it into instructions with a confidence attached. That loop is what this adds.

How it works

hooks ──► .claude/taste-signals.jsonl ──► /taste-learn ──► .claude/taste/**/taste.md ──► model context
capture        raw evidence, local           you review          rules + confidence         inject

Capture (hooks/capture.mjs) writes one JSONL line per event: prompts you submit, edits that land, tool calls you deny, turn boundaries. Local only, never pushed, silent when learning is off.

It also watches for the loudest signal there is — you rewriting what the coding agent wrote. Each file the agent touches gets snapshotted; at your next prompt the snapshot is compared against disk, and any hand edit is recorded with its diff:

{ "kind": "revision", "file": "parser.ts", "line": 2,
  "removed": ["  // Parse the input string into tokens", "  if (input) {"],
  "added":   ["  if (!input) return [];"] }

That single record contains two preferences — no comments restating the code, guard clauses over nesting. Detection is lazy (a hash comparison at prompt time), so there is no watcher, no daemon, and no background process. The agent's own later edits re-snapshot the file, so they never masquerade as your corrections.

Distill (/taste-learn) is the coding agent reading that log and proposing rules. This is the deliberate part. A preferences file you never agreed to is worse than no preferences file, so distillation is a step you take, not something that happens behind you.

Inject puts only rules above the confidence floor into context, capped at a character budget. Claude Code injects at session start; OpenCode injects on each model request. Everything else stays on disk until it earns its place.

Share is git. taste push -g moves a package to your global store; taste push --all commits and pushes to a repo you own. Merges are by rule id.

The file format

Human-first markdown. The bookkeeping rides in an HTML comment, invisible when rendered, so the file stays something you can read, edit, and argue with.

## Put tests next to the source file, not in a top-level tests/ dir
<!-- taste {"id":"put-tests-next-to-the-source-file","confirms":4,"contradicts":0,
     "first":"2026-06-02T…","last":"2026-07-27T…","sources":["edit","stated"]} -->

Observed across 6 files during the parser work.

The scoring rule

Confidence is a Beta-Bernoulli posterior mean over "did this preference hold up?", with each past observation discounted by a 90-day half-life:

c(t) = (α₀ + C̃(t)) / (α₀ + β₀ + C̃(t) + D̃(t))

C̃(t) = Σᵢ λ^((t − tᵢ)/H)   over confirmations
D̃(t) = Σⱼ λ^((t − tⱼ)/H)   over contradictions

α₀ = 1, β₀ = 2, λ = ½, H = 90 days

Observations are weighted by where they came from: something you said counts ×3, a revision or a denial ×2, an inferred edit ×1. A rule you stated outright is stronger evidence than one guessed from a diff.

The prior starts an unseen rule at 0.33, so one sighting is not evidence. Confirmations and contradictions are stored as the decayed running totals rather than a full event list, which is algebraically identical and much cheaper — there is a test asserting exactly that.

The injection floor is 0.65, deliberately between two confirmations (0.600) and three (0.667): a pattern seen twice is a coincidence. Something you said (--source stated) counts triple and clears the floor on its own.

That is the entire model. It is 40 lines in src/confidence.mjs, and you should read it before trusting a number it prints.

About that other equation

Command Code's docs render this as an image on the Taste page:

Meta-NeuroSymbolic Objective(φ) = 𝔼ₓ~D_RL 𝔼_y~LLM^NS_φ(x) [ RM_NS(x,y) − β_NS log( LLM^NS_φ(y|x) / LLM^SFT(y|x) ) ] + γ_NS 𝔼ₓ~D_pretrain log LLM^NS_φ(x)

Term by term: sample a prompt x, sample a response y from the current policy, score it with a reward model, subtract a KL penalty that keeps the policy from drifting away from the supervised-fine-tuned reference (β sets the leash), and add a pretraining log-likelihood term so alignment training does not degrade general capability (γ sets the mix).

This is the PPO-ptx objective from InstructGPT (Ouyang et al., 2022, eq. 2), with π renamed to LLM, r_θ renamed to RM, and the subscript NS appended to every term. Nothing in it is neuro-symbolic: there is no symbolic term, no logic or program component, no constraints. Nothing in it is meta-learned: no inner and outer loop, no task distribution, one set of parameters φ under one expectation. It is standard RLHF, correctly transcribed, relabelled.

It is also not something that can run on your laptop from your accept/reject signals — it describes gradient updates to a foundation model during training, not per-user adaptation at the keyboard. Whatever such a feature does in practice is almost certainly what this repo does explicitly: write preferences down and put them in the prompt.

So the equation above is the one this project actually implements. It is much smaller, and it runs.

Install

OpenCode / OpenCode Rig

From a local clone, link the CLI and register the repository as both a plugin and a skill source:

cd /absolute/path/to/taste
npm link

Merge these entries into ~/.config/opencode/opencode.jsonc:

{
  "plugin": ["/absolute/path/to/taste"],
  "skills": {
    "paths": ["/absolute/path/to/taste/skills"]
  }
}

Restart OpenCode after changing config. The two skills appear as /taste and /taste-learn; the plugin captures prompts, successful edits, denied permissions, and turn boundaries, and injects earned preferences. It deliberately continues using .claude/taste/ so Claude Code and OpenCode share one store.

Claude Code

As a Claude Code plugin — this repo is its own marketplace, so it is two steps. plugin install takes a plugin name, never a path:

claude plugin marketplace add toshon-jennings/taste
claude plugin install taste@taste

That gets you both skills, the five hooks, and taste on your PATH inside Claude Code, for about 126 tokens of always-on context.

From a local clone, point the marketplace at the directory instead:

claude plugin marketplace add ./taste
claude plugin install taste@taste

Then, in any project:

taste init

Or skip the plugin and use the CLI alone — you lose the hooks, so nothing is captured automatically, but add, show, push, and pull all work:

npm link && taste status

Working on this repo

Installing copies the plugin into ~/.claude/plugins/cache/ pinned to the version in plugin.json, so edits to your working copy do nothing until you bump it and refresh:

claude plugin marketplace update taste && claude plugin update taste@taste

Drop version from plugin.json if you would rather track the commit SHA and get a new version on every commit.

Commands

| Command | Does | | --- | --- | | taste status | learning state, counts, pending signals, remote | | taste enable \| disable [-u] | toggle learning; -u for all projects | | taste list [-g] | packages and learning counts | | taste show [<pkg>] [-g] | learnings with confidence and evidence | | taste add <pkg> "<rule>" | record a confirmation (--contradict, --note, --source) | | taste lint [<pkg>\|--all] [--fix] | validate format and confidence values | | taste open <pkg> [-g] | open in $EDITOR | | taste push <pkg>\|--all [-g] | share to global (-g) or the git remote | | taste pull <pkg>\|--all [-g] | pull the other way (--overwrite to skip merging) | | taste remote [<git-url>] | get or set the sharing remote | | taste signals [--tail N\|--next N\|--json\|--consume [N]\|--clear] | inspect or advance through raw evidence | | taste context [--min 0.65] | render exactly what gets injected |

Settings

Precedence, highest first. taste status reports which file decided.

| Priority | File | Affects | Committed | | --- | --- | --- | --- | | 1 | .claude/taste.local.json | local setup only | no | | 2 | .claude/taste.json | this project | yes | | 3 | ~/.claude/taste.json | all your projects | — | | 4 | unset | — | on by default |

These are separate files rather than keys inside Claude Code's own settings.json, so toggling taste can never invalidate the host's config.

Privacy

Two things are written locally and never shared:

  • .claude/taste-signals.jsonl — the signal log, which contains your prompts
  • .claude/taste-watch/ — snapshots of files the coding agent wrote, used to diff your hand edits. Capped at 50 files and 256 KB each. Files that look sensitive (.env, *.pem, *.key, id_rsa, credentials, secrets.*) are never snapshotted, and there is a test asserting that.

taste init adds both to .gitignore. Only distilled rules are ever pushed. taste signals --clear wipes the log and the snapshots. taste disable stops capture entirely: preferences stated during a session stay in that session.

Nothing in this repo makes a network call except taste push / taste pull, which run git against a remote you configured.

Development

node test/run.mjs

28 tests, no dependencies, covering the scoring rule (monotonicity, decay, the equivalence of running totals and event replay, the floor boundaries), the store (round-trip, dedupe, merge idempotence), and revision detection (exact diffs, report-once, no false positive from the agent's own edits, secrets never snapshotted, bounded tracking with no orphaned files), plus the OpenCode adapter and bounded signal-batch consumption.

License

MIT