A starter project for PostCSS plugins.
- ๐ฏ PostCSS 8+ compatible - Uses the latest plugin API
- ๐งช Complete test suite - Vitest with coverage reporting
- ๐ง Development tooling - Biome for linting and formatting
- ๐ Well-documented - Comprehensive examples and comments
- โ Complete hooks reference - Includes all hooks PostCSS exposes
- ๐ Production ready - Includes CI/CD scripts and
package.json
boilerplate
- Clone or fork this repository
- Install dependencies:
npm install
- Run tests:
npm test
- Start development with watch mode:
npm run dev
- Start developing your plugin in
src/index.js
This boilerplate demonstrates all major PostCSS plugin hooks:
Hook | Purpose | Example Use Case |
---|---|---|
Once |
Runs once per CSS file | Add header comments, global setup |
Root |
Process entire CSS AST | Global transformations |
AtRule |
Handle at-rules (@media , @import , etc.) |
Transform or remove specific at-rules |
Rule |
Process CSS rules (selectors) | Transform selectors |
Declaration |
Handle CSS properties and values | Transform properties or values |
Comment |
Process CSS comments | Remove or transform comments |
OnceExit |
Final processing | Add footer comments, cleanup |
The starter includes several example options:
import postcss from 'postcss';
import plugin from 'postcss-starter';
postcss({
plugins: [
plugin({
addComment: true, // Add header comment
addFinalComment: true, // Add footer comment
transformSelectors: true, // Transform .old- to .new-
transformValues: true, // Transform custom() to var()
removeComments: true, // Remove TODO comments
logMediaQueries: true // Log @media queries to console
})
]
}).process(css, { from: 'input.css', to: 'output.css' })
.then(result => {
console.log(result.css);
});
/* TODO: Fix this later */
@media (max-width: 768px) {
.old-header {
--custom-color: blue;
background: custom(primary);
}
}
/* Processed by postcss-starter */
@media (max-width: 768px) {
.new-header {
--my-color: blue;
background: var(--primary);
}
}
/* Processed successfully */
Run tests in watch mode with Vitest:
npm run dev
Run tests with coverage and linting:
npm test
Run Biome for linting and formatting:
npm run lint
Release new version using np
:
npm run release
-
Update the plugin name in
src/index.js
:const PLUGIN_NAME = 'postcss-your-plugin-name';
-
Update
package.json
:{ "name": "postcss-your-plugin-name", "description": "Your plugin description" }
-
Update test descriptions in
test/index.test.js
- Add new hook or extend existing ones in
src/index.js
- Add corresponding tests in
test/index.test.js
- Update README with new options and examples
- Run tests to ensure everything works (
npm test
)
Declaration(decl) {
// Your existing transformations...
// New transformation
if (opts.transformUnits && decl.value.includes('px')) {
decl.value = decl.value.replace(/(\d+)px/g, (match, num) => {
return `${num / 16}rem`;
});
}
}
- Update package.json: version, description, keywords
- Run tests:
npm test
(includes linting and coverage) - Update README: with actual plugin functionality
- Test in real project: Create a test PostCSS setup
The npm run release
script uses np for automated, interactive releases with proper versioning, changelog generation, and npm publishing.