Skip to content

Commit

Permalink
Merge pull request #412 from asottile/dont_crash_no_description
Browse files Browse the repository at this point in the history
Don't crash if there is no description
  • Loading branch information
sigmavirus24 authored Oct 15, 2018
2 parents 191cf5c + 125b772 commit bd1d8b0
Show file tree
Hide file tree
Showing 2 changed files with 55 additions and 23 deletions.
36 changes: 32 additions & 4 deletions tests/test_check.py
Original file line number Diff line number Diff line change
Expand Up @@ -58,11 +58,13 @@ def test_check_passing_distribution(monkeypatch):
renderer = pretend.stub(
render=pretend.call_recorder(lambda *a, **kw: "valid")
)
package = pretend.stub(metadata_dictionary=lambda: {"description": "blah"})
package = pretend.stub(metadata_dictionary=lambda: {
"description": "blah", 'description_content_type': 'text/markdown',
})
output_stream = check.StringIO()
warning_stream = ""

monkeypatch.setattr(check, "_RENDERERS", {"": renderer})
monkeypatch.setattr(check, "_RENDERERS", {None: renderer})
monkeypatch.setattr(check, "_find_dists", lambda a: ["dist/dist.tar.gz"])
monkeypatch.setattr(
check,
Expand All @@ -81,15 +83,41 @@ def test_check_passing_distribution(monkeypatch):
]


def test_check_no_description(monkeypatch, capsys):
package = pretend.stub(metadata_dictionary=lambda: {
'description': None, 'description_content_type': None,
})

monkeypatch.setattr(check, "_find_dists", lambda a: ["dist/dist.tar.gz"])
monkeypatch.setattr(
check,
"PackageFile",
pretend.stub(from_filename=lambda *a, **kw: package),
)

# used to crash with `AttributeError`
output_stream = check.StringIO()
check.check("dist/*", output_stream=output_stream)
assert output_stream.getvalue() == (
'Checking distribution dist/dist.tar.gz: '
'warning: `long_description_content_type` missing. '
'defaulting to `text/x-rst`.\n'
'warning: `long_description` missing.\n'
'Passed\n'
)


def test_check_failing_distribution(monkeypatch):
renderer = pretend.stub(
render=pretend.call_recorder(lambda *a, **kw: None)
)
package = pretend.stub(metadata_dictionary=lambda: {"description": "blah"})
package = pretend.stub(metadata_dictionary=lambda: {
"description": "blah", "description_content_type": 'text/markdown',
})
output_stream = check.StringIO()
warning_stream = "WARNING"

monkeypatch.setattr(check, "_RENDERERS", {"": renderer})
monkeypatch.setattr(check, "_RENDERERS", {None: renderer})
monkeypatch.setattr(check, "_find_dists", lambda a: ["dist/dist.tar.gz"])
monkeypatch.setattr(
check,
Expand Down
42 changes: 23 additions & 19 deletions twine/commands/check.py
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,6 @@

_RENDERERS = {
None: readme_renderer.rst, # Default if description_content_type is None
"": readme_renderer.rst, # Default if description_content_type is None
"text/plain": readme_renderer.txt,
"text/x-rst": readme_renderer.rst,
"text/markdown": readme_renderer.markdown,
Expand Down Expand Up @@ -85,28 +84,33 @@ def check(dists, output_stream=sys.stdout):
package = PackageFile.from_filename(filename, comment=None)

metadata = package.metadata_dictionary()
content_type, parameters = cgi.parse_header(
metadata.get("description_content_type") or ""
)

# Get the appropriate renderer
renderer = _RENDERERS.get(content_type, readme_renderer.txt)

# Actually render the given value
rendered = renderer.render(
metadata.get("description"), stream=stream, **parameters
)
description = metadata["description"]
description_content_type = metadata["description_content_type"]

if rendered is None:
failure = True
output_stream.write("Failed\n")
if description_content_type is None:
output_stream.write(
"The project's long_description has invalid markup which will "
"not be rendered on PyPI. The following syntax errors were "
"detected:\n%s" % stream
'warning: `long_description_content_type` missing. '
'defaulting to `text/x-rst`.\n'
)
else:
description_content_type = 'text/x-rst'

content_type, params = cgi.parse_header(description_content_type)
renderer = _RENDERERS.get(content_type, _RENDERERS[None])

if description in {None, 'UNKNOWN\n\n\n'}:
output_stream.write('warning: `long_description` missing.\n')
output_stream.write("Passed\n")
else:
if renderer.render(description, stream=stream, **params) is None:
failure = True
output_stream.write("Failed\n")
output_stream.write(
"The project's long_description has invalid markup which "
"will not be rendered on PyPI. The following syntax "
"errors were detected:\n%s" % stream
)
else:
output_stream.write("Passed\n")

return failure

Expand Down

0 comments on commit bd1d8b0

Please sign in to comment.