Skip to content

Commit 97420ae

Browse files
committed
Support - in npm version ranges #83
Reference: #83 Signed-off-by: Tushar Goel <tushar.goel.dav@gmail.com>
1 parent d3c8797 commit 97420ae

3 files changed

Lines changed: 96 additions & 35 deletions

File tree

src/univers/version_range.py

Lines changed: 42 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -238,7 +238,7 @@ def get_allof_constraints(cls, clause):
238238
return allof_constraints
239239

240240

241-
def get_npm_version_constraint_for_tilde_and_caret(string, cls):
241+
def get_npm_version_constraints_from_semver_npm_spec(string, cls):
242242
"""
243243
Return a VersionConstraint for the provided ``string``.
244244
"""
@@ -254,7 +254,6 @@ def get_npm_version_constraint_for_tilde_and_caret(string, cls):
254254
anyof_constraints.extend(alloc)
255255
else:
256256
raise ValueError(f"Unknown clause type: {spec!r}")
257-
258257
return anyof_constraints
259258

260259

@@ -289,39 +288,56 @@ def from_native(cls, string):
289288
)
290289

291290
constraints = []
292-
comparator = ""
293291
vrc = cls.version_class
294292
# A constraint item can be a comparator or a version or a version with comparator
295293
# If it's empty continue
296294
# If it's in `vers_by_native_comparators`, append it with the comparator and continue
297295
# If it's a version, make version constraint from the version and use the comparator from the previous item and make comparator empty
298296
# If it's a version with comparator, use split_req to get version and comparator to form constraint and make comparator empty
299-
for constraint_item in string.split(" "):
300-
if not constraint_item or constraint_item == "||":
301-
continue
302-
if "".join([comparator, constraint_item]) in cls.vers_by_native_comparators:
303-
comparator = "".join([comparator, constraint_item])
304-
comparator = cls.vers_by_native_comparators[comparator]
297+
298+
for range in string.split("||"):
299+
if " - " in range:
300+
constraints.extend(get_npm_version_constraints_from_semver_npm_spec(range, cls))
305301
continue
306-
if comparator:
307-
constraint_item = constraint_item.lstrip("vV")
308-
constraints.append(
309-
VersionConstraint(comparator=comparator, version=vrc(constraint_item))
310-
)
311-
else:
312-
if constraint_item.startswith("~") or constraint_item.startswith("^"):
313-
constraints.extend(
314-
get_npm_version_constraint_for_tilde_and_caret(constraint_item, cls)
315-
)
316-
else:
317-
comparator, version_constraint = split_req(
318-
constraint_item, cls.vers_by_native_comparators, default="="
319-
)
320-
version_constraint = version_constraint.lstrip("vV")
302+
comparator = ""
303+
for constraint in range.split(" "):
304+
if not constraint:
305+
continue
306+
if "".join([comparator, constraint]) in cls.vers_by_native_comparators:
307+
comparator = "".join([comparator, constraint])
308+
comparator = cls.vers_by_native_comparators[comparator]
309+
continue
310+
if comparator:
311+
if ".x" in constraint:
312+
constraints.extend(
313+
get_npm_version_constraints_from_semver_npm_spec(constraint, cls)
314+
)
315+
continue
316+
constraint = constraint.lstrip("vV")
321317
constraints.append(
322-
VersionConstraint(comparator=comparator, version=vrc(version_constraint))
318+
VersionConstraint(comparator=comparator, version=vrc(constraint))
323319
)
324-
comparator = ""
320+
else:
321+
if ".x" in constraint:
322+
constraints.extend(
323+
get_npm_version_constraints_from_semver_npm_spec(constraint, cls)
324+
)
325+
continue
326+
if constraint.startswith("~") or constraint.startswith("^"):
327+
constraints.extend(
328+
get_npm_version_constraints_from_semver_npm_spec(constraint, cls)
329+
)
330+
else:
331+
comparator, version_constraint = split_req(
332+
constraint, cls.vers_by_native_comparators, default="="
333+
)
334+
version_constraint = version_constraint.lstrip("vV")
335+
constraints.append(
336+
VersionConstraint(
337+
comparator=comparator, version=vrc(version_constraint)
338+
)
339+
)
340+
comparator = ""
325341
return cls(constraints=constraints)
326342

327343

tests/data/npm_advisory.json

