Setting up Storybook for Gatsby

Storybook is a user interface development environment and playground for UI components. The tool enables developers to create components independently and showcase components interactively in an isolated development environment.
In this blog you will know about how to setup storybook for Gatsby.

To know more about storybook and its use , you can watch the below demo

Install storybook-cli

npm install -g @storybook/cli

Initialize storybook

Initialize storybook in the root of your Gatsby Project

sb init

This command adds a set of boilerplate files for Storybook in your project. You also need to update storybook configuration for Gatsby project.

Then,

npm i @storybook/addon-viewport @storybook/addon-links @storybook/addon-storysource @storybook/addon-actions -D 

// If you are using workspace, then use `yarn workspace gatsby-woocommerce-theme add @storybook/addon-viewport @storybook/addon-links @storybook/addon-storysource @storybook/addon-actions -D ` 

Add configurations in main.js

Now update the .storybook/main.js file with below configurations.

module.exports = {
	stories: ['../src/stories/**/*.stories.js'],
	addons: [
		'@storybook/addon-actions',
		'@storybook/addon-links',
		'@storybook/addon-viewport/register',
		'@storybook/addon-storysource',
	],
};

Adding config.js

Now create a file a called config.js inside of .storybook

import { action } from "@storybook/addon-actions";
import { GlobalStyle } from '../src/shared/global';
import React from 'react';

// Add viewport addon for mobile responsive development.
import { addParameters, configure } from '@storybook/react';
import { INITIAL_VIEWPORTS } from '@storybook/addon-viewport';

global.__BASE_PATH__ = '';

// automatically import all files ending in *.stories.js
configure( [
	require.context( "../src/components", true, /\.stories\.js$/ )
], module );

// Gatsby's Link overrides:
// Gatsby defines a global called ___loader to prevent its method calls from creating console errors you override it here
global.___loader = {
	enqueue: () => {
	},
	hovering: () => {
	}
}

// Gatsby internal mocking to prevent unnecessary errors in storybook testing environment
global.__PATH_PREFIX__ = "";

// This is to utilized to override the window.___navigate method Gatsby defines and uses to report what path a Link would be taking us to if it wasn't inside a storybook
window.___navigate = pathname => {
	action( "NavigateTo:" )( pathname )
}

addParameters( {
	viewport: {
		viewports: INITIAL_VIEWPORTS,
	},
} );

Add Webpack.config.js

  
const path = require( 'path' );

module.exports = ( { config } ) => {
	// Transpile Gatsby module because Gatsby includes un-transpiled ES6 code.
	config.module.rules[ 0 ].exclude = [ /node_modules\/(?!(gatsby)\/)/ ];

	// use installed babel-loader which is v8.0-beta (which is meant to work with @babel/core@7)
	config.module.rules[ 0 ].use[ 0 ].loader = require.resolve( 'babel-loader' );

	// use @babel/preset-react for JSX and env (instead of staged presets)
	config.module.rules[ 0 ].use[ 0 ].options.presets = [
		require.resolve( '@babel/preset-react' ),
		require.resolve( '@babel/preset-env' )
	];

	config.module.rules[ 0 ].use[ 0 ].options.plugins = [
		// use @babel/plugin-proposal-class-properties for class arrow functions
		require.resolve( '@babel/plugin-proposal-class-properties' ),
		// use babel-plugin-remove-graphql-queries to remove static queries from components when rendering in storybook
		require.resolve( 'babel-plugin-remove-graphql-queries' )
	];

	config.module.rules[ 1 ].test = /\.(sa|sc|c)ss$/;
	config.module.rules[ 1 ].use = [
		require.resolve( 'style-loader' ),
		require.resolve( 'css-loader' ),
		require.resolve( 'sass-loader' ),
	];

	// Prefer Gatsby ES6 entrypoint (module) over commonjs (main) entrypoint
	config.resolve.mainFields = [ 'browser', 'module', 'main' ];

	return config;
};

Install babel-preset-react-app

npm install --save-dev babel-preset-react-app

When you setup storybook , It automatically adds the following scripts to your package.json

  "scripts": {
    "storybook": "start-storybook -p 6006",
    "build-storybook": "build-storybook"
  }

Create your first story

Create a directory called stories inside of src/components and add create a new file called example.stories.js. Storybook will automatically pick up all files ending with ...stories.js

// example.stories.js

import React from "react"
export default {
	title: "Dashboard/header",
}
export const exampleStory = () => (
	<div style={{ padding: "16px", backgroundColor: "#eeeeee" }}>
		<h1 style={{ color: "rebeccapurple" }}>Hello from Storybook and Gatsby!</h1>
	</div>
)
npm run storybook

Leave a Reply