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

tenancyjs-cli

v0.1.11

Published

Operational CLI for TenancyJS: scaffold, inspect, and run tenant registry, provisioning, and migration commands against your own tenancy config.

Readme

tenancyjs-cli

Safe, deterministic project initialization and diagnostics for TenancyJS.

New to TenancyJS? Start with the docs → — install, the tenancy CLI, and how this package fits with an adapter + integration.

Init supports Express 5.2 with Prisma 7.8, TypeORM 1, Sequelize 6.37, or Drizzle 0.45; AdonisJS 7.3 with Lucid 22.4; and Next.js 16 with Prisma 7.8. It detects the stack from package.json and scaffolds the matching row-level wiring. It uses Node built-ins only, makes no network calls, reads no .env files, and never invokes a shell or remote package runner.

Install & run

The binary is tenancy. You don't have to install it — run it straight from your package manager:

npx tenancyjs-cli init       # npm
pnpm dlx tenancyjs-cli init  # pnpm
yarn dlx tenancyjs-cli init  # yarn
bunx tenancyjs-cli init      # bun

Prefer it installed? Add it globally or as a dev dependency:

npm install -g tenancyjs-cli     # then: tenancyjs-cli init
# or, per-project:
npm install -D tenancyjs-cli     # then: npx tenancyjs-cli init, or a package.json script

Requires Node.js 24+. Every command accepts --json for machine-readable, secret-redacted output.

Commands

# Preview new wiring files; this is the default and writes nothing.
tenancyjs-cli init

# Create only non-conflicting files after path and symlink validation.
tenancyjs-cli init --apply
tenancyjs-cli init --framework express --orm drizzle --apply

# Scaffold a different isolation strategy (default is row-level).
tenancyjs-cli init --framework express --orm sequelize --strategy database-per-tenant --apply
tenancyjs-cli init --framework express --orm typeorm --strategy schema-per-tenant --apply

# Also write a stack-specific TENANCY.md and register a TenancyJS block in an
# existing AGENTS.md/CLAUDE.md. Interactive init offers this; --ai-context opts
# in non-interactively. It never creates an agent-memory file that is not present.
tenancyjs-cli init --apply --ai-context

# Inventory wiring, versions, base clients, raw/nested/relation usage,
# model classification, leak-test evidence, and migration effort.
tenancy doctor
tenancy doctor --json

# Run one explicit, contained JavaScript leak test directly with local Node.
tenancy test:leak --test-file test/tenancy.leak.test.mjs

# Generate review-ready PostgreSQL forced-RLS DDL for your tenant tables.
# Prints SQL only - it executes nothing. Review it, then apply with your migrator.
tenancy policy --table posts --table comments --role app_runtime
tenancy policy --table posts --role app_runtime --tenant-column org_id --out db/rls.sql

All commands accept --root <path>. init never overwrites: matching files are unchanged and differing files are conflicts. Generated writes are staged and rolled back if commit fails.

Doctor exit codes are 0 healthy, 1 warnings, and 2 errors. test:leak returns 0 only when the explicit test file exits successfully. Output redacts URL credentials and secret-like assignments.

Generated Files

Express + Prisma, TypeORM, Sequelize, or Drizzle (Next.js uses lib/tenancy/ + a server helper):

  • tenancy.config.ts
  • src/tenancy/register.ts
  • src/middleware/tenancy.ts
  • test/tenancy.leak.test.mjs — a starter two-tenant isolation test; wire the three TODOs, then prove it with tenancy test:leak. It fails until wired (fail-closed by default).

AdonisJS + Lucid (no leak test — a standalone .mjs can't boot the Adonis runtime; use a japa test with the /testing helper):

  • config/tenancy.ts
  • app/middleware/tenant_middleware.ts

With --ai-context (or by accepting the interactive prompt), init also writes TENANCY.md at the project root — a stack-specific guide of the commands, wiring notes, and isolation model — and adds an idempotent <!-- tenancyjs:start -->…<!-- tenancyjs:end --> block to any AGENTS.md/CLAUDE.md already present so AI assistants pick up the fail-closed rules. Neither file is created if absent; if no agent-memory file exists, init prints the block for you to paste in.

The generated classification is intentionally empty. Classify every model as tenant or central and add a real leak test before Doctor can pass. For AdonisJS, register the provider in adonisrc.ts, apply the middleware to tenant route groups, and add a migration that enables and FORCES PostgreSQL row-level security under a non-privileged runtime role. Static Doctor output estimates migration work; it does not prove runtime tenant isolation.

Security Boundary

  • Project roots are canonicalized with realpath.
  • Absolute paths, traversal, symlink parents/destinations, duplicate paths, and overwrites are rejected.
  • .env, dependencies, generated/build output, VCS metadata, binaries, and large source files are not consumed as configuration.
  • Only the explicit test:leak JavaScript file is executed, via process.execPath and an argument array. The CLI never invokes a shell. The trusted test is not sandboxed, receives only allowlisted database/test/Tenancy environment variables, and is bounded to 120 seconds and 1,000,000 output characters by default.
  • Init never connects to a database or runs migrations; operational migration/provisioning commands delegate only to explicit host runtime hooks.