Skip to content

PebbleRoad/cobblestone

Repository files navigation

Cobblestone logo

Cobblestone

Modern static site generator

Build Status

Getting started · Package scripts · Project structure · Recipes · FAQ


What is Cobblestone?

Cobblestone is a collection of files, folders and configuration which developers can use as a starting point to create highly performant, well-tested and maintainable static websites with ease.

What's included?

  • 📦 Webpack for dev server and production build
  • 🖼 Vue.js for routing, views, and components
  • ⚡️ Prerenderer for static-site generation from a SPA
  • 🎨 Sass, Scarab, PostCSS for styling
  • 😴 lazysizes for lazy-loaded, responsive images
  • 🤖 Babel, ES6+ for writing JavaScript
  • 📖 Storybook for UI component development environment
  • ✅ Jest + Cypress for automated testing
  • ✋🏼 BackstopJS for visual regression testing
  • 🕶 cypress-axe for A11y validation
  • ⏱ Lighthouse and sitespeed.io for performance audits
  • 💄 Prettier for opinionated code formatting
  • 🥁 Battlecry for scaffolding files
  • 📂 Opinionated folder structure for separation of concerns
  • 👻 Bring-your-own headless CMS

Getting started

Clone this repository and use it as a boilerplate:

$ git clone git@github.com:PebbleRoad/cobblestone.git my-project

Make sure you have these installed:

To start developing:

$ cd my-project
$ yarn
$ yarn dev # start the development server

Package scripts

These scripts can be executed by running yarn SCRIPT_NAME:

Script name Description Notes
Development
dev Start the app development server localhost:3000/
component <name> Scaffold a new Vue component Always use PascalCased component names
fetch Fetch data from the CMS and write to src/data/ You'll need to customize lib/scripts/fetch-from-cms.js
build Build the app for production Generated in dist/
serve Serve the production build locally localhost:3333/
lighthouse Run Google Lighthouse performance tests You must first serve the production build at http://localhost:3333
sitespeed Run sitespeed.io performance tests You must first serve the production build at http://localhost:3333
analyze Run and display an analysis of the Webpack app bundle size localhost:8888/
Storybook
storybook Start the Storybook development server and open Vue devtools localhost:4000/
storybook:ci Start the Storybook development server with the --ci flag localhost:4000/
storybook:build Generate and export a static build of Generated in .storybook/dist/
storybook:serve Serve the .storybook/dist/ folder locally localhost:4444/
Testing
test Run all Jest, Cypress and Backstop tests
├─ test:jest Run all Jest tests
├─ test:cypress Ensure the dev server is running, then run all Cypress tests
└─ test:backstop Run all Backstop tests
Cypress
cypress:open Open the Cypress dashboard
cypress:app Run Cypress e2e tests
cypress:app Run Cypress component tests
BackstopJS
backstop:run Run Backstop tests (using Docker)
backstop:report Open the Backstop report GUI
backstop:approve Approve the current Backstop snapshots

Project structure

✨ src/

Project source files

The src/ folder contains the project source files. These files are processed by Webpack's dev server or build system (depending on the current NODE_ENV). Only the production build contains optimized assets.

View src/ folder structure
File / Folder Description
📁 src/ Project source files
📁 ├── app/ App files
📄 │ ├── App.vue Root App component
📄 │ ├── index.js Application entry point
📄 │ ├── plugins.js Vue plugin configuration
📄 │ └── router.js Vue router configuration
📁 ├── components/ Vue components
📁 ├── assets/ Static asset files
📄 │ ├── favicon.png Site favicon file
📁 │ ├── fonts/ Webfont files
📁 │ └── images/ Image files
📁 ├── data/ JSON data files
📁 ├── html/ HTML templates for html-webpack-plugin
📁 ├── public/ Static public assets
📄 │ └── index.html Main index.html file for SPA
📁 ├── scripts/ Global scripts
📁 ├── styles/ Sass stylesheets
📁 ‌‌│ ├── config/ Stylesheet configuration
📁 ‌‌│ ├── tokens/ Design token configuration
📁 ‌‌│ ├── typography/ Global typography styles
📄 ‌‌│ ├── base.scss Global base styles
📄 ‌‌│ ├── carapace.scss Carapace entry point
📄 ‌‌│ ├── reset.scss CSS reset/normalize styles
📄 ‌‌│ └── style.scss Main stylesheet entry point
📁 └── views/ App views

🎁 dist/

Optimized production build

The production build is generated in the dist/ folder by the Webpack build system.

