Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

cuttlebelle

Package Overview
Dependencies
Maintainers
1
Versions
78
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

cuttlebelle

The react static site generator that separates editing and code concerns

  • 1.0.0-alpha.8
  • Source
  • npm
  • Socket score

Version published
Weekly downloads
16
decreased by-20%
Maintainers
1
Weekly downloads
 
Created
Source

Cuttlebelle

The react static site generator with editing in mind

NPM

💡 Why yet another static site generator?

All static site generators I have used restrict you to use one layout per page. Todays webdesign needs have outgrown this and we often find ourself either adding code into our content pages (markdown files, liquid templates) or content into our layout pages. That makes updating and maintaining a page hard, especially for a non-technical content author.

I needed a generator that can separate content from code as cleanly as possible while still staying a static site generator.

React comes with the component paradigm and was exactly what I’m looking for. JSX enables a very easy templating like way to write components while still keeping the power of javascript. No more templating languages that only do half of what you need. Use javascript to write your layouts.

Contents


Install

yarn global add cuttlebelle
npm install cuttlebelle -g

⬆ back to top


Usage

CLI

Cuttlebelle cli

I recommend installing Cuttlebelle globally as it exposes the cuttlebelle command to your system.

Once installed you can run it inside the rot of your project:

cd /path/to/my/project
cuttlebelle

This will generate all pages into the site folder (unless specified otherwise).

Watch

Cuttlebelle watch

You can also run our highly optimized watch while adding content or developing your layouts.

cuttlebelle --watch

This command will first build your pages and then watch for changes in any of them. It will dutifully only build the absolute minimum of pages once it detects a change somewhere. It is so eager to only build those pages that it thinks are relevant that it misses sometimes. In cases where you add content from the _sites prop in one of your layouts for instance. I have added a new and somewhat genius trick to catch cases like that.

Introducing the double save TM

If you feel like the watch may have missed a page and you don’t want to leave your editor to complain about it to the watch, just save your file twice quickly like a double click. The watch will detect the double saveTM and generate all pages for you again.

No generator

Sometimes you may only want to start a watch and not rebuild all pages. For that use the no-generate option:

cuttlebelle --watch --no-generate
Help

Cuttlebelle help

Of course there is also a help option. Just run it with the help flag:

cuttlebelle --help

↑ back to Usage

Your content

The default folder structure divides content into the content/ folder and the layout and component react files into the src/ folder.

.
├── content/           # The content folder
│   ├── page1/         # Each folder represents a page and will be converted to `page1/index.html`
│   │                  # 💡 As long as contains an `index.yml` file.
│   │
│   ├── index/         # The index folder is treated as the homepage and converted to `index.html`
│   │
│   └── page2/         # You can nest pages by nesting them in the folder structure
│       │
│       └── subpage1/  # As long as this folder has an `index.yml` file
│                      # it will be converted to `page2/subpage1/index.html`
│
└── src/               # The `src` folder is where your layout lives

( 💡 All folders can be configured in your package.json file via the cuttlebelle customizations.)

Now let’s look into one folder:

.
└── content
    ├── page1
    │   ├── index.yml      # This folder includes an `index.yml` file so it will be converted into a page
    │   ├── partial1.md    # The partials are all in markdown format and can have any name.
    │   └── partial2.md    # They are only converted if they are referenced inside your `index.yml` file
    │
    └── shared             # A folder won’t be generated if it doesn’t have an `index.yml` file
        ├── component1.md  # You can use such folders to share partials between pages
        └── component2.md  # This is just a suggestion. Partials can live anywhere.
Your index.yml

A typical index.yml file could look like this:

layout: layout/page  # The layout defaults to `layout/page` if it’s not set
title: Homepage      # It’s always a good idea to give your page a title
partials:            # `partials` define the sequence of horizontal building blocks of this page
  - /shared/header   # Not this partial starts with a slash `/`
                     # which means it will be found relative to your `src/` folder
  - feature-image    # Partials starting with just letters are found
  - cta              # relative to the folder the `index.yml` is in
  - contact-cards
  - /shared/footer

( 💡 All variables that are defined inside a page are available as props under { _sites }.)

Your partials

And a typical partial.md file could look like this:

