madpah / requirements-parser

A Pip requirements file parser.
https://requirements-parser.readthedocs.io
Apache License 2.0
128 stars 42 forks source link

the parser chokes on a single dot #83

Open szabgab opened 1 year ago

szabgab commented 1 year ago

In the PyDigger project I monitor PyPI and analyze recent releases. Among other things I use requirements-parser to parse the requirements.txt file.

Recently I encountered this project https://github.com/Te-k/pycrtsh where the "requirements.txt" file contains a single dot"

.

the parser raises an exception.

Is this a bug in requirements.parse or is having a single dot really incorrect?

See:

>>> import requirements
>>> for req in requirements.parse(".\n"): print(req)
... 

Traceback (most recent call last):
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/_vendor/packaging/requirements.py", line 98, in __init__
    req = REQUIREMENT.parseString(requirement_string)
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/_vendor/pyparsing.py", line 1654, in parseString
    raise exc
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/_vendor/pyparsing.py", line 1644, in parseString
    loc, tokens = self._parse( instring, 0 )
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/_vendor/pyparsing.py", line 1402, in _parseNoCache
    loc,tokens = self.parseImpl( instring, preloc, doActions )
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/_vendor/pyparsing.py", line 3417, in parseImpl
    loc, exprtokens = e._parse( instring, loc, doActions )
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/_vendor/pyparsing.py", line 1402, in _parseNoCache
    loc,tokens = self.parseImpl( instring, preloc, doActions )
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/_vendor/pyparsing.py", line 3739, in parseImpl
    return self.expr._parse( instring, loc, doActions, callPreParse=False )
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/_vendor/pyparsing.py", line 1402, in _parseNoCache
    loc,tokens = self.parseImpl( instring, preloc, doActions )
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/_vendor/pyparsing.py", line 3400, in parseImpl
    loc, resultlist = self.exprs[0]._parse( instring, loc, doActions, callPreParse=False )
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/_vendor/pyparsing.py", line 1406, in _parseNoCache
    loc,tokens = self.parseImpl( instring, preloc, doActions )
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/_vendor/pyparsing.py", line 2711, in parseImpl
    raise ParseException(instring, loc, self.errmsg, self)
pkg_resources._vendor.pyparsing.ParseException: Expected W:(abcd...) (at char 0), (line:1, col:1)

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python3.9/site-packages/requirements/parser.py", line 87, in parse
    yield Requirement.parse(line)
  File "/usr/local/lib/python3.9/site-packages/requirements/requirement.py", line 254, in parse
    return cls.parse_line(line)
  File "/usr/local/lib/python3.9/site-packages/requirements/requirement.py", line 232, in parse_line
    pkg_req = Req.parse(line)
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/__init__.py", line 3139, in parse
    req, = parse_requirements(s)
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/__init__.py", line 3084, in parse_requirements
    yield Requirement(line)
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/__init__.py", line 3094, in __init__
    super(Requirement, self).__init__(requirement_string)
  File "/usr/local/lib/python3.9/site-packages/pkg_resources/_vendor/packaging/requirements.py", line 100, in __init__
    raise InvalidRequirement(
pkg_resources.extern.packaging.requirements.InvalidRequirement: Parse error at "'.'": Expected W:(abcd...)
madpah commented 7 months ago

Thanks for taking the time to share this @szabgab.

A single dot in a requirements.txt can be used when dependencies are defined in another place (e.g. setup.py in the example you share).

Agree that this project shouldn't choke on this however, so will look to make an improvement.