List of optimizations

  • Compresses images with a focus on performance
  • Minifies scripts, styles, and other static assets
  • Provides code splitting with Webpack dynamic imports
  • Includes an offline Service Worker, so the app works offline
  • Generates favicons and a PWA-compatible manifest.json file
  • Polyfills JavaScript and CSS for browser support down to IE10

☑️ tests/

Test configuration

The tests/ folder contains configuration and supporting files for Jest, Cypress and Backstop.


⚙️ webpack/

Webpack configuration

The webpack/ folder contains configuration files for Webpack. Configuration is split across different targets (build, production and analyze), with a base configuration file that is merged via webpack-merge.

Default Webpack entry points

Name Path Description
babelPolyfill node_modules/@babel/polyfill For ES2015+ support in IE10+
customEventPolyfill node_modules/custom-event-polyfill Polyfill for window.CustomEvent
lazysizes node_modules/lazysizes Library for lazy-loaded, responsive images
carapace src/styles/carapace.scss CSS utility classes
app src/app/index.js Application source code
scripts src/scripts/index.js Entry point for global scripts
(has to be loaded after lazysizes)

Webpack resolve aliases

These Webpack resolve aliases are registered by default, so you can go easy on dot-dot-slashes.

Alias Path
~App src/app
~Views src/views
~Components src/components
~Styles src/styles
~Scripts src/scripts
~Data src/data
~Assets src/assets

📖 .storybook/

Storybook configuration

The storybook/ folder contains files for Storybook configuration.


💼 lib/

Internal project utilities

The lib/ folder is meant for customized internal scripts and utilities that may be used on a per-project basis. (e.g. a project may require a custom parser for a specific data schema)

Recipes

Managing design tokens

Design tokens are defined in src/styles/tokens/.

Cobblestone's Webpack configuration makes it possible to use Scarab's design tokens and helper functions anywhere in the src/styles/ folder and also in Vue SFC files.


Creating new components

To create a new component run:

$ yarn component ComponentName

This will create the following files:

Description Path
Component README src/components/ComponentName/ComponentName.md
Storybook stories src/components/ComponentName/ComponentName.stories.js
Vue SFC file src/components/ComponentName/ComponentName.vue
Jest component tests src/components/ComponentName/ComponentName.test.js
Cypress component tests tests/cypress/integration/components/ComponentName.spec.js

Creating router views

Views are defined as Vue components in the src/views/ folder.


Configuring app routes

We use vue-router for routing. The router is configured in src/app/router.js. This file maps routes (i.e. URLs) to router views.

Visit the Vue router documentation for more information on configuring vue-router.


Writing component stories

Component stories serve as content for Storybook. They live in the same folder as the component's Vue file.

  • Stories are located in the src/components/ComponentName/ folder

Refer to the Storybook documentation for how to write stories.


Writing and running tests

Component unit and integration tests

Component unit and integration tests can be run by either Cypress or Jest.

  • With Cypress:
    tests/cypress/integration/components/ComponentName/ComponentName.spec.js

  • With Jest:
    src/components/ComponentName/ComponentName.spec.js

App integration and E2E tests

We use Cypress for app integration and E2E tests.

  • Cypress test specs are located in the tests/cypress/integration/app/ folder

Accessibility validation

We use cypress-axe for a11y validation. Use the provided cy.injectAxe() and cy.checkA11y() Cypress commands to test accessibility within components or at the application level.

Visual regression testing

We use BackstopJS for visual regression testing.

  • Backstop test scenarios are defined in tests/backstop/scenarios.js
  • Backstop configuration is defined in ./backstop.config.js

Performance audits

Performance audits are run with Lighthouse and sitespeed.io, and need to be run on the production build.

  1. Run yarn build to generate the production build
  2. Run yarn serve to serve the production build locally
  3. Run yarn lighthouse to run and view a Lighthouse performance report
  4. Run yarn sitespeed to run and serve a sitespeed.io performance report at http://localhost:5000

Configuring Webpack

Webpack configuration is located in the webpack/ folder. Cobblestone uses a merge strategy to handle Webpack configuration. The following configuration files are present by default:

  • base.config.js — Base Webpack configuration
  • dev.config.js — Configuration for development server
  • prod.config.js — Configuration for production build
  • analyze.config.js — Configuration for webpack-bundle-analyzer

FAQ

  • Why can't I use my browser's Vue devtools extension in Storybook?
    This is a known issue. As a workaround, Cobblestone uses the @vue/devtools package, a standalone Electron version of the Vue devtools. Running $ yarn storybook will automatically launch the Vue devtools window. To relaunch the devtools window, run $ yarn run vue-devtools.