Skip to content

Commit 922337d

Browse files
author
Bilal Al
committed
Added version property, applied csv files for testing and updated equalto and inlist matchers
1 parent ee6174b commit 922337d

File tree

7 files changed

+153
-95
lines changed

7 files changed

+153
-95
lines changed

splitio/models/grammar/matchers/semver.py

Lines changed: 32 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -26,14 +26,25 @@ def __init__(self, version):
2626
self._patch = 0
2727
self._pre_release = []
2828
self._is_stable = False
29-
self._old_version = version
30-
self._parse()
29+
self.version = ""
30+
self._metadata = ""
31+
self._parse(version)
32+
33+
@classmethod
34+
def build(cls, version):
35+
try:
36+
self = cls(version)
37+
except RuntimeError as e:
38+
_LOGGER.error("Failed to parse Semver data, incorrect data type: %s", e)
39+
return None
40+
41+
return self
3142

32-
def _parse(self):
43+
def _parse(self, version):
3344
"""
34-
Parse the string in self._old_version to update the other internal variables
45+
Parse the string in self.version to update the other internal variables
3546
"""
36-
without_metadata = self.remove_metadata_if_exists()
47+
without_metadata = self.remove_metadata_if_exists(version)
3748

3849
index = without_metadata.find(self._PRE_RELEASE_DELIMITER)
3950
if index == -1:
@@ -45,18 +56,19 @@ def _parse(self):
4556

4657
self.set_major_minor_and_patch(without_metadata)
4758

48-
def remove_metadata_if_exists(self):
59+
def remove_metadata_if_exists(self, version):
4960
"""
50-
Check if there is any metadata characters in self._old_version.
61+
Check if there is any metadata characters in self.version.
5162
5263
:returns: The semver string without the metadata
5364
:rtype: str
5465
"""
55-
index = self._old_version.find(self._METADATA_DELIMITER)
66+
index = version.find(self._METADATA_DELIMITER)
5667
if index == -1:
57-
return self._old_version
68+
return version
5869

59-
return self._old_version[:index]
70+
self._metadata = version[index:]
71+
return version[:index]
6072

