-
Notifications
You must be signed in to change notification settings - Fork 2
Home
Carcade — генератор статических сайтов, написанный на Питоне.
В качестве шаблонизатора используется Jinja2 (с интегрированными webassets и i18n); данные страниц (далее — контекст страницы) задаются с помощью Markdown и YAML.
В отличии от большинства аналогичных библиотек, так или иначе ориентированных на создание блогов, Carcade предоставляет гибкий (хоть и несколько «низкоуровневый») интерфейс, позволяющий создавать сайты со сложной структурой.
Статический сайт можно рассматривать как дерево. Основная идея Carcade заключается в том, чтобы в шаблонах предоставить возможность доступа к дереву, содержащему контексты всех страниц сайта. Например, для того, чтобы отобразить главное меню на любой странице сайта, достаточно иметь список контекстов страниц первого уровня; для того, чтобы образить страницу /blog/
со ссылками на запиcи блога (/blog/<id>/
), достаточно иметь список контекстов «детей» страницы /blog/
, и так далее.
Каталог с Carcade-сайтом должен содержать:
- Каталог
layouts
, содержащий Jinja2-шаблоны; - Каталог
pages
, содержащий каталоги (возможно, вложенные) с данными страниц — Markdown- и YAML-файлами; - Каталог
static
; - Файл
carcade_settings.py
с настройками.
carcade init
carcade build
carcade runserver
Дерево сайта это упорядоченное дерево, узлы которого проименованы и, за исключением корня, соответствуют страницам сайта.
Каждый узел дерева имеет ключ. Ключ это строка, которая отражает путь от корня до данного узла. Например:
. Ключ:
├── about about
└── blog blog
├── 1 blog/1
│ └── example blog/1/example
└── 2 blog/2
-
Carcade создаёт дерево сайта, в точности отражающее структуру директории
pages
. Каждый узел получает имя, совпадающее с названием его директории, а также контекст — словарь с данными, полученными из файлов этой директории.
Вначале обрабатываются Markdown-файлы (<name>.md
), и результат обработки записывается в контекст под ключом<name>
. Далее обрабатываются YAML-файлы (<name>.yaml
), содержащие словари, и данные из них записываются поверх данных, полученных из Markdown-файлов. -
Если задан порядок узлов, дерево сортируется. Если заданы настройки пагинации, в дерево вставляются специальные узлы, соответствующие страницам.
-
Содержимое директории
static
копируется в целевую директорию. Для каждой страницы в дереве:- определяется её root-relative URL;
- определяется шаблон, с помощью которого она должна быть отображена;
- шаблон рендерится в контексте страницы и результат сохраняется в целевой директории в
<root-relative-URL>/index.html
.
Контекст шаблона всегда содержит следующие переменные:
-
NAME
: имя страницы; -
PATH
: ключ страницы в дереве сайта; -
LANGUAGE
: язык страницы; -
CHILDREN
: список контекстов детей; -
PARENT
: контекст родителя; -
SIBLINGS
: список контекстов узлов-«братьев» (узлов, имеющих того же родителя). Включает также и текущий контекст; -
PREV_SIBLING
: контекст предыдущего «брата»; -
NEXT_SIBLING
: контекст следующего «брата»; -
ROOT
: контекст корня дерева. Корень дерева не соответствует никакой странице сайта, и потому единственное непустое поле в его контексте —CHILDREN
.
Также в шаблоне доступна функция url_for(path)
, которая принимает ключ страницы и возвращает её root-relative URL.
###Пример: Положим, исходная директория выглядит следующим образом:
.
├── layouts
│ ├── _base.html
│ └── page.html
├── pages
│ ├── four
│ │ └── content.md
│ ├── one
│ │ ├── a
│ │ │ └── content.md
│ │ ├── b
│ │ │ └── content.md
│ │ ├── c
│ │ │ └── content.md
│ │ ├── d
│ │ │ └── content.md
│ │ ├── e
│ │ │ └── content.md
│ │ ├── f
│ │ │ └── content.md
│ │ ├── g
│ │ │ └── content.md
│ │ └── content.md
│ ├── three
│ │ └── content.md
│ └── two
│ └── content.md
├── static
│ ├── css
│ │ └── reset.css
│ ├── img
│ │ └── logo.png
│ └── favicon.ico
├── translations
└── carcade_settings.py
Содержимое carcade_settings.py
:
from collections import defaultdict
from webassets import Bundle
DEFAULT_PAGE = 'one'
LAYOUTS = defaultdict(lambda: 'page.html', {})
BUNDLES = {
'css': Bundle('./css/reset.css', output='./gen/styles.css'),
}
ORDERING = {
'*': ['one', 'two', 'three', 'four'],
'one/*': 'alphabetically',
}
PAGINATION = {
'one/*': 3,
}
PAGE_NAME = 'page%i'
####Шаг 1
Дерево читается из директории pages
:
####Шаг 2
После чего оно сортируется:
И подвергается пагинации:
####Шаг 3
Результат выглядит так:
www
├── css
│ └── reset.css
├── four
│ └── index.html
├── img
│ └── logo.png
├── one
│ ├── a
│ │ └── index.html
│ ├── b
│ │ └── index.html
│ ├── c
│ │ └── index.html
│ ├── d
│ │ └── index.html
│ ├── e
│ │ └── index.html
│ ├── f
│ │ └── index.html
│ ├── g
│ │ └── index.html
│ ├── page2
│ │ └── index.html
│ ├── page3
│ │ └── index.html
│ └── index.html
├── three
│ └── index.html
├── two
│ └── index.html
├── favicon.ico
└── index.html
Работающие примеры можно увидеть здесь: https://github.com/aromanovich/carcade-examples
TODO