Skip to content

dance2die/template.tailwind.nextjs

Repository files navigation

Next.JS + Tailwind CSS

Setting up Tailwind CSS ("Tailwind") in Next.JS 9.3.0 ("Next").

This is based on

  1. the official setup example.
  2. Sung's blog entry, Tailwind for Create-React-App Cheat Sheet

Table of Contents

  1. Assumption
  2. Install DEV dependencies
  3. Create a Tailwind configuration file
  4. Configure PostCSS for Tailwind
  5. Create a Tailwind file
  6. Create NPM Scripts
  7. Import Tailwind CSS Output
  8. (Optional) Normalize body

0. Assumption

I will assume that you have an existing Next site.

1. Install DEV dependencies

# yarn
yarn add -D @fullhuman/postcss-purgecss autoprefixer npm-run-all cross-env cssnano postcss-cli purgecss tailwindcss
# npm
npm install -D @fullhuman/postcss-purgecss autoprefixer npm-run-all cross-env cssnano postcss-cli purgecss tailwindcss

2. Create a Tailwind configuration file

npx tailwind init tailwind.config.js

3. Configure PostCSS for Tailwind

  1. Create a PostCSS configuration file.
# bash
touch postcss.config.js
# Powershell
new-item postcss.config.js
  1. Configure PostCSS

If you have React components in <project root>/components folder, add "./components/**/*.js" to contents: [...].

⚠ Note: Next disallows require in PostCSS configuration file.
So unlike the create-react-app version, you need to use a subset of configuration option using an object syntax.

const purgecss = {
  '@fullhuman/postcss-purgecss': {
    // Use this if you have `./components` folder
    // content: ["./components/**/*.js", "./pages/**/*.js"],
    content: ['./pages/**/*.js'],
    defaultExtractor: content => content.match(/[\w-/:]+(?<!:)/g) || []
  }
}

module.exports = {
  plugins: {
    tailwindcss: {},
    autoprefixer: {},
    // Purge and minify CSS only production builds only
    ...(process.env.NODE_ENV === 'production'
      ? { ...purgecss, cssnano: {} }
      : {})
  }
}

4. Create a Tailwind file

Create a file ./src/styles/tailwind.css.

# bash
mkdir -p ./src/styles/ && touch ./src/styles/tailwind.css
# Powershell
new-item ./src/styles/tailwind.css -ItemType File -Force

and add following Tailwind utilities.

@tailwind base;
@tailwind components;
@tailwind utilities;

5. Create NPM Scripts

Update the `package.json` script to create Tailwind CSS file before starting/building.

"scripts": {
  "build:css": "postcss src/styles/tailwind.css -o src/styles/index.css",
  "watch:css": "postcss src/styles/tailwind.css -o src/styles/index.css --watch",
  "env:dev": "cross-env NODE_ENV=development",
  "env:prod": "cross-env NODE_ENV=production",
  "next:dev": "sleep 5 && next dev",
  "next:build": "next build",
  "dev": "run-p env:dev watch:css next:dev",
  "build": "run-s env:prod build:css next:build",
  "start": "next start"
},

6. Import Tailwind CSS Output

If you already don't have a Custom App, create it (./pages/_app.js).

Import the Tailwind generated CSS file.

import React from 'react'
// This is the Tailwind generated CSS file
import '../src/styles/index.css'

export default function App({ Component, pageProps }) {
  return <Component {...pageProps} />
}

7. (Optional) Normalize body

I couldn't figure out how but for some reason, Tailwind's normalize in @tailwind base isn't applied thus applying margin (8px) around the site.

You can add normalize CSS as a global style in the custom App file.
The updated App file would look like the following.

import React from 'react'
import '../src/styles/index.css'

export default function App({ Component, pageProps }) {
  return (
    <>
      <Component {...pageProps} />
      {/* 
      Tailwind's normalize isn't applied
      thus 8px margin is added around "body". 
      Fix it with a global style.
      https://github.com/zeit/next.js/issues/151#issuecomment-257090939 */}
      <style jsx global>{`
        body {
          margin: 0;
          padding: 0;
          box-sizing: border-box;
        }
      `}</style>
    </>
  )
}

Releases

No releases published

Packages

No packages published