Skip to content
This repository has been archived by the owner on Dec 25, 2023. It is now read-only.

csstools/cccp

Repository files navigation

CCCP (Compact Client-side Compatible PostCSS) PostCSS Logo

NPM Version Build Status Licensing Changelog Gitter Chat

Introduction · Usage · Writing a Plugin · API · JSON Syntax

CCCP lets you use CSS as JSON on the client-side and still apply PostCSS plugins.

body {
	font-size: 16px;
}
[0, [2, "body", [3, "font-size", "16px"]]]
cccp.render(json, [plugins]); // creates <style> with css from json

Normally, including PostCSS in the browser would consume 30KB, while this script is only 1KB.

Usage

Add CCCP to your build tool:

npm install cccp --save-dev
require('cccp/postcss').process(YOUR_CSS, { /* options */ });

PostCSS

Add PostCSS to your build tool:

npm install postcss --save-dev

Use CCCP as a plugin

postcss([
	require('cccp/postcss')({ /* options */ })
]).process(YOUR_CSS, /* options */);

PostCSS Gulp

Add Gulp PostCSS to your build tool:

npm install gulp-postcss --save-dev

Use CCCP in your Gulpfile:

var postcss = require('gulp-postcss');

gulp.task('css', function () {
	return gulp.src('./src/*.css').pipe(
		postcss([
			require('cccp/postcss')({ /* options */ })
		])
	).pipe(
		gulp.dest('.')
	);
});

PostCSS Grunt

Add Grunt PostCSS to your build tool:

npm install grunt-postcss --save-dev

Use CCCP in your Gruntfile:

grunt.loadNpmTasks('grunt-postcss');

grunt.initConfig({
	postcss: {
		options: {
			use: [
				require('cccp/postcss')({ /* options */ })
			]
		},
		dist: {
			src: '*.css'
		}
	}
});

Options

json

Type: Path | Function
Default: ${ css.source.input.file || path.join(process.cwd(), 'index') }.json

The path to the JSON file generated by the CSS. If a function is passed, the plugin will send the non-stringified JSON to that function, rather than write the stringified JSON to a file.


Plugins

CCCP plugins are very similar to PostCSS plugins with a few key differences:

  • Plugins do not declare themselves with postcss.plugin(name, plugin). Let source maps handle tracking.
  • Plugins hook into a single walker to save processing.
  • Plugins have less methods; remove() becomes an empty replaceWith() and removeAll() becomes an empty replaceChildren() — less methods provide small savings, but the repetitions due to less methods improve gzipping.

Writing a Plugin

Plugins contain keys that intercept a specific kind of node.

module.exports = {
	root(node) {
		// do something with a root, similar to how PostCSS works
	},
	atrule(node) {
		// do something with an at-rule
	},
	rule(node) {
		// do something with a rule
	},
	decl(node) {
		// do something with a declaration
	}
};

API

CCCP

cccp is a global object containing methods to process JSON as CSS.

cccp.process

cccp.process( json, plugins )

Parses the JSON. Returns a Promise of the resulting CSS.

cccp.render

cccp.render( json, plugins )

Parses the JSON and inserts the resulting CSS into a new <style> element on the page. Returns a Promise of the resulting CSS.

Node

CCCP nodes share the same methods as their PostCSS counterparts, only with a little less sugar.

Node#type

node.type // 'root' | 'atrule' | 'rule' | 'decl'

The type of the current node.

Node#nodes

node.nodes // ...nodes

The array of children of the current node.

Node#name

node.name // string name

The name of the current atrule node (e.g. media).

Node#params

node.params // string params

The params of the current atrule node (e.g. screen and (min-width: 1200px)).

Node#selector

node.selector // string selector

The selector of the current rule node (e.g. #the.quick[data-brown="fox"]).

Node#prop

node.prop // string property

The property of the current declaration node (e.g. background-color).

Node#value

node.value // string value

The value of the current declaration node (e.g. blue url(background.jpg) no-repeat).

The type of node being worked with.

Node#replaceWith

node.replaceWith( ...nodes )

Replaces the current node with nodes. Returns the current node.

If you need to remove a node, pass no arguments to Node#replaceWith().

Node#before

node.before( ...nodes )

Inserts nodes before the current node. Returns the current node.

Node#after

node.after( ...nodes )

Inserts nodes after the current node. Returns the current node.

Node#clone

node.clone( ...props )

Returns a clone of the current node using properties you specify.

Node#prepend

node.prepend( ...nodes )

Inserts nodes as starting children of the current node. Returns the current node.

Node#append

node.append( ...nodes )

Inserts nodes as ending children of the current node. Returns the current node.

Node#replaceChildren

node.replaceChildren( ...nodes )

Replaces all children of the current node with nodes. Returns the current node.

If you need to empty a node of children, pass no arguments to Node#replaceChildren().

Node#walk

node.walk( callback )

Traverses the current node’s descendants with the callback (until the callback returns false). Returns the current node.

If you need to iterate through a Node’s immediate children, use Node.nodes#forEach.

JSON

It is recommended that you use the PostCSS plugin to generate the JSON version of a CSS tree.

root

[ 0, ...nodes ]

A root contains child nodes.

atrule

[ 1, name, params, ...nodes ]

An atrule contains a name, params, and any child nodes.

rule

[ 2, selector, ...nodes ]

A rule contains a selector and any child nodes.

decl

[ 3, prop, value ]

A decl contains a property and value.

Releases

No releases published

Packages

No packages published