Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: Add setting to omit selected Typogrify filters. Fixes #3436 #3439

Merged
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 8 additions & 1 deletion docs/settings.rst
Original file line number Diff line number Diff line change
@@ -288,7 +288,14 @@ Basic settings

A list of tags for Typogrify to ignore. By default Typogrify will ignore
``pre`` and ``code`` tags. This requires that Typogrify version 2.0.4 or
later is installed
later is installed.

.. data:: TYPOGRIFY_OMIT_FILTERS = []

A list of Typogrify filters to skip. Allowed values are: ``'amp'``,
``'smartypants'``, ``'caps'``, ``'initial_quotes'``, ``'widont'``. By
default, no filter is omitted (in other words, all filters get applied). This
davidlesieur marked this conversation as resolved.
Show resolved Hide resolved
setting requires that Typogrify version 2.1.0 or later is installed.

.. data:: TYPOGRIFY_DASHES = 'default'

17 changes: 14 additions & 3 deletions pelican/readers.py
Original file line number Diff line number Diff line change
@@ -648,11 +648,22 @@ def read_file(
smartypants.Attr.default |= smartypants.Attr.w

def typogrify_wrapper(text):
"""Ensures ignore_tags feature is backward compatible"""
"""Ensure compatibility with older versions of Typogrify.

The 'TYPOGRIFY_IGNORE_TAGS' and/or 'TYPOGRIFY_OMIT_FILTERS'
settings will be ignored if the installed version of Typogrify
doesn't have the corresponding features."""
try:
return typogrify(text, self.settings["TYPOGRIFY_IGNORE_TAGS"])
return typogrify(
text,
self.settings["TYPOGRIFY_IGNORE_TAGS"],
**{f: False for f in self.settings["TYPOGRIFY_OMIT_FILTERS"]},
)
except TypeError:
return typogrify(text)
try:
typogrify(text, self.settings["TYPOGRIFY_IGNORE_TAGS"])
except TypeError:
return typogrify(text)

if content:
content = typogrify_wrapper(content)
1 change: 1 addition & 0 deletions pelican/settings.py
Original file line number Diff line number Diff line change
@@ -149,6 +149,7 @@ def load_source(name: str, path: str) -> ModuleType:
"ARTICLE_PERMALINK_STRUCTURE": "",
"TYPOGRIFY": False,
"TYPOGRIFY_IGNORE_TAGS": [],
"TYPOGRIFY_OMIT_FILTERS": [],
"TYPOGRIFY_DASHES": "default",
"SUMMARY_END_SUFFIX": "…",
"SUMMARY_MAX_LENGTH": 50,
84 changes: 84 additions & 0 deletions pelican/tests/test_readers.py
Original file line number Diff line number Diff line change
@@ -409,6 +409,90 @@ def test_typogrify_summary(self):
except ImportError:
return unittest.skip("need the typogrify distribution")

def test_typogrify_ignore_filters(self):
try:
# typogrify should be able to ignore user specified filters.
page = self.read_file(
path="article_with_code_block.rst",
TYPOGRIFY=True,
TYPOGRIFY_OMIT_FILTERS=["amp"],
)
expected = (
"<p>An article with some&nbsp;code</p>\n"
'<div class="highlight"><pre><span></span>'
'<span class="n">x</span>'
' <span class="o">&amp;</span>'
' <span class="n">y</span>\n</pre></div>\n'
"<p>A block&nbsp;quote:</p>\n<blockquote>\nx "
"&amp; y</blockquote>\n"
"<p>Normal:\nx &amp;&nbsp;y</p>\n"
)
self.assertEqual(page.content, expected)

page = self.read_file(
path="article.rst",
TYPOGRIFY=True,
TYPOGRIFY_OMIT_FILTERS=["smartypants"],
)
expected = (
'<p><span class="caps">THIS</span> is some content. '
"With some stuff to&nbsp;&quot;typogrify&quot;...</p>\n"
'<p>Now with added support for <abbr title="three letter '
'acronym"><span class="caps">TLA</span></abbr>.</p>\n'
)
self.assertEqual(page.content, expected)

page = self.read_file(
path="article.rst",
TYPOGRIFY=True,
TYPOGRIFY_OMIT_FILTERS=["caps"],
)
expected = (
"<p>THIS is some content. "
"With some stuff to&nbsp;&#8220;typogrify&#8221;&#8230;</p>\n"
'<p>Now with added support for <abbr title="three letter '
'acronym">TLA</abbr>.</p>\n'
)
self.assertEqual(page.content, expected)

page = self.read_file(
path="article.rst",
TYPOGRIFY=True,
TYPOGRIFY_OMIT_FILTERS=["initial_quotes"],
)
expected = (
'<p><span class="caps">THIS</span> is some content. '
"With some stuff to&nbsp;&#8220;typogrify&#8221;&#8230;</p>\n"
'<p>Now with added support for <abbr title="three letter '
'acronym"><span class="caps">TLA</span></abbr>.</p>\n'
)
self.assertEqual(page.content, expected)

page = self.read_file(
path="article.rst",
TYPOGRIFY=True,
TYPOGRIFY_OMIT_FILTERS=["widont"],
)
expected = (
'<p><span class="caps">THIS</span> is some content. '
"With some stuff to "
"&#8220;typogrify&#8221;&#8230;</p>\n<p>Now with added "
'support for <abbr title="three letter acronym">'
'<span class="caps">TLA</span></abbr>.</p>\n'
)
self.assertEqual(page.content, expected)

page = self.read_file(
path="article.rst",
TYPOGRIFY=True,
TYPOGRIFY_OMIT_FILTERS=["this-filter-does-not-exists"],
)
self.assertRaises(TypeError)
except ImportError:
return unittest.skip("need the typogrify distribution")
except TypeError:
return unittest.skip("need typogrify version 2.1.0 or later")

def test_typogrify_ignore_tags(self):
try:
# typogrify should be able to ignore user specified tags.
Loading