diff --git a/lib/vers/parser.rb b/lib/vers/parser.rb index dc68d32..ceef528 100644 --- a/lib/vers/parser.rb +++ b/lib/vers/parser.rb @@ -66,7 +66,7 @@ def parse(vers_string, require_canonical_order: false) unless vers_string.is_a?(String) && vers_string.start_with?("vers:") raise ArgumentError, "Invalid vers URI format: #{vers_string}" end - if vers_string.match?(/[ \t\r\n]/) + if vers_string.match?(/[\t\r\n]/) || (require_canonical_order && vers_string.include?(" ")) raise ArgumentError, "non-canonical VERS: whitespace is not permitted" end @@ -82,9 +82,13 @@ def parse(vers_string, require_canonical_order: false) end scheme = Scheme.canonical(raw_scheme) constraints_string = remainder[(slash + 1)..] - if constraints_string.empty? || constraints_string == "*" + if constraints_string.empty? + if require_canonical_order + raise ArgumentError, "non-canonical VERS: constraints must not be empty" + end return VersionRange.unbounded(scheme: scheme) end + return VersionRange.unbounded(scheme: scheme) if constraints_string == "*" validate_vers_constraints!(constraints_string, scheme, require_canonical_order) @@ -279,6 +283,9 @@ def validate_vers_version!(version, scheme) if lowercase_ascii_hex?(first) || lowercase_ascii_hex?(second) raise ArgumentError, "non-canonical VERS: percent-encoding in version is not canonical" end + if first == 48 && [57, 65, 66, 67, 68].include?(second) + raise ArgumentError, "non-canonical VERS: whitespace is not permitted" + end index += 3 end diff --git a/lib/vers/special_version.rb b/lib/vers/special_version.rb index d46043c..9e45307 100644 --- a/lib/vers/special_version.rb +++ b/lib/vers/special_version.rb @@ -289,8 +289,8 @@ module IntDotVersion extend self def compare(left, right) - left_parts = left.to_s.split(".", -1) - right_parts = right.to_s.split(".", -1) + left_parts = left.to_s[/\A[\d.]*/].split(".", -1) + right_parts = right.to_s[/\A[\d.]*/].split(".", -1) [left_parts.length, right_parts.length].max.times do |index| comparison = VersionComparison.compare_numbers(left_parts[index], right_parts[index]) diff --git a/test/test_range_conformance.rb b/test/test_range_conformance.rb index f3fef39..f580197 100644 --- a/test/test_range_conformance.rb +++ b/test/test_range_conformance.rb @@ -44,8 +44,8 @@ class TestRangeConformance < Minitest::Test when "parse" range = Vers::Parser.new.parse(test_case.fetch("input"), require_canonical_order: true) { - "scheme" => range.scheme, - "version_constraints" => range_constraints(range) + "type" => range.scheme, + "constraints" => range_constraints(range) } when "validate" range = Vers.parse(test_case.fetch("input")) diff --git a/test/vers-spec b/test/vers-spec index 93ff155..ec1a0c8 160000 --- a/test/vers-spec +++ b/test/vers-spec @@ -1 +1 @@ -Subproject commit 93ff155247ea34986e76476556ba46c31f3bed69 +Subproject commit ec1a0c8143b105a054b0f7cb1feb368b85c9c781