6173
def set_major_minor_and_patch(self, version):
6274
"""
@@ -74,6 +86,12 @@ def set_major_minor_and_patch(self, version):
7486
self._minor = int(parts[1])
7587
self._patch = int(parts[2])
7688

89+
self.version = "{major}{DELIMITER}{minor}{DELIMITER}{patch}".format(major = self._major, DELIMITER = self._VALUE_DELIMITER,
90+
minor = self._minor, patch = self._patch)
91+
self.version += "{DELIMITER}{pre_release}".format(DELIMITER=self._PRE_RELEASE_DELIMITER,
92+
pre_release = '.'.join(self._pre_release)) if len(self._pre_release) > 0 else ""
93+
self.version += "{DELIMITER}{metadata}".format(DELIMITER=self._METADATA_DELIMITER, metadata = self._metadata) if self._metadata != "" else ""
94+
7795
def compare(self, to_compare):
7896
"""
7997
Compare the current Semver object to a given Semver object, return:
@@ -87,7 +105,7 @@ def compare(self, to_compare):
87105
:returns: integer based on comparison
88106
:rtype: int
89107
"""
90-
if self._old_version == to_compare._old_version:
108+
if self.version == to_compare.version:
91109
return 0
92110

93111
# Compare major, minor, and patch versions numerically
@@ -178,7 +196,7 @@ def _match(self, key, attributes=None, context=None):
178196
if matching_data is None:
179197
return False
180198

181-
return self._semver.compare(Semver(matching_data)) == 0
199+
return self._semver.version == Semver(matching_data).version
182200

183201
def __str__(self):
184202
"""Return string Representation."""
@@ -362,12 +380,12 @@ def _match(self, key, attributes=None, context=None):
362380
if matching_data is None:
363381
return False
364382

365-
return any([item.compare(Semver(matching_data)) == 0 if item is not None else False for item in self._semver_list])
383+
return any([item.version == Semver(matching_data).version if item is not None else False for item in self._semver_list])
366384

367385
def __str__(self):
368386
"""Return string Representation."""
369387
return 'in list semver {data}'.format(data=self._data)
370388

371389
def _add_matcher_specific_properties_to_json(self):
372390
"""Add matcher specific properties to base dict before returning it."""
373-
return {'matcherType': 'IN_LIST_SEMVER', 'whitelistMatcherData': {'whitelist': self._data}}
391+
return {'matcherType': 'IN_LIST_SEMVER', 'whitelistMatcherData': {'whitelist': self._data}}
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
version1,version2,version3,expected
2+
1.1.1,2.2.2,3.3.3,true
3+
1.1.1-rc.1,1.1.1-rc.2,1.1.1-rc.3,true
4+
1.0.0-alpha,1.0.0-alpha.1,1.0.0-alpha.beta,true
5+
1.0.0-alpha.1,1.0.0-alpha.beta,1.0.0-beta,true
6+
1.0.0-alpha.beta,1.0.0-beta,1.0.0-beta.2,true
7+
1.0.0-beta,1.0.0-beta.2,1.0.0-beta.11,true
8+
1.0.0-beta.2,1.0.0-beta.11,1.0.0-rc.1,true
9+
1.0.0-beta.11,1.0.0-rc.1,1.0.0,true
10+
1.1.2,1.1.3,1.1.4,true
11+
1.2.1,1.3.1,1.4.1,true
12+
2.0.0,3.0.0,4.0.0,true
13+
2.2.2,2.2.3-rc1,2.2.3,true
14+
2.2.2,2.3.2-rc100,2.3.3,true
15+
1.0.0-rc.1+build.1,1.2.3-beta,1.2.3-rc.1+build.123,true
16+
3.3.3,3.3.3-alpha,3.3.4,false
17+
2.2.2-rc.1,2.2.2+metadata,2.2.2-rc.10,false
18+
1.1.1-rc.1,1.1.1-rc.3,1.1.1-rc.2,false
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
version1,version2,equals
2+
1.1.1,1.1.1,true
3+
1.1.1,1.1.1+metadata,false
4+
1.1.1,1.1.1-rc.1,false
5+
88.88.88,88.88.88,true
6+
1.2.3----RC-SNAPSHOT.12.9.1--.12,1.2.3----RC-SNAPSHOT.12.9.1--.12,true
7+
10.2.3-DEV-SNAPSHOT,10.2.3-SNAPSHOT-123,false
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
invalid
2+
1
3+
1.2
4+
1.alpha.2
5+
+invalid
6+
-invalid
7+
-invalid+invalid
8+
-invalid.01
9+
alpha
10+
alpha.beta
11+
alpha.beta.1
12+
alpha.1
13+
alpha+beta
14+
alpha_beta
15+
alpha.
16+
alpha..
17+
beta
18+
-alpha.
19+
1.2
20+
1.2.3.DEV
21+
1.2-SNAPSHOT
22+
1.2.31.2.3----RC-SNAPSHOT.12.09.1--..12+788
23+
1.2-RC-SNAPSHOT
24+
-1.0.3-gamma+b7718
25+
+justmeta
26+
#99999999999999999999999.999999999999999999.99999999999999999----RC-SNAPSHOT.12.09.1--------------------------------..12
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
higher,lower
2+
1.1.2,1.1.1
3+
1.0.0,1.0.0-rc.1
4+
1.1.0-rc.1,1.0.0-beta.11
5+
1.0.0-beta.11,1.0.0-beta.2
6+
1.0.0-beta.2,1.0.0-beta
7+
1.0.0-beta,1.0.0-alpha.beta
8+
1.0.0-alpha.beta,1.0.0-alpha.1
9+
1.0.0-alpha.1,1.0.0-alpha
10+
2.2.2-rc.2+metadata-lalala,2.2.2-rc.1.2
11+
1.2.3,0.0.4
12+
1.1.2+meta,1.1.2-prerelease+meta
13+
1.0.0-beta,1.0.0-alpha
14+
1.0.0-alpha0.valid,1.0.0-alpha.0valid
15+
1.0.0-rc.1+build.1,1.0.0-alpha-a.b-c-somethinglong+build.1-aef.1-its-okay
16+
10.2.3-DEV-SNAPSHOT,1.2.3-SNAPSHOT-123
17+
1.1.1-rc2,1.0.0-0A.is.legal
18+
1.2.3----RC-SNAPSHOT.12.9.1--.12+788,1.2.3----R-S.12.9.1--.12+meta
19+
1.2.3----RC-SNAPSHOT.12.9.1--.12.88,1.2.3----RC-SNAPSHOT.12.9.1--.12
20+
9223372036854775807.9223372036854775807.9223372036854775807,9223372036854775807.9223372036854775807.9223372036854775806
21+
1.1.1-alpha.beta.rc.build.java.pr.support.10,1.1.1-alpha.beta.rc.build.java.pr.support
22+
1.1.2,1.1.1
23+
1.2.1,1.1.1
24+
2.1.1,1.1.1
25+
1.1.1-rc.1,1.1.1-rc.0

tests/models/grammar/test_matchers.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -909,7 +909,7 @@ def test_from_raw(self, mocker):
909909
def test_matcher_behaviour(self, mocker):
910910
"""Test if the matcher works properly."""
911911
parsed = matchers.from_raw(self.raw)
912-
assert parsed._match("2.1.8+rc")
912+
assert not parsed._match("2.1.8+rc")
913913
assert parsed._match("2.1.8")
914914
assert not parsed._match("2.1.5")
915915
assert not parsed._match("2.1.5-rc1")
@@ -1079,8 +1079,8 @@ def test_from_raw(self, mocker):
10791079
def test_matcher_behaviour(self, mocker):
10801080
"""Test if the matcher works properly."""
10811081
parsed = matchers.from_raw(self.raw)
1082-
assert parsed._match("2.1.8+rc")
1083-
assert not parsed._match("2.1.8-rc1")
1082+
assert not parsed._match("2.1.8+rc")
1083+
assert parsed._match("2.1.8")
10841084
assert not parsed._match("2.1.11-rc12")
10851085
assert parsed._match("2.1.11")
10861086
assert not parsed._match("2.1.7")
Lines changed: 42 additions & 78 deletions
Original file line numberDiff line numberDiff line change
@@ -1,91 +1,55 @@
11
"""Condition model tests module."""
22
import pytest
3+
import csv
4+
import os
35

46
from splitio.models.grammar.matchers.semver import Semver
57

8+
valid_versions = os.path.join(os.path.dirname(__file__), 'files', 'valid-semantic-versions.csv')
9+
invalid_versions = os.path.join(os.path.dirname(__file__), 'files', 'invalid-semantic-versions.csv')
10+
equalto_versions = os.path.join(os.path.dirname(__file__), 'files', 'equal-to-semver.csv')
11+
between_versions = os.path.join(os.path.dirname(__file__), 'files', 'between-semver.csv')
12+
613
class SemverTests(object):
714
"""Test the semver object model."""
815

9-
valid_versions = ["1.1.2", "1.1.1", "1.0.0", "1.0.0-rc.1", "1.0.0-beta.11", "1.0.0-beta.2",
10-
"1.0.0-beta", "1.0.0-alpha.beta", "1.0.0-alpha.1", "1.0.0-alpha", "2.2.2-rc.2+metadata-lalala", "2.2.2-rc.1.2",
11-
"1.2.3", "0.0.4", "1.1.2+meta", "1.1.2-prerelease+meta", "1.0.0-beta", "1.0.0-alpha", "1.0.0-alpha0.valid",
12-
"1.0.0-alpha.0valid", "1.0.0-rc.1+build.1", "1.0.0-alpha-a.b-c-somethinglong+build.1-aef.1-its-okay",
13-
"10.2.3-DEV-SNAPSHOT", "1.2.3-SNAPSHOT-123", "1.1.1-rc2", "1.0.0-0A.is.legal", "1.2.3----RC-SNAPSHOT.12.9.1--.12+788",
14-
"1.2.3----R-S.12.9.1--.12+meta", "1.2.3----RC-SNAPSHOT.12.9.1--.12.88", "1.2.3----RC-SNAPSHOT.12.9.1--.12",
15-
"9223372036854775807.9223372036854775807.9223372036854775807", "9223372036854775807.9223372036854775807.9223372036854775806",
16-
"1.1.1-alpha.beta.rc.build.java.pr.support.10", "1.1.1-alpha.beta.rc.build.java.pr.support"]
17-
1816
def test_valid_versions(self):
19-
major = [1, 1, 1, 1, 1, 1,
20-
1, 1, 1, 1, 2, 2,
21-
1, 0, 1, 1, 1, 1, 1,
22-
1, 1, 1,
23-
10, 1, 1, 1, 1,
24-
1, 1, 1,
25-
9223372036854775807, 9223372036854775807,
26-
1,1]
27-
minor = [1, 1, 0, 0, 0, 0,
28-
0, 0, 0, 0, 2, 2,
29-
2, 0, 1, 1, 0, 0, 0,
30-
0, 0, 0,
31-
2, 2, 1, 0, 2,
32-
2, 2, 2,
33-
9223372036854775807, 9223372036854775807,
34-
1, 1]
35-
patch = [2, 1, 0, 0, 0, 0,
36-
0, 0, 0, 0, 2, 2,
37-
3, 4, 2, 2, 0, 0, 0,
38-
0, 0, 0,
39-
3, 3, 1, 0, 3,
40-
3, 3, 3,
41-
9223372036854775807, 9223372036854775806,
42-
1, 1]
43-
pre_release = [[], [], [], ["rc","1"], ["beta","11"],["beta","2"],
44-
["beta"], ["alpha","beta"], ["alpha","1"], ["alpha"], ["rc","2"], ["rc","1","2"],
45-
[], [], [], ["prerelease"], ["beta"], ["alpha"], ["alpha0","valid"],
46-
["alpha","0valid"], ["rc","1"], ["alpha-a","b-c-somethinglong"],
47-
["DEV-SNAPSHOT"], ["SNAPSHOT-123"], ["rc2"], ["0A","is","legal"], ["---RC-SNAPSHOT","12","9","1--","12"],
48-
["---R-S","12","9","1--","12"], ["---RC-SNAPSHOT","12","9","1--","12","88"], ["---RC-SNAPSHOT","12","9","1--","12"],
49-
[], [],
50-
["alpha","beta","rc","build","java","pr","support","10"], ["alpha","beta","rc","build","java","pr","support"]]
51-
52-
for i in range(len(major)-1):
53-
semver = Semver(self.valid_versions[i])
54-
self._verify_version(semver, major[i], minor[i], patch[i], pre_release[i], pre_release[i]==[])
17+
with open(valid_versions) as csvfile:
18+
reader = csv.DictReader(csvfile)
19+
for row in reader:
20+
assert Semver.build(row['higher']) is not None
21+
assert Semver.build(row['lower']) is not None
5522

5623
def test_invalid_versions(self):
57-
"""Test parsing invalid versions."""
58-
invalid_versions = [
59-
"1", "1.2", "1.alpha.2", "+invalid", "-invalid", "-invalid+invalid", "+justmeta",
60-
"-invalid.01", "alpha", "alpha.beta", "alpha.beta.1", "alpha.1", "alpha+beta",
61-
"alpha_beta", "alpha.", "alpha..", "beta", "-alpha.", "1.2", "1.2.3.DEV", "-1.0.3-gamma+b7718",
62-
"1.2-SNAPSHOT", "1.2.31.2.3----RC-SNAPSHOT.12.09.1--..12+788", "1.2-RC-SNAPSHOT"]
63-
# "99999999999999999999999.999999999999999999.99999999999999999----RC-SNAPSHOT.12.09.1--------------------------------..12"]
64-
65-
for version in invalid_versions:
66-
with pytest.raises(RuntimeError):
67-
semver = Semver(version)
68-
pass
24+
with open(invalid_versions) as csvfile:
25+
reader = csv.DictReader(csvfile)
26+
for row in reader:
27+
assert Semver.build(row['invalid']) is None
6928

7029
def test_compare(self):
71-
cnt = 0
72-
for i in range(int(len(self.valid_versions)/2)):
73-
assert Semver(self.valid_versions[cnt]).compare(Semver(self.valid_versions[cnt+1])) == 1
74-
assert Semver(self.valid_versions[cnt+1]).compare(Semver(self.valid_versions[cnt])) == -1
75-
assert Semver(self.valid_versions[cnt]).compare(Semver(self.valid_versions[cnt])) == 0
76-
assert Semver(self.valid_versions[cnt+1]).compare(Semver(self.valid_versions[cnt+1])) == 0
77-
cnt = cnt + 2
78-
79-
assert Semver("1.1.1").compare(Semver("1.1.1")) == 0
80-
assert Semver("1.1.1").compare(Semver("1.1.1+metadata")) == 0
81-
assert Semver("1.1.1").compare(Semver("1.1.1-rc.1")) == 1
82-
assert Semver("88.88.88").compare(Semver("88.88.88")) == 0
83-
assert Semver("1.2.3----RC-SNAPSHOT.12.9.1--.12").compare(Semver("1.2.3----RC-SNAPSHOT.12.9.1--.12")) == 0
84-
assert Semver("10.2.3-DEV-SNAPSHOT").compare(Semver("10.2.3-SNAPSHOT-123")) == -1
85-
86-
def _verify_version(self, semver, major, minor, patch, pre_release="", is_stable=True):
87-
assert semver._major == major
88-
assert semver._minor == minor
89-
assert semver._patch == patch
90-
assert semver._pre_release == pre_release
91-
assert semver._is_stable == is_stable
30+
with open(valid_versions) as csvfile:
31+
reader = csv.DictReader(csvfile)
32+
for row in reader:
33+
assert Semver.build(row['higher']).compare(Semver.build(row['lower'])) == 1
34+
assert Semver.build(row['lower']).compare(Semver.build(row['higher'])) == -1
35+
36+
with open(equalto_versions) as csvfile:
37+
reader = csv.DictReader(csvfile)
38+
for row in reader:
39+
version1 = Semver.build(row['version1'])
40+
version2 = Semver.build(row['version2'])
41+
if row['equals'] == "true":
42+
assert version1.version == version2.version
43+
else:
44+
assert version1.version != version2.version
45+
46+
with open(between_versions) as csvfile:
47+
reader = csv.DictReader(csvfile)
48+
for row in reader:
49+
version1 = Semver.build(row['version1'])
50+
version2 = Semver.build(row['version2'])
51+
version3 = Semver.build(row['version3'])
52+
if row['expected'] == "true":
53+
assert version2.compare(version1) >= 0 and version3.compare(version2) >= 0
54+
else:
55+
assert version2.compare(version1) < 0 or version3.compare(version2) < 0

0 commit comments

Comments
 (0)