Home

Awesome

<img src="media/header.svg" width="800" align="center" alt="cssed"/>

cssed

🤷‍♂️ CSS-in-JS modules (via babel plugin):

Rationale

Why create another CSS-in-JS library? Well, I tried hard to avoid doing it, but couldn't find one which does what I want. And I don't want much:

  1. Template literals syntax.
  2. Write pure CSS/SASS/stylus but in JS.
  3. Media queries and pseudoclasses support.
  4. Seamless intergration with framework (NextJSVite in my case).

More on struggle finding existing solution here

Installation

npm i cssed

Configuration

With Vite

vite.config.js:

import cssedVitePlugin from 'cssed/vite-plugin'

export default {
  plugins: [
    // ...
    cssedVitePlugin()
    // ...
  ]
}

With webpack/next/babel

No configuration required as long as you have enabled module:cssed in your .babelrc:

{
  "plugins": ["module:cssed"]
}

Also, add compilation artifcats to gitignore:

# cssed compilation artifacts
.cssed

Usage

import { css } from 'cssed'
import { dark, light } from './constants'

const styles = css`
  .red {
    color: red;
    background: ${dark};
  }

  .blue {
    color: blue;
    background: ${light};
  }
`

const Box = (props) => (
  <div className={props.isRed ? styles.red : styles.blue}></div>
)

That's it? That's it.

How it works

Babel plugin during compilation will extract content of css function call into a separate .module.css file and will place it in .cssed folder in the root of the project, rebasing URLs in css.

Before:

// index.js – before compilation
import { css } from 'cssed'
const styles = css`
  .red {
    color: red;
  }
`

const Box = (props) => <div className={styles.red}></div>

After compilation with cssed:

// index.js – compiled with cssed
import _a from '../.cssed/[hash].module.css'
const styles = _a

const Box = (props) => <div className={styles.red}></div>

And file [hash].module.css contains extracted css:

/* [hash].module.css */
/* AUTO GENERATED FILE. DO NOT EDIT  */
.red {
  color: red;
}

From here Webpack will handle it as a regular file, which has imported CSS and will process it accordingly to configured pipeline.

Syntax Highlight

Same as for styled-jsx package.

Visual Studio Code Extension

Launch VS Code Quick Open (⌘+P), paste the following command, and press enter.

ext install vscode-styled-jsx

Autocomplete Visual Studio Code Extension

Launch VS Code Quick Open (⌘+P), paste the following command, and press enter.

ext install vscode-styled-jsx-languageserver
<img src="media/autocomplete.png" width="400" align="center" alt="Autocomplete"/>

Exmaples

check examples for:

Prior art

This would not be possible, without linaria. In fact inability to make it work in NextJS pushed me over the line to create cssed 🙃. They did awesome job making evaluators for template literals. So you can write expressions like these:

import { light } from './theme'

const cls = css`
  .some {
    color: ${light};
    font-size: ${22 + 20};
  }
`

Other notable projects:

// this will not generate `cls.red` and `cls.blue` you would expect
const cls = css`
  .red {
    color: red;
  }
  .blue {
    color: blue;
  }
`
const Header = () => {
  // This will not be styled. It's frustrating as hell.
  const moreItems = (
    <>
      <div className={'item'}></div>
      <div className={'item'}></div>
    </>
  )

  return (
    <>
      <div className={'item'}></div>
      {moreItems}
      <style jsx>
        {`
          .item {
            color: red;
          }
        `}
      </style>
    </>
  )
}
import { dark } from '../theme'

// this will throw
const styles = css`
  .red {
    border: 2px solid ${dark};
    padding: 10px;
  }
`

Gimmicks:

CSSed is dead-simple CSS-in-JS implementation, without any gimmicks. Here is one if you need it:* <img src="media/gimmick.svg" width="800" align="center" alt="Can you read it? 🧐"/>

License

MIT