PostCSS in Practice

Andrey Sitnik, Evil Martians

PostCSS in Practice

Andrey Sitnik, Evil Martians

Our Clients

Our Open Source

Part 1 What is PostCSS?

Older Preprocessors

a {
    <%= include clickable %>
    color: <%= $link-color %>;
}

Inside PostCSS

CSS
source map
Parser
Plugin
Plugin
Stringifier
New CSS
new source map

Usage

gulp.task('css', () => {
    let postcss = require('gulp-postcss');
 
    return gulp.src('src/*.css')
        .pipe( postcss([ plugin1, plugin2 ]) )
        .pipe( gulp.desc('build/') );
});

postcss-nested

.block {
    &_title {
        font-size: 200%;
    }
}
.block_title {
    font-size: 200%;
}

W3C Draft postcss-media-minmax

@media (width <= 600px) {

}
@media (max-width: 600px) {

}

Why did we create PostCSS?

To overcome older preprocessors' limits:

1 000 000 downloads per month

PostCSS Users

Part 2 Plugins

Setting up Plugins

postcss([
    require('autoprefixer')({
        browsers: 'last 2 version'
    }),
    require('postcss-cssnext'),
    require('precss')
])

Problem Implicitness

.icon {
    top: center;
}

Solution postcss-use

@use postcss-center;
 
.icon {
    top: center;
}

Rule 1

All plugins with custom syntax should be added via postcss-use

Rule 2

Start by setting up plugin packs

Part 3 Isolation

Rule 3

Use PostCSS to keep code maintainable—not just for syntax sugar

CommonJS

var moment = require('moment');

Components

Problems

  1. Conflicting selectors
  2. Inherited properties

Problem 1 Conflicting Selectors

logo.css

header.css

.name {
    color: black;
}
.name {
    color: gray;
}

Solution 1 postcss-bem

@b Logo {
    @e name {
        color: gray;
    }
}
.Logo-name {
    color: gray
}

All machines must suffer

Solution 2 CSS Modules

.name {
    color: gray;
}
.Logo__name__sVK0p {
    color: gray
}

CSS Modules in JS

import styles from './logo.css';
 
class Logo extends React.Component {
    render() {
        return <div className={ styles.name }>We</div>;
    }
}

What Isolation You Should Use

CSS Modules:

BEM

Problem 2 Inherited Properties

<Header>
    color: white
    <Logo>
        background: white
    </Logo>
</Header>

Problem 3 Third-Party Widgets

* {
    box-sizing: border-box;
}
div {
    margin-top: 10px;
}

Solution postcss-autoreset

.logo {
    color: black;
}
.logo--big {
    width: 200px;
}
.logo {
    all: initial; 
    color: black;
}
.logo--big {
    width: 200px;
}

W3C Draft postcss-initial — IE support

.logo {
    all: initial;
}
.logo {
    color: black;
    background: white;
    box-sizing: content-box;
    line-height: normal;
    text-shadow: none;
    vertical-align: baseline;
    white-space: normal;

The Best Isolation Method

Part 4 Explicit Code