spec_parser: check next_token if not expecting next token (#49408)

This commit is contained in:
Harmen Stoppels 2025-03-12 08:39:23 +01:00 committed by GitHub
parent 9f69d9b286
commit db7ab9826d
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
2 changed files with 24 additions and 12 deletions

View File

@ -485,23 +485,18 @@ def parse_one_or_raise(
text (str): text to be parsed
initial_spec: buffer where to parse the spec. If None a new one will be created.
"""
stripped_text = text.strip()
parser = SpecParser(stripped_text)
parser = SpecParser(text)
result = parser.next_spec(initial_spec)
last_token = parser.ctx.current_token
next_token = parser.ctx.next_token
if last_token is not None and last_token.end != len(stripped_text):
message = "a single spec was requested, but parsed more than one:"
message += f"\n{text}"
if last_token is not None:
underline = f"\n{' ' * last_token.end}{'^' * (len(text) - last_token.end)}"
if next_token:
message = f"expected a single spec, but got more:\n{text}"
underline = f"\n{' ' * next_token.start}{'^' * len(next_token.value)}"
message += color.colorize(f"@*r{{{underline}}}")
raise ValueError(message)
if result is None:
message = "a single spec was requested, but none was parsed:"
message += f"\n{text}"
raise ValueError(message)
raise ValueError("expected a single spec, but got none")
return result

View File

@ -21,6 +21,7 @@
SpecParsingError,
SpecTokenizationError,
SpecTokens,
parse_one_or_raise,
)
from spack.tokenize import Token
@ -1285,3 +1286,19 @@ def test_git_ref_spec_equivalences(mock_packages, lhs_str, rhs_str, expected):
def test_platform_is_none_if_not_present(spec_str):
s = SpecParser(spec_str).next_spec()
assert s.architecture.platform is None, s
def test_parse_one_or_raise_error_message():
with pytest.raises(ValueError) as exc:
parse_one_or_raise(" x y z")
msg = """\
expected a single spec, but got more:
x y z
^\
"""
assert str(exc.value) == msg
with pytest.raises(ValueError, match="expected a single spec, but got none"):
parse_one_or_raise(" ")