1
0
mirror of https://github.com/venthur/blag.git synced 2025-11-25 20:52:43 +00:00

Merge branch 'master' into split_archive

This commit is contained in:
Bastian Venthur
2023-06-13 16:37:52 +02:00
7 changed files with 102 additions and 37 deletions

View File

@@ -2,10 +2,22 @@
## [unreleased] ## [unreleased]
* **Breaking Change**: Split former archive page which served as index.html ### Breaking
into "index" and "archive", each with their own template, respectively. Index
is the landing page and shows by default only the latest 10 articles. Archive * blag does not use default fallback templates anymore and will return an error
shows the full list of articles. if it is unable to find required templates, e.g. in `templates/`.
Users upgrading from older versions can either run `blag quickstart` (don't
forget to backup your `config.ini` or copy the templates from blag's
resources (the resource path is shown in the error message).
New users are not affected as `blag quickstart` will generate the needed
templates.
* Split former archive page which served as index.html into "index" and
"archive", each with their own template, respectively. Index is the landing
page and shows by default only the latest 10 articles. Archive shows the full
list of articles.
If you used custom templates, If you used custom templates,
* you should create an "index.html"-template (take blag's default one as a * you should create an "index.html"-template (take blag's default one as a
@@ -13,6 +25,7 @@
* you may want to include the new "/archive.html" link somewhere in your * you may want to include the new "/archive.html" link somewhere in your
navigation navigation
## [1.5.0] - 2023-04-16 ## [1.5.0] - 2023-04-16
* moved to pyproject.toml * moved to pyproject.toml

View File

@@ -16,13 +16,13 @@ import sys
from jinja2 import ( from jinja2 import (
Environment, Environment,
ChoiceLoader,
FileSystemLoader, FileSystemLoader,
PackageLoader,
Template, Template,
TemplateNotFound,
) )
import feedgenerator import feedgenerator
import blag
from blag.markdown import markdown_factory, convert_markdown from blag.markdown import markdown_factory, convert_markdown
from blag.devserver import serve from blag.devserver import serve
from blag.version import __VERSION__ from blag.version import __VERSION__
@@ -185,15 +185,14 @@ def get_config(configfile: str) -> configparser.SectionProxy:
def environment_factory( def environment_factory(
template_dir: str | None = None, template_dir: str,
globals_: dict[str, object] | None = None, globals_: dict[str, object] | None = None,
) -> Environment: ) -> Environment:
"""Environment factory. """Environment factory.
Creates a Jinja2 Environment with the default templates and Creates a Jinja2 Environment with the templates from `template_dir` loaded.
additional templates from `template_dir` loaded. If `globals` are If `globals` are provided, they are attached to the environment and thus
provided, they are attached to the environment and thus available to available to all contexts.
all contexts.
Parameters Parameters
---------- ----------
@@ -206,13 +205,7 @@ def environment_factory(
jinja2.Environment jinja2.Environment
""" """
# first we try the custom templates, and fall back the ones provided env = Environment(loader=FileSystemLoader(template_dir))
# by blag
loaders: list[FileSystemLoader | PackageLoader] = []
if template_dir:
loaders.append(FileSystemLoader([template_dir]))
loaders.append(PackageLoader('blag', 'templates'))
env = Environment(loader=ChoiceLoader(loaders))
if globals_: if globals_:
env.globals = globals_ env.globals = globals_
return env return env
@@ -261,12 +254,22 @@ def build(args: argparse.Namespace) -> None:
env = environment_factory(args.template_dir, dict(site=config)) env = environment_factory(args.template_dir, dict(site=config))
try:
page_template = env.get_template('page.html') page_template = env.get_template('page.html')
article_template = env.get_template('article.html') article_template = env.get_template('article.html')
index_template = env.get_template('index.html') index_template = env.get_template('index.html')
archive_template = env.get_template('archive.html') archive_template = env.get_template('archive.html')
tags_template = env.get_template('tags.html') tags_template = env.get_template('tags.html')
tag_template = env.get_template('tag.html') tag_template = env.get_template('tag.html')
except TemplateNotFound as exc:
tmpl = os.path.join(blag.__path__[0], 'templates')
logger.error(
f'Template "{exc.name}" not found in {args.template_dir}! '
'Consider running `blag quickstart` or copying the '
f'missing template from {tmpl}.'
)
sys.exit(1)
articles, pages = process_markdown( articles, pages = process_markdown(
convertibles, convertibles,

View File

@@ -6,6 +6,10 @@
from __future__ import annotations from __future__ import annotations
import configparser import configparser
import argparse import argparse
import shutil
import os
import blag
def get_input(question: str, default: str) -> str: def get_input(question: str, default: str) -> str:
@@ -33,6 +37,22 @@ def get_input(question: str, default: str) -> str:
return reply return reply
def copy_templates() -> None:
"""Copy templates into current directory.
It will not overwrite existing files.
"""
print("Copying templates...")
try:
shutil.copytree(
os.path.join(blag.__path__[0], 'templates'),
'templates',
)
except FileExistsError:
print("Templates already exist. Skipping.")
def quickstart(args: argparse.Namespace | None) -> None: def quickstart(args: argparse.Namespace | None) -> None:
"""Quickstart. """Quickstart.
@@ -71,3 +91,5 @@ def quickstart(args: argparse.Namespace | None) -> None:
} }
with open('config.ini', 'w') as fh: with open('config.ini', 'w') as fh:
config.write(fh) config.write(fh)
copy_templates()

View File

@@ -13,7 +13,7 @@ Install blag from PyPI_
.. _pypi: https://pypi.org/project/blag/ .. _pypi: https://pypi.org/project/blag/
Run blag's quickstart command to create the configuration needed Run blag's quickstart command to create the configuration and templates needed
.. code-block:: sh .. code-block:: sh
@@ -40,8 +40,8 @@ If you want more separation between the static files and the markdown content,
you can put all static files into the ``static`` directory. Blag will copy you can put all static files into the ``static`` directory. Blag will copy
them over to the ``build`` directory. them over to the ``build`` directory.
If you want to customize the looks of the generated site, create a If you want to customize the look of the generated site, visit the ``template``
``template`` directory and put your jinja2 templates here. directory. It contains jinja2 templates and can be modified as needed.
Those directories can be changed via command line arguments. See Those directories can be changed via command line arguments. See
@@ -186,9 +186,7 @@ becomes
Templating Templating
---------- ----------
Custom templates are **optional** and stored by default in the ``templates`` Templates are stored by default in the ``templates`` directory.
directory. blag will search the ``templates`` directory first, and fall back
to blag's default built-in templates.
============ ====================================== =================== ============ ====================================== ===================
Template Used For Variables Template Used For Variables

View File

@@ -8,18 +8,18 @@ import os
import pytest import pytest
from jinja2 import Environment, Template from jinja2 import Environment, Template
from blag import blag from blag import blag, quickstart
@pytest.fixture @pytest.fixture
def environment() -> Iterator[Environment]: def environment(cleandir: str) -> Iterator[Environment]:
site = { site = {
'base_url': 'site base_url', 'base_url': 'site base_url',
'title': 'site title', 'title': 'site title',
'description': 'site description', 'description': 'site description',
'author': 'site author', 'author': 'site author',
} }
env = blag.environment_factory(globals_=dict(site=site)) env = blag.environment_factory('templates', globals_=dict(site=site))
yield env yield env
@@ -55,7 +55,7 @@ def tag_template(environment: Environment) -> Iterator[Template]:
@pytest.fixture @pytest.fixture
def cleandir() -> Iterator[str]: def cleandir() -> Iterator[str]:
"""Create a temporary workind directory and cwd.""" """Create a temporary working directory and cwd."""
config = """ config = """
[main] [main]
base_url = https://example.com/ base_url = https://example.com/
@@ -65,13 +65,14 @@ author = a. u. thor
""" """
with TemporaryDirectory() as dir: with TemporaryDirectory() as dir:
for d in 'content', 'build', 'static', 'templates': for d in 'content', 'build', 'static':
os.mkdir(f'{dir}/{d}') os.mkdir(f'{dir}/{d}')
with open(f'{dir}/config.ini', 'w') as fh: with open(f'{dir}/config.ini', 'w') as fh:
fh.write(config) fh.write(config)
# change directory # change directory
old_cwd = os.getcwd() old_cwd = os.getcwd()
os.chdir(dir) os.chdir(dir)
quickstart.copy_templates()
yield dir yield dir
# and change back afterwards # and change back afterwards
os.chdir(old_cwd) os.chdir(old_cwd)

View File

@@ -179,9 +179,9 @@ author = a. u. thor
assert config_parsed['base_url'] == 'https://example.com/' assert config_parsed['base_url'] == 'https://example.com/'
def test_environment_factory() -> None: def test_environment_factory(cleandir: str) -> None:
globals_: dict[str, object] = {'foo': 'bar', 'test': 'me'} globals_: dict[str, object] = {'foo': 'bar', 'test': 'me'}
env = blag.environment_factory(globals_=globals_) env = blag.environment_factory("templates", globals_=globals_)
assert env.globals['foo'] == 'bar' assert env.globals['foo'] == 'bar'
assert env.globals['test'] == 'me' assert env.globals['test'] == 'me'
@@ -301,6 +301,23 @@ foo bar
assert os.path.exists(f'{args.output_dir}/tags/bar.html') assert os.path.exists(f'{args.output_dir}/tags/bar.html')
@pytest.mark.parametrize(
'template',
[
'page.html',
'article.html',
'index.html',
'archive.html',
'tags.html',
'tag.html',
]
)
def test_missing_template_raises(template: str, args: Namespace) -> None:
os.remove(f'templates/{template}')
with pytest.raises(SystemExit):
blag.build(args)
def test_main(cleandir: str) -> None: def test_main(cleandir: str) -> None:
blag.main(['build']) blag.main(['build'])

View File

@@ -1,5 +1,6 @@
# remove when we don't support py38 anymore # remove when we don't support py38 anymore
from __future__ import annotations from __future__ import annotations
import os
from pytest import MonkeyPatch from pytest import MonkeyPatch
@@ -27,3 +28,13 @@ def test_quickstart(cleandir: str, monkeypatch: MonkeyPatch) -> None:
assert 'title = foo' in data assert 'title = foo' in data
assert 'description = foo' in data assert 'description = foo' in data
assert 'author = foo' in data assert 'author = foo' in data
for template in (
"archive.html",
"article.html",
"base.html",
"page.html",
"tag.html",
"tags.html",
):
assert os.path.exists(f'templates/{template}')