Skip to content

Commit cb09331

Browse files
committed
Enforce word boundaries in operators and names
This ensures that these are only parsed when they're independent words.
1 parent b41326d commit cb09331

File tree

2 files changed

+26
-8
lines changed

2 files changed

+26
-8
lines changed

packaging/_tokenizer.py

+6-6
Original file line numberDiff line numberDiff line change
@@ -53,12 +53,12 @@ def __str__(self) -> str:
5353
re.VERBOSE,
5454
),
5555
"OP": r"(===|==|~=|!=|<=|>=|<|>)",
56-
"BOOLOP": r"(or|and)",
57-
"IN": r"in",
58-
"NOT": r"not",
56+
"BOOLOP": r"\b(or|and)\b",
57+
"IN": r"\bin\b",
58+
"NOT": r"\bnot\b",
5959
"VARIABLE": re.compile(
6060
r"""
61-
(
61+
\b(
6262
python_version
6363
|python_full_version
6464
|os[._]name
@@ -68,14 +68,14 @@ def __str__(self) -> str:
6868
|python_implementation
6969
|implementation_(name|version)
7070
|extra
71-
)
71+
)\b
7272
""",
7373
re.VERBOSE,
7474
),
7575
"VERSION": re.compile(Specifier._version_regex_str, re.VERBOSE | re.IGNORECASE),
7676
"AT": r"\@",
7777
"URL": r"[^ \t]+",
78-
"IDENTIFIER": r"[a-zA-Z0-9][a-zA-Z0-9._-]*",
78+
"IDENTIFIER": r"\b[a-zA-Z0-9][a-zA-Z0-9._-]*\b",
7979
"WS": r"[ \t]+",
8080
"END": r"$",
8181
}

tests/test_requirements.py

+20-2
Original file line numberDiff line numberDiff line change
@@ -390,9 +390,27 @@ def test_error_invalid_marker_notin_without_whitespace(self) -> None:
390390
# THEN
391391
assert ctx.exconly() == (
392392
"packaging.requirements.InvalidRequirement: "
393-
"Expected whitespace after 'not'\n"
393+
"Expected marker operator, one of <=, <, !=, ==, >=, >, ~=, ===, "
394+
"not, not in\n"
394395
" name; '3.7' notin python_version\n"
395-
" ^"
396+
" ^"
397+
)
398+
399+
def test_error_when_no_word_boundary(self) -> None:
400+
# GIVEN
401+
to_parse = "name; '3.6'inpython_version"
402+
403+
# WHEN
404+
with pytest.raises(InvalidRequirement) as ctx:
405+
Requirement(to_parse)
406+
407+
# THEN
408+
assert ctx.exconly() == (
409+
"packaging.requirements.InvalidRequirement: "
410+
"Expected marker operator, one of <=, <, !=, ==, >=, >, ~=, ===, "
411+
"not, not in\n"
412+
" name; '3.6'inpython_version\n"
413+
" ^"
396414
)
397415

398416
def test_error_invalid_marker_not_without_in(self) -> None:

0 commit comments

Comments
 (0)