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

skills-package-manager

v0.3.0

Published

Core library and CLI for managing agent skills.

Readme

spm

Core library and CLI for managing agent skills.

CLI Usage

spm --help
spm --version
spm add <specifier> [--skill <name>]
spm install
spm update [skill...]
spm init [--yes]
  • spm with no command shows top-level help
  • spm --help prints top-level help
  • spm --version prints the package version

spm add

Add skills to your project.

# Interactive — clone repo, discover skills, select via multiselect prompt
spm add owner/repo
spm add https://github.com/owner/repo

# Non-interactive — add a specific skill by name
spm add owner/repo --skill find-skills

# Direct specifier — skip discovery
spm add https://github.com/owner/repo.git#path:/skills/my-skill
spm add file:./local-source#path:/skills/my-skill

After spm add, the newly added skills are resolved, materialized into installDir, and linked to each configured linkTarget immediately.

How it works

When given owner/repo or a GitHub URL:

  1. Shallow-clones the repository into a temp directory
  2. Scans for SKILL.md files (checks root, then skills/, .agents/skills/, etc.)
  3. Presents an interactive multiselect prompt (powered by @clack/prompts)
  4. Writes selected skills to skills.json and resolves skills-lock.yaml
  5. Cleans up the temp directory

spm init

Create a new skills.json manifest in the current directory.

# Interactive — prompt for installDir and linkTargets
spm init

# Non-interactive — write the default manifest immediately
spm init --yes

Behavior:

  • spm init prompts for installDir and linkTargets, then writes skills.json
  • spm init --yes skips prompts and writes the default manifest
  • If skills.json already exists, the command fails and does not overwrite it

Default skills.json written by spm init --yes:

{
  "installDir": ".agents/skills",
  "linkTargets": [],
  "skills": {}
}

spm install

Install all skills declared in skills.json:

spm install

This resolves each skill from its specifier, materializes it into installDir (default .agents/skills/), and creates symlinks for each linkTarget.

spm update

Refresh git-based skills declared in skills.json without changing the manifest:

spm update
spm update find-skills rspress-custom-theme

Behavior:

  • Uses skills.json as the source of truth
  • Re-resolves git refs to the latest commit
  • Skips file: skills
  • Fails immediately for unknown skill names
  • Writes skills-lock.yaml only after fetch and link succeed

Programmatic API

import { addCommand, installCommand, listRepoSkills } from 'skills-package-manager'

// Add a skill
await addCommand({
  cwd: process.cwd(),
  specifier: 'vercel-labs/skills',
  skill: 'find-skills',
})

// Install all skills from skills.json
await installCommand({ cwd: process.cwd() })

// List skills in a GitHub repo (clone + scan)
const skills = await listRepoSkills('vercel-labs', 'skills')
// => [{ name: 'find-skills', description: '...', path: '/skills/find-skills' }]

Specifier Format

<source>#[ref&]path:<skill-path>

| Part | Description | Example | |------|-------------|---------| | source | Git URL or file: path | https://github.com/o/r.git, file:./local | | ref | Optional git ref | main, v1.0.0, HEAD, 6cb0992, 6cb0992a176f2ca142e19f64dca8ac12025b035e | | path | Path to skill directory within source | /skills/my-skill |

ref can point to a branch, tag, full commit SHA, or short commit SHA.

Resolution Types

  • git — Clones the repo, resolves commit hash, copies skill files
  • file — Reads from local filesystem, computes content digest

Architecture

src/
├── bin/           # CLI entry points (spm, skills)
├── cli/           # CLI runner and interactive prompts
├── commands/      # add, install command implementations
├── config/        # skills.json / skills-lock.yaml read/write
├── github/        # Git clone + skill discovery (listSkills)
├── install/       # Skill materialization, linking, pruning
├── specifiers/    # Specifier parsing and normalization
└── utils/         # Hashing, filesystem helpers

Build

pnpm build    # Builds with Rslib (ESM output + DTS)

Test

pnpm test     # Runs tests with Rstest

``