denis-sokolov/portent

View on GitHub
README.md

Summary

Maintainability
Test Coverage
# ![portent: perfect websites](media/logo.png)

[![Build Status](https://travis-ci.org/denis-sokolov/portent.svg?branch=master)](https://travis-ci.org/denis-sokolov/portent)
[![Dependency Status](https://gemnasium.com/denis-sokolov/portent.svg)](https://gemnasium.com/denis-sokolov/portent)
[![Codacy Badge](https://api.codacy.com/project/badge/5386b47284f34b5f85cfca06976f4cdc)](https://www.codacy.com/app/denis-sokolov/portent)
[![Code Climate](https://codeclimate.com/github/denis-sokolov/portent/badges/gpa.svg)](https://codeclimate.com/github/denis-sokolov/portent)
[![bitHound Score](https://app.bithound.io/denis-sokolov/portent/badges/score.svg)](http://app.bithound.io/denis-sokolov/portent)

Simple best-practices static website generator.

## Quick start
Run `npm install --save portent`, then add two scripts to your `package.json`:

```json
"scripts": {
    "start": "portent run .",
    "build": "portent build .",
    "deploy": "portent deploy . my-ssh-server:path/to/destination"
}
```

Then create a `pages` directory, maybe a few more files as described below, run `npm start` and start editing and using your website.

## File hierarchy convention
The website project directory should look as follows:

```
/css
  header.css
  typography.less
    whatever.ie9.css
/errors
  404.html
/img
  favicon.png
  p1.jpg
  logo.png
/js
  /_stuff
  fluidImages.js
  base.js
/pages
  index.html
  about.html
  _fragment.html
/static
  other-public-files.txt
htaccess
robots.txt
```

Anywhere in the tree files and directories prefixed with an `_` are ignored.

The structure above will produce a website that responds to URLs `/` and `/about`.

### Page structure
`pages` directory contains actual routes for pages in the website. Every `html` file inside is a single URL route. Pages with Unicode names do not work perfectly, but if they work for you, great.

It is recommended to include a <base> tag in every template and refer to files and URLs relative to the root of the project, without using a leading slash. For example, to link from `projects/foo` to `about`, use a string `about`, not `../about`. A workflow different from this has undefined behavior.

If `pages` contains a file `transform.js`, it will be used to modify HTML programatically:

```js
module.exports = function(path, $){
  $.root().append('Hello, world');
}
```

### Errors
`errors` directory contains templates for HTTP errors.

### CSS
All CSS are combined and included in your HTML.

To refer to images, use `url('foo.png')` syntax, where the images are located in the same directory as your CSS file, or deeper with `url('foo/bar.png')`.

If a file ends in `.less`, it will be processed with LESS. Take care to ensure your submodules are hidden behind an `_` name, or else they will be included twice.

If a file ends in `.ie9.css` or `ie9.less` (or ie 8), the files will be conditionally connected only in Internet Explorer.

#### Portent-base
Portent includes a base stylesheet that promotes some best practices. Import it using `@import 'portent/base.less'`.

### JS
All JavaScript files are combined and included in your HTML.

If a file ends in `.min.js`, it will not be processed, but included as is in a separate bundle and will run before your regular scripts.

If a file ends in `.cjs.js`, it will be Browserified. Take care to ensure your submodules are hidden behind an `_` name, or else they will be included twice.

### HTML
HTML files are processed using [nunjucks](https://github.com/mozilla/nunjucks) templating syntax (version 2) that is primarily useful for its [`extends` tag](https://mozilla.github.io/nunjucks/templating.html#extends).

#### Portent-base
Portent includes a base template for HTML websites that promotes best practices in HTML authoring. Use it by extending in your templates with `{% extends "portent/base.html" %}`, and then defining blocks and variables as follows:

```
{% extends "portent/base.html" %}

{% block title %}
    Document title
{% endblock %}

{% block head %}
    <meta name=description content="">
    <link rel=stylesheet href="http://fonts.googleapis.com/...">
{% endblock %}

{% block body %}
    <header>Website-generic content</header>
    <div>
        Include new custom blocks for further extending:
        {% block content %}{% endblock %}
    </div>
{% endblock %}
```

If your website is non-English, make sure to set the language with a `{% set lang='XX' %}` anywhere in the template.

Set a theme color for your website to use whenever it is possible to customize browser chrome with `{% set themeColor='blue' %}`. Any CSS color or syntax works.

### Images
Images in `img` will become part of your website.

If a file `favicon.png` is present in the root of your images directory, it will be added to your website as a proper favicon, resized and included in HTML. It is recommended to have the base favicon in at least the 196x196 size.

### Static
Everything in `static` will become part of your website. Use this to host fonts, videos, other resources of the sort.

## Usage

### Development server
To develop your website, run a development server in the terminal: `portent run .` or in Node: `portent(directory).server.listen(port)`.

### Building for production
To build the website for production, use `portent build .`, or in Node `portent(directory).build(destination, { onWarning: console.log.bind(console) })`.

### Deploying
To deploy the website, portent exposes a nicer way to use rsync on your machine. Run `portent deploy . ssh-server:path/on/remote/`.