Lines changed: 45 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -728,13 +728,13 @@
728728
{
729729
"test_index": 122,
730730
"scheme": "npm",
731-
"npm_native": ">=2.0.0-alpha8",
731+
"npm_native": ">=v2.0.0-alpha8",
732732
"expected_vers": "vers:npm/>=2.0.0-alpha8"
733733
},
734734
{
735735
"test_index": 123,
736736
"scheme": "npm",
737-
"npm_native": "<=2.0.0-alpha7",
737+
"npm_native": "<=v2.0.0-alpha7",
738738
"expected_vers": "vers:npm/<=2.0.0-alpha7"
739739
},
740740
{
@@ -1406,13 +1406,13 @@
14061406
{
14071407
"test_index": 235,
14081408
"scheme": "npm",
1409-
"npm_native": ">=v2.6.0",
1409+
"npm_native": ">=2.6.0",
14101410
"expected_vers": "vers:npm/>=2.6.0"
14111411
},
14121412
{
14131413
"test_index": 236,
14141414
"scheme": "npm",
1415-
"npm_native": "<v2.6.0",
1415+
"npm_native": "<2.6.0",
14161416
"expected_vers": "vers:npm/<2.6.0"
14171417
},
14181418
{
@@ -1653,13 +1653,13 @@
16531653
"test_index": 276,
16541654
"scheme": "npm",
16551655
"npm_native": ">= 2.2.x",
1656-
"expected_vers": "vers:npm/>=2.2.0+x"
1656+
"expected_vers": "vers:npm/>=2.2.0|<2.3.0"
16571657
},
16581658
{
16591659
"test_index": 277,
16601660
"scheme": "npm",
16611661
"npm_native": "2.0.x || 2.1.x",
1662-
"expected_vers": "vers:npm/2.0.0+x|2.1.0+x"
1662+
"expected_vers": "vers:npm/>=2.0.0|<2.1.0|>=2.1.0|<2.2.0"
16631663
},
16641664
{
16651665
"test_index": 278,
@@ -2481,7 +2481,7 @@
24812481
"test_index": 414,
24822482
"scheme": "npm",
24832483
"npm_native": ">= 1.x",
2484-
"expected_vers": "vers:npm/>=1.0.0+x"
2484+
"expected_vers": "vers:npm/>=1.0.0|<2.0.0"
24852485
},
24862486
{
24872487
"test_index": 415,
@@ -3429,7 +3429,7 @@
34293429
"test_index": 572,
34303430
"scheme": "npm",
34313431
"npm_native": ">=3.4.6 < 4.0.0|| >=4.0.5",
3432-
"expected_vers": "vers:npm/>=3.4.6|<4.0.0--|>=4.0.5"
3432+
"expected_vers": "vers:npm/>=3.4.6|<4.0.0|>=4.0.5"
34333433
},
34343434
{
34353435
"test_index": 573,
@@ -4077,7 +4077,7 @@
40774077
"test_index": 680,
40784078
"scheme": "npm",
40794079
"npm_native": ">= 1.x",
4080-
"expected_vers": "vers:npm/>=1.0.0+x"
4080+
"expected_vers": "vers:npm/>=1.0.0|<2.0.0"
40814081
},
40824082
{
40834083
"test_index": 681,
@@ -5272,5 +5272,41 @@
52725272
"scheme": "npm",
52735273
"npm_native": "<3.0.1",
52745274
"expected_vers": "vers:npm/<3.0.1"
5275+
},
5276+
{
5277+
"test_index": 880,
5278+
"scheme": "npm",
5279+
"npm_native": "^1.2.9",
5280+
"expected_vers": "vers:npm/>=1.2.9|<2.0.0"
5281+
},
5282+
{
5283+
"test_index": 881,
5284+
"scheme": "npm",
5285+
"npm_native": "~3.8.2",
5286+
"expected_vers": "vers:npm/>=3.8.2|<3.9.0"
5287+
},
5288+
{
5289+
"test_index": 882,
5290+
"scheme": "npm",
5291+
"npm_native": "5.0.0 - 7.2.3",
5292+
"expected_vers": "vers:npm/>=5.0.0|<=7.2.3"
5293+
},
5294+
{
5295+
"test_index": 883,
5296+
"scheme": "npm",
5297+
"npm_native": "2.1 || 2.6",
5298+
"expected_vers": "vers:npm/2.1.0|2.6.0"
5299+
},
5300+
{
5301+
"test_index": 884,
5302+
"scheme": "npm",
5303+
"npm_native": "1.1.2 1.2.2",
5304+
"expected_vers": "vers:npm/1.1.2|1.2.2"
5305+
},
5306+
{
5307+
"test_index": 885,
5308+
"scheme": "npm",
5309+
"npm_native": "<=2.1 >=1.1",
5310+
"expected_vers": "vers:npm/>=1.1.0|<=2.1.0"
52755311
}
52765312
]

tests/test_version_range.py

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -281,6 +281,15 @@ def test_nuget_version_range(self):
281281

282282
VERSION_RANGE_TESTS_BY_SCHEME = {
283283
"nginx": ["0.8.40+", "0.7.52-0.8.39", "0.9.10", "1.5.0+, 1.4.1+"],
284+
"npm": [
285+
"^1.2.9",
286+
"~3.8.2",
287+
"5.0.0 - 7.2.3",
288+
"2.1.0 || 2.6.0",
289+
"1.1.2 1.2.2",
290+
"<=2.1.0 >=1.1.0",
291+
"1.2.x",
292+
],
284293
"openssl": ["1.1.1ak", "1.1.0", "3.0.2", "3.0.1, 0.9.7a", "1.0.2ck, 3.1.2"],
285294
"pypi": [">= 1.0", "<2.1.0", "!=5"],
286295
}

0 commit comments

Comments
 (0)