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

open-sites-mcp

v0.9.0

Published

MCP server that lets any AI agent (Claude Desktop, Claude Code, Cursor, …) create, publish, and share websites on a self-hosted open-sites hub

Readme

open-sites-mcp

MCP server that gives any AI agent — Claude Desktop, Claude Code, Cowork, Cursor, or anything else that speaks the Model Context Protocol — the tools to create, version, publish, and share websites on a self-hosted open-sites hub: an open equivalent of ChatGPT Sites you run yourself.

Setup

  1. You need a hub: deploy one in a few minutes with the Vercel guide or Docker.

  2. Sign in once from a terminal (stores an API token in ~/.config/open-sites/config.json):

    npx open-sites-mcp login https://your-hub.example.com

    …or create a token in the hub's Settings page and pass it as environment variables (see below).

  3. Add the server to your MCP client:

    {
      "mcpServers": {
        "open-sites": {
          "command": "npx",
          "args": ["-y", "open-sites-mcp"]
        }
      }
    }

    Claude Desktop: Settings → Developer → Edit Config. Cursor: .cursor/mcp.json. Claude Code: claude mcp add open-sites -- npx -y open-sites-mcp (or install the plugin, which also ships a site-building skill).

    To use environment variables instead of login, add "env": { "OPEN_SITES_URL": "https://your-hub.example.com", "OPEN_SITES_TOKEN": "ost_…" }.

Without configuration the server still starts; every tool then explains how to connect. npx open-sites-mcp status shows what it would connect as, logout removes the stored token.

Tools

| Tool | What it does | |---|---| | list_sites (q, owner, sort, limit, offset) | Sites you can access, with owner (ownerKind: personal | team), visibility, deployed version, version count, URL, hasServer (the deployed version runs server code) | | create_site · get_site · update_site · delete_site | Lifecycle; create_site takes an optional org, update_site renames, changes the slug, or transfers to another user/organization | | save_version | Save a complete set of files as a new version (optionally deploy); add _server/index.js for a full-stack site (server syntax errors are rejected at save time) | | update_files | Change some files / remove paths on top of the latest (or any) version | | get_version_files | List files of latest / deployed / n, optionally with contents in one call | | deploy · undeploy · list_versions · delete_version | Publish, roll back, take offline, tidy up (list_versions paginates and reports file counts/sizes and hasServer) | | diff_versions | Added / removed / changed / moved files between two versions (from/to accept latest/deployed); include_patch adds unified patches | | list_kv · get_kv · delete_kv · list_objects · delete_object | Inspect and tidy the runtime data a site stored via _api/kv / _api/objects (editors) | | set_secrets · list_secrets · delete_secret | Secrets a full-stack site's server code reads as env.SECRETS.NAME — set/replace/delete by name (owner), list names only (values are never returned) | | get_logs (limit, offset, since, kind, level, requestId) | Server logs of a full-stack site, newest first: request lines, console output, uncaught errors with stacks — pass the request id from a 500 page to see one request end to end | | get_build (slug, version?, wait?) · rebuild (slug, version?) · get_container (slug) · restart_container (slug) | Container apps (a Dockerfile in the version, run by the hub's runner): build state — wait polls until ready/failed —, re-run a build, the deployed container's status, recreate it | | run_sql (slug, query, params?, maxRows?) | Run SQL in the site's own Postgres schema as the site's role (owner): one statement with params, or a ;-script in one transaction — create/migrate tables before deploying, inspect and repair data. Errors: sql_error with details.sqlstate/position | | list_tables (slug) | The site's tables with columns, row counts and size, plus usage against the per-site quota and whether SQL is on/off/unavailable on the hub (editors) | | get_usage | Storage a site uses (incl. server-log rows and secret count); admins get hub-wide totals with a per-owner breakdown when slug is omitted | | get_preview_url | Temporary sandboxed link to review any version before deploying | | set_access · list_users · create_user | Private / password / public, per-user grants, anonymous-write toggle | | list_orgs · get_org · create_org · set_org_members | Organizations: sites owned by a team rather than a person; members need no per-site grant | | get_analytics | Views, uniques, per-day series, top pages | | whoami | Which hub/user the server is connected as, which organizations they belong to, whether the hub allows server code (hub.functions) and per-site SQL (hub.sql) |

Sites are static HTML/CSS/JS with a built-in runtime API for visitor identity and per-site / per-visitor storage — see the hub docs. A version that contains _server/index.js (export default { async fetch(request, env, ctx) }) is full-stack: static files win for GET/HEAD, everything else runs the sandboxed handler with env.KV, env.OBJECTS, env.SQL (a Postgres schema of its own — run_sql/list_tables manage it), env.SECRETS, env.visitor and outbound fetch; get_logs shows what happened. On hubs with a runner (whoamihub.containers: "on") a version with a root Dockerfile is a container app in any language — the hub builds and runs it (get_build, get_container), still versioned and access-controlled. Errors come back as Hub error <status> (<code>): <message> with stable codes so agents can react — validation_failed, bad_request, unauthorized, forbidden, not_found, conflict, payload_too_large, rate_limited (wait Retry-After seconds, then retry), sql_error (a Postgres error from run_sql; details.sqlstate), unavailable (SQL or containers off/unavailable on the hub), build_pending / build_failed / container_start_failed (container apps), quota_exceeded (don't retry; details.quota is sitesPerOrg | bytesPerOrg | versionsPerSite | kvScopesPerSite | orgsPerUser | sqlBytesPerSite | containerAppsPerOrg — the message says what to delete or that the hub admin must raise the quota), internal_error. Hubs enforce per-owner quotas (QUOTA_*) and hub-wide rate limits (RATE_LIMIT_*); get_usage shows a site's storage. MIT.