diff --git a/homepage/pelicanconf.py b/homepage/pelicanconf.py index e4f96e3..7cb12fe 100644 --- a/homepage/pelicanconf.py +++ b/homepage/pelicanconf.py @@ -45,7 +45,9 @@ PAGE_SAVE_AS = '{slug}/index.html' ARTICLE_SAVE_AS = 'blog/{slug}/index.html' PLUGIN_PATHS = ['./plugins'] -PLUGINS = ['decorate_content', 'assets'] +PLUGINS = ['decorate_content', 'assets', 'summary'] + +SUMMARY_USE_FIRST_PARAGRAPH = True MARKDOWN = { 'extension_configs': { diff --git a/homepage/plugins/summary/NOTICE b/homepage/plugins/summary/NOTICE new file mode 100644 index 0000000..a7412d2 --- /dev/null +++ b/homepage/plugins/summary/NOTICE @@ -0,0 +1,15 @@ +Pelican Summary Plugin +Copyright The Pelican Authors + +This program is free software: you can redistribute it and/or modify +it under the terms of the GNU Affero General Public License as published by +the Free Software Foundation, either version 3 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU Affero General Public License for more details. + +You should have received a copy of the GNU Affero General Public License +along with this program. If not, see . diff --git a/homepage/plugins/summary/__init__.py b/homepage/plugins/summary/__init__.py new file mode 100644 index 0000000..afe9311 --- /dev/null +++ b/homepage/plugins/summary/__init__.py @@ -0,0 +1 @@ +from .summary import * diff --git a/homepage/plugins/summary/summary.py b/homepage/plugins/summary/summary.py new file mode 100644 index 0000000..26f1d37 --- /dev/null +++ b/homepage/plugins/summary/summary.py @@ -0,0 +1,111 @@ +""" +Summary +------- + +This plugin allows easy, variable length summaries directly embedded into the +body of your articles. +""" + +from __future__ import unicode_literals +from bs4 import BeautifulSoup +from pelican import signals +from pelican.generators import ArticlesGenerator, StaticGenerator, PagesGenerator +import re + +def initialized(pelican): + from pelican.settings import DEFAULT_CONFIG + DEFAULT_CONFIG.setdefault('SUMMARY_BEGIN_MARKER', + '') + DEFAULT_CONFIG.setdefault('SUMMARY_END_MARKER', + '') + DEFAULT_CONFIG.setdefault('SUMMARY_USE_FIRST_PARAGRAPH', False) + if pelican: + pelican.settings.setdefault('SUMMARY_BEGIN_MARKER', + '') + pelican.settings.setdefault('SUMMARY_END_MARKER', + '') + pelican.settings.setdefault('SUMMARY_USE_FIRST_PARAGRAPH', False) + +def extract_summary(instance): + # if summary is already specified, use it + # if there is no content, there's nothing to do + if hasattr(instance, '_summary') or 'summary' in instance.metadata: + instance.has_summary = True + return + + if not instance._content: + instance.has_summary = False + return + + begin_marker = instance.settings['SUMMARY_BEGIN_MARKER'] + end_marker = instance.settings['SUMMARY_END_MARKER'] + use_first_paragraph = instance.settings['SUMMARY_USE_FIRST_PARAGRAPH'] + remove_markers = True + + content = instance._update_content(instance._content, instance.settings['SITEURL']) + begin_summary = -1 + end_summary = -1 + if begin_marker: + begin_summary = content.find(begin_marker) + if end_marker: + end_summary = content.find(end_marker) + + if begin_summary == -1 and end_summary == -1 and use_first_paragraph: + begin_marker, end_marker = '

', '

' + remove_markers = False + begin_summary = content.find(begin_marker) + end_summary = content.find(end_marker) + + if begin_summary == -1 and end_summary == -1: + instance.has_summary = False + return + + # skip over the begin marker, if present + if begin_summary == -1: + begin_summary = 0 + else: + begin_summary = begin_summary + len(begin_marker) + + if end_summary == -1: + end_summary = None + + summary = content[begin_summary:end_summary] + + if remove_markers: + # remove the markers from the content + if begin_summary: + content = content.replace(begin_marker, '', 1) + if end_summary: + content = content.replace(end_marker, '', 1) + + summary = str(BeautifulSoup(summary, 'html.parser')) + + instance._content = content + # default_status was added to Pelican Content objects after 3.7.1. + # Its use here is strictly to decide on how to set the summary. + # There's probably a better way to do this but I couldn't find it. + if hasattr(instance, 'default_status'): + instance.metadata['summary'] = summary + else: + instance._summary = summary + instance.has_summary = True + + +def run_plugin(generators): + for generator in generators: + if isinstance(generator, ArticlesGenerator): + for article in generator.articles: + extract_summary(article) + elif isinstance(generator, PagesGenerator): + for page in generator.pages: + extract_summary(page) + + +def register(): + signals.initialized.connect(initialized) + try: + signals.all_generators_finalized.connect(run_plugin) + except AttributeError: + # NOTE: This results in #314 so shouldn't really be relied on + # https://github.com/getpelican/pelican-plugins/issues/314 + signals.content_object_init.connect(extract_summary) diff --git a/homepage/theme/templates/archives.html b/homepage/theme/templates/archives.html index 9433912..55e00c9 100644 --- a/homepage/theme/templates/archives.html +++ b/homepage/theme/templates/archives.html @@ -14,7 +14,7 @@ {% endif %}
- {{ article.content }} + {{ article.summary }}
{% endfor %}