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 🙏

© 2025 – Pkg Stats / Ryan Hefner

tailwindcss-patch

v8.4.3

Published

patch tailwindcss for exposing context and extract classes

Readme

tailwindcss-patch

Modern tooling to patch Tailwind CSS, capture runtime contexts, and materialise every class that Tailwind can generate. The package now ships with a redesigned architecture focused on clarity, predictable configuration, and first-class Tailwind v4 support.

  • Export runtime contexts for Tailwind v2/v3 without editing source files manually.
  • Traverse Tailwind v4 projects by scanning CSS outputs and content sources.
  • Write class inventories to disk or keep them in memory for tooling integrations.
  • Control caching, filtering, and custom unit extensions from a single, typed entrypoint.

Installation

pnpm add -D tailwindcss-patch
pnpm dlx tw-patch install

Keep the patch applied after installs by adding a prepare hook:

{
  "scripts": {
    "prepare": "tw-patch install"
  }
}

CLI Usage

Run the CLI through tw-patch (or tailwindcss-patch) from your project root.

# Apply runtime patches to the local Tailwind installation
pnpm dlx tw-patch install

# Extract all classes into the configured output file
pnpm dlx tw-patch extract

# Capture every token (candidate) with file/position metadata
pnpm dlx tw-patch tokens --format lines

Embed into another CLI

Reuse the same commands inside your own cac program:

import cac from 'cac'
import { mountTailwindcssPatchCommands } from 'tailwindcss-patch'

const cli = cac('my-tool')
mountTailwindcssPatchCommands(cli, {
  commandPrefix: 'tw:', // optional
  commands: ['install', 'tokens'], // mount a subset if needed (defaults to all)
  commandOptions: {
    install: { name: 'patch-install', aliases: ['tw-install'] }, // override names/aliases
  },
})
cli.help()
cli.parse()

Custom command hooks

Hosts can override per-command lifecycles by supplying commandHandlers. Each handler receives a context object (with the resolved cwd, parsed args, memoized loadConfig/createPatcher helpers, and the shared logger) plus a next() callback that runs the built-in action.

mountTailwindcssPatchCommands(cli, {
  commandHandlers: {
    install: async (ctx) => {
      const patcher = await ctx.createPatcher()
      await clearTailwindcssPatcherCache(ctx.cwd)
      await patcher.patch()
      await saveCliPatchTargetRecord({ cwd: ctx.cwd })
    },
    extract: async (ctx, next) => {
      const result = await next() // run the default extract implementation
      ctx.logger.success(`[host] wrote ${result.classList.length} classes`)
      return result
    },
  },
  commandOptions: {
    extract: {
      description: 'Localised extract command',
      appendDefaultOptions: false,
      optionDefs: [
        { flags: '--entry <file>', description: 'Tailwind CSS entry file' },
        { flags: '--preview', description: 'Print a preview instead of writing' },
      ],
    },
  },
})

Skip next() to fully replace a command (e.g. custom init or cache clearing before install). Calling next() returns the default result—ExtractResult, TailwindTokenReport, etc.—so hosts can log metadata or feed it into their own telemetry without re-implementing the commands.

Extract options

| Flag | Description | | ------------------------ | ---------------------------------------------------------------- | | --cwd <dir> | Use a different working directory when loading configuration. | | --output <file> | Override the target file for the generated class list. | | --format <json\|lines> | Switch between JSON output (default) and newline-delimited text. | | --css <file> | Provide a CSS entry file when working with Tailwind v4 projects. | | --no-write | Skip writing to disk and only return the collected classes. |

The CLI loads tailwindcss-patch.config.ts via @tailwindcss-mangle/config. Legacy configs continue to work; see the migration guide for hints on the new fields.

Token report options

| Flag | Description | | -------------------------------------- | ----------------------------------------------------------------------------------------- | | --cwd <dir> | Use a different working directory when loading configuration. | | --output <file> | Override the token report target file (defaults to .tw-patch/tw-token-report.json). | | --format <json\|lines\|grouped-json> | Choose between a JSON payload (default), newline summaries, or JSON grouped by file path. | | --group-key <relative\|absolute> | Control grouped-json keys (defaults to relative paths). | | --no-write | Skip writing to disk and only print a preview. |

Programmatic API

import { TailwindcssPatcher } from 'tailwindcss-patch'

const patcher = new TailwindcssPatcher({
  overwrite: true,
  cache: {
    enabled: true,
    dir: '.tw-patch/cache',
    strategy: 'merge',
  },
  output: {
    file: '.tw-patch/tw-class-list.json',
    format: 'json',
  },
  features: {
    exposeContext: { refProperty: 'runtimeContexts' },
    extendLengthUnits: {
      units: ['rpx'],
    },
  },
  tailwind: {
    version: 4,
    v4: {
      base: './src',
      cssEntries: ['dist/tailwind.css'],
    },
  },
})

await patcher.patch()
const { classList, filename } = await patcher.extract()
const tokenReport = await patcher.collectContentTokens()
console.log(tokenReport.entries[0]) // { rawCandidate, file, line, column, ... }
const groupedTokens = await patcher.collectContentTokensByFile()
console.log(groupedTokens['src/button.tsx'][0].rawCandidate)
// Preserve absolute file paths:
// await patcher.collectContentTokensByFile({ key: 'absolute', stripAbsolutePaths: false })

The constructor accepts either the new object shown above or the historical patch/cache shape. Conversions happen internally so existing configs remain backwards compatible.

Helper utilities

  • normalizeOptions – normalise raw user input to the runtime shape.
  • CacheStore – read/write class caches respecting merge or overwrite semantics.
  • extractProjectCandidatesWithPositions – gather Tailwind tokens for every configured source file with location metadata.
  • groupTokensByFile – convert a token report into a { [filePath]: TailwindTokenLocation[] } map.
  • extractValidCandidates – scan Tailwind v4 CSS/content sources with the Tailwind Oxide scanner.
  • runTailwindBuild – run the Tailwind PostCSS plugin for v2/v3 projects to prime runtime contexts.

All helpers are exported from the package root for direct consumption in custom tooling.

Configuration Example

// tailwindcss-patch.config.ts
import { defineConfig } from 'tailwindcss-patch'

export default defineConfig({
  patch: {
    output: {
      filename: '.tw-patch/tw-class-list.json',
      removeUniversalSelector: true,
      format: 'json',
    },
    tailwindcss: {
      version: 4,
      v4: {
        cssEntries: ['dist/tailwind.css'],
        sources: [{ base: 'src', pattern: '**/*.{html,tsx}', negated: false }],
      },
    },
    applyPatches: {
      exportContext: true,
      extendLengthUnits: {
        units: ['rpx'],
      },
    },
  },
})

Even though defineConfig still exposes the historical shape, every new option is supported and will be normalised automatically.

Migration

Breaking changes, module moves, and upgrade paths are documented in MIGRATION.md. Review it when updating from tailwindcss-patch v7.x or earlier.

License

MIT © ice breaker