---                                   # Each markdown file can hav frontmatter
layout: layout/cards                  # The power of cuttlebelle is each partial has it’s own layout
                                      # The layout defaults to layout/partial if it’s undefined
title: partial4                       # You can add any number of variables
cards:                                # Even arrays
  - id: ID1                           # Or objects
    title: Card1
    content: content for first card
  - id: ID2
    title: Card2
    content: content for second card
---

Content
<!-- The content of the markdown file is exposed as { _body } to the props -->

( 💡 Of course all variables are again available as props to the layout by their own name.)

↑ back to Usage

The layout

The layout are all react components. You have to assign a layout to each page and partial. Each component will have a bunch of props exposed to it.

A page layout

A typical component for a page might look like this:

import React from "react";

export default ( page ) => (
	<html>
	<head>
		<title>{ page.title }</title>
	</head>
	<body>
		<main>
			<h1>{ page.title }</h1>
			<div>{ page._partials }</div>
		</main>
	</body>
	</html>
);

A page will receive the following props:

prop namedescription
_myselfThe ID of the current page
_parentsAn array of all parent pages IDs
_sitesAn object of all pages; with ID as key
_partialsThe generated HTML of all declared partials

Plus all other variables declared inside your index.yml.

A partial layout

A typical component for a partial might look like this:

import React from "react";

export default ( page ) => (
	<article>
		<h2>{ page.title }</h2>
		<div>{ page._body }</div>
	</article>
);

A page will receive the following props:

prop namedescription
_myselfThe ID of the current page
_parentsAn array of all parent pages IDs
_sitesAn object of all pages; with ID as key
_bodyThe body of your markdown file

Plus all other variables declared inside your partial.

( 💡 You can access the page your partial was called in via: page._sites[ page._myself ].)

↑ back to Usage

Customizations

Cuttlebelle can be customized via your own package.json file.

( 💡 You can generate it via npm init if you don’t have package.json.)

See below all configuration with default values:

{
	"name": "your name",
	"version": "1.0.0",
	"description": "Your description",
	"main": "index.js",
	"scripts": {
		"test": "echo \"Error: no test specified\" && exit 1"
	},
+	"cuttlebelle": {
+		"folder": {
+			"content": "/content/",
+			"src": "/src/",
+			"site": "/site/",
+			"index": "index.yml",
+			"homepage": "index"
+		},
+		"layouts": {
+			"page": "layout/page",
+			"partial": "layout/partial"
+		},
+		"site": {
+			"root": "/",
+			"doctype": "<!DOCTYPE html>",
+			"redirectReact": true
+		}
+	},
	"keywords": [],
	"author": "",
	"license": "ISC"
}

A breakdown:

"cuttlebelle": {                  # The cuttlebelle object
  "folder": {                     # The is where we can adjust folder/file names
    "content": "content/",        # Where does your content live?
    "src": "src/",                # Where do your react layouts live?
    "site": "site/",              # Where do you want to generate your static site to?
    "index": "index.yml",         # What is the name of the file we look for to generate pages?
    "homepage": "index"           # What should the index folder be named?
  },
  "layouts": {                    # Your layout settings
    "page": "layout/page",        # What is the default layout for pages?
    "partial": "layout/partial"   # What is the default layout for partials?
  },
  "site": {                       # General settings
    "root": "/",                  # What should cuttlebelle append to links?
    "doctype": "<!DOCTYPE html>", # What doctype string do you want to add?
    "redirectReact": true         # You can disable redirecting `import` calls to the locally installed
                                  # react instance of cuttlebelle rather than your local folder.
  }
},

⬆ back to top


Build

To contribute to this still young project you need to install it’s dependencies and run a watch to transpile th files.

yarn
yarn watch

( 💡 Please look at the coding style and work with it, not against it :smile:.)

⬆ back to top


Tests

TODO

⬆ back to top


Release History

  • v0.1.0 - 💥 Initial version

⬆ back to top


License

Copyright (c) Dominik Wilkowski. Licensed under GNU-GPLv3.

⬆ back to top

};

Keywords

FAQs

Package last updated on 10 Jun 2017

Did you know?

Socket

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Install

Related posts

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc