Skip to content

Commit

Permalink
Disallow files for license inputs
Browse files Browse the repository at this point in the history
The ability to handle files was originally added and documented based on
a misunderstanding of what the `license` field should include. The field
should be the name of the license, not the full text.

It is likely that anyone actually using this was outputing malformed
PKG-INFO files, because most license files contain newlines.

See GH issue pypa#1551
  • Loading branch information
RajdeepRao authored and pganssle committed Dec 29, 2018
1 parent 17ad2b7 commit 8f00d60
Show file tree
Hide file tree
Showing 3 changed files with 44 additions and 4 deletions.
1 change: 0 additions & 1 deletion setup.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -26,4 +26,3 @@ universal = 1
license_file = LICENSE

[bumpversion:file:setup.py]

22 changes: 20 additions & 2 deletions setuptools/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -246,6 +246,24 @@ def _parse_bool(cls, value):
value = value.lower()
return value in ('1', 'true', 'yes')

@classmethod
def _exclude_files_parser(cls, key):
"""Returns a parser function to make sure field inputs
are not files.
Parses a value after getting the key so error messages are
more informative.
:param key:
:rtype: callable
"""
def parser(value):
exclude_directive = 'file:'
if value.startswith(exclude_directive):
raise ValueError('Only strings are accepted for the {0} field, files are not accepted'.format(key))
return value
return parser

@classmethod
def _parse_file(cls, value):
"""Represents value as a string, allowing including text
Expand All @@ -255,7 +273,6 @@ def _parse_file(cls, value):
directory with setup.py.
Examples:
file: LICENSE
file: README.rst, CHANGELOG.md, src/file.txt
:param str value:
Expand Down Expand Up @@ -449,6 +466,7 @@ def parsers(self):
parse_list = self._parse_list
parse_file = self._parse_file
parse_dict = self._parse_dict
exclude_files_parser = self._exclude_files_parser

return {
'platforms': parse_list,
Expand All @@ -460,7 +478,7 @@ def parsers(self):
DeprecationWarning),
'obsoletes': parse_list,
'classifiers': self._get_parser_compound(parse_file, parse_list),
'license': parse_file,
'license': exclude_files_parser('license'),
'description': parse_file,
'long_description': parse_file,
'version': self._parse_version,
Expand Down
25 changes: 24 additions & 1 deletion setuptools/tests/test_egg_info.py
Original file line number Diff line number Diff line change
Expand Up @@ -148,6 +148,26 @@ def test_expected_files_produced(self, tmpdir_cwd, env):
]
assert sorted(actual) == expected

def test_license_is_a_string(self, tmpdir_cwd, env):
setup_config = DALS("""
[metadata]
name=foo
version=0.0.1
license=file:MIT
""")

setup_script = DALS("""
from setuptools import setup
setup()
""")

build_files({'setup.py': setup_script,
'setup.cfg': setup_config})

with pytest.raises(ValueError):
self._run_egg_info_command(tmpdir_cwd, env)

def test_rebuilt(self, tmpdir_cwd, env):
"""Ensure timestamps are updated when the command is re-run."""
self._create_project()
Expand Down Expand Up @@ -598,7 +618,10 @@ def _run_egg_info_command(self, tmpdir_cwd, env, cmd=None, output=None):
env=environ,
)
if code:
raise AssertionError(data)
if 'ValueError' in data:
raise ValueError(data)
else:
raise AssertionError(data)
if output:
assert output in data

Expand Down

0 comments on commit 8f00d60

Please sign in to comment.