addressable 2.3.5 → 2.3.6
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of addressable might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/CHANGELOG.md +11 -2
- data/Gemfile +9 -0
- data/README.md +1 -4
- data/lib/addressable/template.rb +37 -12
- data/lib/addressable/uri.rb +34 -20
- data/lib/addressable/version.rb +1 -1
- data/spec/addressable/template_spec.rb +214 -38
- data/spec/addressable/uri_spec.rb +119 -15
- data/spec/spec_helper.rb +6 -2
- data/tasks/rubyforge.rake +0 -16
- data/website/index.html +2 -2
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: c062f20a75939191f680842716b9ce79816e8952
|
4
|
+
data.tar.gz: 4ff3027264ee6f61fe887f1035c4fa7c472f7c90
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 26da95b6a6dd459054e700fa3ff906fbc5512dcc0ad2b3cb47e0b5a1a05d2722767605b8f62f044534425ffa4485a53e8132a816792136b37e80c3ff0c20bfbf
|
7
|
+
data.tar.gz: 9a0d4766e4faeb57353a6d14524e31610e77b84dd9dda33d51ba472db803197cc2989f3c6dc08623ebbc8e95850e331d8a065b9483483a8e78223c3887381283
|
data/CHANGELOG.md
CHANGED
@@ -1,3 +1,12 @@
|
|
1
|
+
# Addressable 2.3.6
|
2
|
+
- normalization drops empty query string
|
3
|
+
- better handling in template extract for missing values
|
4
|
+
- template modifier for `'?'` now treated as optional
|
5
|
+
- fixed issue where character class parameters were modified
|
6
|
+
- templates can now be tested for equality
|
7
|
+
- added `:sorted` option to normalization of query strings
|
8
|
+
- fixed issue with normalization of hosts given in `'example.com.'` form
|
9
|
+
|
1
10
|
# Addressable 2.3.5
|
2
11
|
- added Addressable::URI#empty? method
|
3
12
|
- Addressable::URI#hostname methods now strip square brackets from IPv6 hosts
|
@@ -149,11 +158,11 @@
|
|
149
158
|
- improved normalization
|
150
159
|
- fixed bug in joining algorithm
|
151
160
|
- updated specifications
|
152
|
-
|
161
|
+
|
153
162
|
# Addressable 0.1.1
|
154
163
|
- updated documentation
|
155
164
|
- added URI Template variable extraction
|
156
|
-
|
165
|
+
|
157
166
|
# Addressable 0.1.0
|
158
167
|
- initial release
|
159
168
|
- implementation based on RFC 3986, 3987
|
data/Gemfile
CHANGED
data/README.md
CHANGED
@@ -98,8 +98,5 @@ idn gem:
|
|
98
98
|
```console
|
99
99
|
$ sudo apt-get install idn # Debian/Ubuntu
|
100
100
|
$ sudo brew install libidn # OS X
|
101
|
-
$ sudo gem install idn
|
101
|
+
$ sudo gem install idn-ruby
|
102
102
|
```
|
103
|
-
|
104
|
-
**NOTE:** Native IDN support appears to be broken in Ruby 1.9.x. The IDN gem
|
105
|
-
hasn't been updated in years.
|
data/lib/addressable/template.rb
CHANGED
@@ -250,6 +250,26 @@ module Addressable
|
|
250
250
|
self.class.to_s, self.object_id, self.pattern)
|
251
251
|
end
|
252
252
|
|
253
|
+
##
|
254
|
+
# Returns <code>true</code> if the Template objects are equal. This method
|
255
|
+
# does NOT normalize either Template before doing the comparison.
|
256
|
+
#
|
257
|
+
# @param [Object] template The Template to compare.
|
258
|
+
#
|
259
|
+
# @return [TrueClass, FalseClass]
|
260
|
+
# <code>true</code> if the Templates are equivalent, <code>false</code>
|
261
|
+
# otherwise.
|
262
|
+
def ==(template)
|
263
|
+
return false unless template.kind_of?(Template)
|
264
|
+
return self.pattern == template.pattern
|
265
|
+
end
|
266
|
+
|
267
|
+
##
|
268
|
+
# Addressable::Template makes no distinction between `==` and `eql?`.
|
269
|
+
#
|
270
|
+
# @see #==
|
271
|
+
alias_method :eql?, :==
|
272
|
+
|
253
273
|
##
|
254
274
|
# Extracts a mapping from the URI using a URI Template pattern.
|
255
275
|
#
|
@@ -397,6 +417,7 @@ module Addressable
|
|
397
417
|
_, operator, varlist = *expansion.match(EXPRESSION)
|
398
418
|
varlist.split(',').each do |varspec|
|
399
419
|
_, name, modifier = *varspec.match(VARSPEC)
|
420
|
+
mapping[name] ||= nil
|
400
421
|
case operator
|
401
422
|
when nil, '+', '#', '/', '.'
|
402
423
|
unparsed_value = unparsed_values[index]
|
@@ -405,12 +426,14 @@ module Addressable
|
|
405
426
|
value = value.split(JOINERS[operator]) if value && modifier == '*'
|
406
427
|
when ';', '?', '&'
|
407
428
|
if modifier == '*'
|
408
|
-
|
409
|
-
|
410
|
-
|
411
|
-
|
412
|
-
|
413
|
-
|
429
|
+
if unparsed_values[index]
|
430
|
+
value = unparsed_values[index].split(JOINERS[operator])
|
431
|
+
value = value.inject({}) do |acc, v|
|
432
|
+
key, val = v.split('=')
|
433
|
+
val = "" if val.nil?
|
434
|
+
acc[key] = val
|
435
|
+
acc
|
436
|
+
end
|
414
437
|
end
|
415
438
|
else
|
416
439
|
if (unparsed_values[index])
|
@@ -435,10 +458,9 @@ module Addressable
|
|
435
458
|
value = Addressable::URI.unencode_component(value)
|
436
459
|
end
|
437
460
|
end
|
438
|
-
if mapping
|
461
|
+
if !mapping.has_key?(name) || mapping[name].nil?
|
462
|
+
# Doesn't exist, set to value (even if value is nil)
|
439
463
|
mapping[name] = value
|
440
|
-
else
|
441
|
-
return nil
|
442
464
|
end
|
443
465
|
index = index + 1
|
444
466
|
end
|
@@ -872,10 +894,12 @@ module Addressable
|
|
872
894
|
_, operator, varlist = *expansion.match(EXPRESSION)
|
873
895
|
leader = Regexp.escape(LEADERS.fetch(operator, ''))
|
874
896
|
joiner = Regexp.escape(JOINERS.fetch(operator, ','))
|
875
|
-
|
897
|
+
combined = varlist.split(',').map do |varspec|
|
876
898
|
_, name, modifier = *varspec.match(VARSPEC)
|
877
|
-
|
878
|
-
|
899
|
+
|
900
|
+
result = processor && processor.respond_to?(:match) ? processor.match(name) : nil
|
901
|
+
if result
|
902
|
+
"(#{ result })"
|
879
903
|
else
|
880
904
|
group = case operator
|
881
905
|
when '+'
|
@@ -902,6 +926,7 @@ module Addressable
|
|
902
926
|
end
|
903
927
|
end
|
904
928
|
end.join("#{joiner}?")
|
929
|
+
"(?:|#{leader}#{combined})"
|
905
930
|
end
|
906
931
|
|
907
932
|
# Ensure that the regular expression matches the whole URI.
|
data/lib/addressable/uri.rb
CHANGED
@@ -162,6 +162,15 @@ module Addressable
|
|
162
162
|
return nil unless uri
|
163
163
|
# If a URI object is passed, just return itself.
|
164
164
|
return uri.dup if uri.kind_of?(self)
|
165
|
+
|
166
|
+
# If a URI object of the Ruby standard library variety is passed,
|
167
|
+
# convert it to a string, then parse the string.
|
168
|
+
# We do the check this way because we don't want to accidentally
|
169
|
+
# cause a missing constant exception to be thrown.
|
170
|
+
if uri.class.name =~ /^URI\b/
|
171
|
+
uri = uri.to_s
|
172
|
+
end
|
173
|
+
|
165
174
|
if !uri.respond_to?(:to_str)
|
166
175
|
raise TypeError, "Can't convert #{uri.class} into String."
|
167
176
|
end
|
@@ -415,8 +424,13 @@ module Addressable
|
|
415
424
|
"Expected Class (String or Addressable::URI), " +
|
416
425
|
"got #{return_type.inspect}"
|
417
426
|
end
|
418
|
-
|
427
|
+
uri = uri.dup
|
428
|
+
# Seriously, only use UTF-8. I'm really not kidding!
|
429
|
+
uri.force_encoding("utf-8") if uri.respond_to?(:force_encoding)
|
430
|
+
leave_encoded.force_encoding("utf-8") if leave_encoded.respond_to?(:force_encoding)
|
431
|
+
result = uri.gsub(/%[0-9a-f]{2}/iu) do |sequence|
|
419
432
|
c = sequence[1..3].to_i(16).chr
|
433
|
+
c.force_encoding("utf-8") if c.respond_to?(:force_encoding)
|
420
434
|
leave_encoded.include?(c) ? sequence : c
|
421
435
|
end
|
422
436
|
result.force_encoding("utf-8") if result.respond_to?(:force_encoding)
|
@@ -496,7 +510,7 @@ module Addressable
|
|
496
510
|
end
|
497
511
|
if character_class.kind_of?(String)
|
498
512
|
leave_re = if leave_encoded.length > 0
|
499
|
-
character_class
|
513
|
+
character_class = "#{character_class}%" unless character_class.include?('%')
|
500
514
|
|
501
515
|
"|%(?!#{leave_encoded.chars.map do |char|
|
502
516
|
seq = char.unpack('C*').map { |c| '%02x' % c }.join
|
@@ -522,6 +536,9 @@ module Addressable
|
|
522
536
|
rescue ArgumentError
|
523
537
|
encoded = self.encode_component(unencoded)
|
524
538
|
end
|
539
|
+
if encoded.respond_to?(:force_encoding)
|
540
|
+
encoded.force_encoding(Encoding::UTF_8)
|
541
|
+
end
|
525
542
|
return encoded
|
526
543
|
end
|
527
544
|
|
@@ -1049,8 +1066,8 @@ module Addressable
|
|
1049
1066
|
result = ::Addressable::IDNA.to_ascii(
|
1050
1067
|
URI.unencode_component(self.host.strip.downcase)
|
1051
1068
|
)
|
1052
|
-
if result[
|
1053
|
-
#
|
1069
|
+
if result =~ /[^\.]\.$/
|
1070
|
+
# Single trailing dots are unnecessary.
|
1054
1071
|
result = result[0...-1]
|
1055
1072
|
end
|
1056
1073
|
result
|
@@ -1449,20 +1466,16 @@ module Addressable
|
|
1449
1466
|
# The query component for this URI, normalized.
|
1450
1467
|
#
|
1451
1468
|
# @return [String] The query component, normalized.
|
1452
|
-
def normalized_query
|
1453
|
-
|
1454
|
-
|
1455
|
-
|
1456
|
-
|
1457
|
-
|
1458
|
-
|
1459
|
-
|
1460
|
-
|
1461
|
-
|
1462
|
-
'+'
|
1463
|
-
)
|
1464
|
-
end).join("&")
|
1465
|
-
end)
|
1469
|
+
def normalized_query(*flags)
|
1470
|
+
modified_query_class = Addressable::URI::CharacterClasses::QUERY.dup
|
1471
|
+
# Make sure possible key-value pair delimiters are escaped.
|
1472
|
+
modified_query_class.sub!("\\&", "").sub!("\\;", "")
|
1473
|
+
pairs = (self.query || "").split("&", -1)
|
1474
|
+
pairs.sort! if flags.include?(:sorted)
|
1475
|
+
component = (pairs.map do |pair|
|
1476
|
+
Addressable::URI.normalize_component(pair, modified_query_class, "+")
|
1477
|
+
end).join("&")
|
1478
|
+
component == "" ? nil : component
|
1466
1479
|
end
|
1467
1480
|
|
1468
1481
|
##
|
@@ -1643,10 +1656,11 @@ module Addressable
|
|
1643
1656
|
# @return [String] The fragment component, normalized.
|
1644
1657
|
def normalized_fragment
|
1645
1658
|
self.fragment && @normalized_fragment ||= (begin
|
1646
|
-
Addressable::URI.normalize_component(
|
1647
|
-
self.fragment
|
1659
|
+
component = Addressable::URI.normalize_component(
|
1660
|
+
self.fragment,
|
1648
1661
|
Addressable::URI::CharacterClasses::FRAGMENT
|
1649
1662
|
)
|
1663
|
+
component == "" ? nil : component
|
1650
1664
|
end)
|
1651
1665
|
end
|
1652
1666
|
|
data/lib/addressable/version.rb
CHANGED
@@ -32,20 +32,72 @@ shared_examples_for 'expands' do |tests|
|
|
32
32
|
end
|
33
33
|
end
|
34
34
|
|
35
|
+
describe "eql?" do
|
36
|
+
let(:template) { Addressable::Template.new('https://www.example.com/{foo}') }
|
37
|
+
it 'is equal when the pattern matches' do
|
38
|
+
other_template = Addressable::Template.new('https://www.example.com/{foo}')
|
39
|
+
expect(template).to be_eql(other_template)
|
40
|
+
expect(other_template).to be_eql(template)
|
41
|
+
end
|
42
|
+
it 'is not equal when the pattern differs' do
|
43
|
+
other_template = Addressable::Template.new('https://www.example.com/{bar}')
|
44
|
+
expect(template).to_not be_eql(other_template)
|
45
|
+
expect(other_template).to_not be_eql(template)
|
46
|
+
end
|
47
|
+
it 'is not equal to non-templates' do
|
48
|
+
uri = 'https://www.example.com/foo/bar'
|
49
|
+
addressable_template = Addressable::Template.new uri
|
50
|
+
addressable_uri = Addressable::URI.parse uri
|
51
|
+
expect(addressable_template).to_not be_eql(addressable_uri)
|
52
|
+
expect(addressable_uri).to_not be_eql(addressable_template)
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
describe "==" do
|
57
|
+
let(:template) { Addressable::Template.new('https://www.example.com/{foo}') }
|
58
|
+
it 'is equal when the pattern matches' do
|
59
|
+
other_template = Addressable::Template.new('https://www.example.com/{foo}')
|
60
|
+
expect(template).should == other_template
|
61
|
+
expect(other_template).should == template
|
62
|
+
end
|
63
|
+
it 'is not equal when the pattern differs' do
|
64
|
+
other_template = Addressable::Template.new('https://www.example.com/{bar}')
|
65
|
+
expect(template).should_not == other_template
|
66
|
+
expect(other_template).should_not == template
|
67
|
+
end
|
68
|
+
it 'is not equal to non-templates' do
|
69
|
+
uri = 'https://www.example.com/foo/bar'
|
70
|
+
addressable_template = Addressable::Template.new uri
|
71
|
+
addressable_uri = Addressable::URI.parse uri
|
72
|
+
expect(addressable_template).should_not == addressable_uri
|
73
|
+
expect(addressable_uri).should_not == addressable_template
|
74
|
+
end
|
75
|
+
end
|
76
|
+
|
35
77
|
describe "Type conversion" do
|
36
|
-
|
37
|
-
|
78
|
+
require "bigdecimal"
|
79
|
+
|
80
|
+
subject {
|
81
|
+
{
|
82
|
+
:var => true,
|
83
|
+
:hello => 1234,
|
84
|
+
:nothing => nil,
|
85
|
+
:sym => :symbolic,
|
86
|
+
:decimal => BigDecimal.new(1)
|
87
|
+
}
|
38
88
|
}
|
89
|
+
|
39
90
|
it_behaves_like 'expands', {
|
40
91
|
'{var}' => 'true',
|
41
92
|
'{hello}' => '1234',
|
42
93
|
'{nothing}' => '',
|
43
|
-
'{sym}' => 'symbolic'
|
94
|
+
'{sym}' => 'symbolic',
|
95
|
+
'{decimal}' => '0.1E1'
|
44
96
|
}
|
45
97
|
end
|
46
98
|
|
47
99
|
describe "Level 1:" do
|
48
|
-
subject{
|
100
|
+
subject {
|
49
101
|
{:var => "value", :hello => "Hello World!"}
|
50
102
|
}
|
51
103
|
it_behaves_like 'expands', {
|
@@ -55,7 +107,7 @@ describe "Level 1:" do
|
|
55
107
|
end
|
56
108
|
|
57
109
|
describe "Level 2" do
|
58
|
-
subject{
|
110
|
+
subject {
|
59
111
|
{
|
60
112
|
:var => "value",
|
61
113
|
:hello => "Hello World!",
|
@@ -79,7 +131,7 @@ describe "Level 2" do
|
|
79
131
|
end
|
80
132
|
|
81
133
|
describe "Level 3" do
|
82
|
-
subject{
|
134
|
+
subject {
|
83
135
|
{
|
84
136
|
:var => "value",
|
85
137
|
:hello => "Hello World!",
|
@@ -140,7 +192,7 @@ describe "Level 3" do
|
|
140
192
|
end
|
141
193
|
|
142
194
|
describe "Level 4" do
|
143
|
-
subject{
|
195
|
+
subject {
|
144
196
|
{
|
145
197
|
:var => "value",
|
146
198
|
:hello => "Hello World!",
|
@@ -338,7 +390,7 @@ describe "Level 4" do
|
|
338
390
|
end
|
339
391
|
end
|
340
392
|
describe "Modifiers" do
|
341
|
-
subject{
|
393
|
+
subject {
|
342
394
|
{
|
343
395
|
:var => "value",
|
344
396
|
:semi => ";",
|
@@ -363,7 +415,7 @@ describe "Modifiers" do
|
|
363
415
|
end
|
364
416
|
end
|
365
417
|
describe "Expansion" do
|
366
|
-
subject{
|
418
|
+
subject {
|
367
419
|
{
|
368
420
|
:count => ["one", "two", "three"],
|
369
421
|
:dom => ["example", "com"],
|
@@ -670,6 +722,11 @@ class ExampleTwoProcessor
|
|
670
722
|
end
|
671
723
|
end
|
672
724
|
|
725
|
+
class DumbProcessor
|
726
|
+
def self.match(name)
|
727
|
+
return ".*?" if name == "first"
|
728
|
+
end
|
729
|
+
end
|
673
730
|
|
674
731
|
describe Addressable::Template do
|
675
732
|
describe "Matching" do
|
@@ -687,54 +744,80 @@ describe Addressable::Template do
|
|
687
744
|
let(:uri4){
|
688
745
|
Addressable::URI.parse("http://example.com/?a=1&b=2&c=3&first=foo")
|
689
746
|
}
|
747
|
+
let(:uri5){
|
748
|
+
"http://example.com/foo"
|
749
|
+
}
|
690
750
|
context "first uri with ExampleTwoProcessor" do
|
691
|
-
subject{
|
751
|
+
subject {
|
692
752
|
match = Addressable::Template.new(
|
693
753
|
"http://example.com/search/{query}/"
|
694
754
|
).match(uri, ExampleTwoProcessor)
|
695
755
|
}
|
696
|
-
its(:variables){ should == ["query"]}
|
697
|
-
its(:captures){ should == ["an example search query"]}
|
756
|
+
its(:variables){ should == ["query"] }
|
757
|
+
its(:captures){ should == ["an example search query"] }
|
698
758
|
end
|
699
759
|
|
700
760
|
context "second uri with ExampleTwoProcessor" do
|
701
|
-
subject{
|
761
|
+
subject {
|
702
762
|
match = Addressable::Template.new(
|
703
763
|
"http://example.com/{first}/{+second}/"
|
704
764
|
).match(uri2, ExampleTwoProcessor)
|
705
765
|
}
|
706
|
-
its(:variables){ should == ["first", "second"]}
|
766
|
+
its(:variables){ should == ["first", "second"] }
|
767
|
+
its(:captures){ should == ["a", "b/c"] }
|
768
|
+
end
|
769
|
+
|
770
|
+
context "second uri with DumbProcessor" do
|
771
|
+
subject {
|
772
|
+
match = Addressable::Template.new(
|
773
|
+
"http://example.com/{first}/{+second}/"
|
774
|
+
).match(uri2, DumbProcessor)
|
775
|
+
}
|
776
|
+
its(:variables){ should == ["first", "second"] }
|
707
777
|
its(:captures){ should == ["a", "b/c"] }
|
708
778
|
end
|
779
|
+
|
709
780
|
context "second uri" do
|
710
|
-
subject{
|
781
|
+
subject {
|
711
782
|
match = Addressable::Template.new(
|
712
783
|
"http://example.com/{first}{/second*}/"
|
713
784
|
).match(uri2)
|
714
785
|
}
|
715
|
-
its(:variables){ should == ["first", "second"]}
|
786
|
+
its(:variables){ should == ["first", "second"] }
|
716
787
|
its(:captures){ should == ["a", ["b","c"]] }
|
717
788
|
end
|
718
789
|
context "third uri" do
|
719
|
-
subject{
|
790
|
+
subject {
|
720
791
|
match = Addressable::Template.new(
|
721
792
|
"http://example.com/{;hash*,first}"
|
722
793
|
).match(uri3)
|
723
794
|
}
|
724
|
-
its(:variables){ should == ["hash", "first"]}
|
795
|
+
its(:variables){ should == ["hash", "first"] }
|
725
796
|
its(:captures){ should == [
|
726
797
|
{"a" => "1", "b" => "2", "c" => "3", "first" => "foo"}, nil] }
|
727
798
|
end
|
799
|
+
# Note that this expansion is impossible to revert deterministically - the
|
800
|
+
# * operator means first could have been a key of hash or a separate key.
|
801
|
+
# Semantically, a separate key is more likely, but both are possible.
|
728
802
|
context "fourth uri" do
|
729
|
-
subject{
|
803
|
+
subject {
|
730
804
|
match = Addressable::Template.new(
|
731
805
|
"http://example.com/{?hash*,first}"
|
732
806
|
).match(uri4)
|
733
807
|
}
|
734
|
-
its(:variables){ should == ["hash", "first"]}
|
808
|
+
its(:variables){ should == ["hash", "first"] }
|
735
809
|
its(:captures){ should == [
|
736
810
|
{"a" => "1", "b" => "2", "c" => "3", "first"=> "foo"}, nil] }
|
737
811
|
end
|
812
|
+
context "fifth uri" do
|
813
|
+
subject {
|
814
|
+
match = Addressable::Template.new(
|
815
|
+
"http://example.com/{path}{?hash*,first}"
|
816
|
+
).match(uri5)
|
817
|
+
}
|
818
|
+
its(:variables){ should == ["path", "hash", "first"] }
|
819
|
+
its(:captures){ should == ["foo", nil, nil] }
|
820
|
+
end
|
738
821
|
end
|
739
822
|
describe "extract" do
|
740
823
|
let(:template) {
|
@@ -743,7 +826,8 @@ describe Addressable::Template do
|
|
743
826
|
)
|
744
827
|
}
|
745
828
|
let(:uri){ "http://example.com/a/b/c/?one=1&two=2#foo" }
|
746
|
-
|
829
|
+
let(:uri2){ "http://example.com/a/b/c/#foo" }
|
830
|
+
it "should be able to extract with queries" do
|
747
831
|
template.extract(uri).should == {
|
748
832
|
"host" => "example.com",
|
749
833
|
"segments" => %w(a b c),
|
@@ -753,10 +837,53 @@ describe Addressable::Template do
|
|
753
837
|
"fragment" => "foo"
|
754
838
|
}
|
755
839
|
end
|
840
|
+
it "should be able to extract without queries" do
|
841
|
+
template.extract(uri2).should == {
|
842
|
+
"host" => "example.com",
|
843
|
+
"segments" => %w(a b c),
|
844
|
+
"one" => nil,
|
845
|
+
"bogus" => nil,
|
846
|
+
"two" => nil,
|
847
|
+
"fragment" => "foo"
|
848
|
+
}
|
849
|
+
end
|
850
|
+
|
851
|
+
context "issue #137" do
|
852
|
+
subject { Addressable::Template.new('/path{?page,per_page}') }
|
853
|
+
|
854
|
+
it "can match empty" do
|
855
|
+
data = subject.extract("/path")
|
856
|
+
data["page"].should == nil
|
857
|
+
data["per_page"].should == nil
|
858
|
+
data.keys.sort.should == ['page', 'per_page']
|
859
|
+
end
|
860
|
+
|
861
|
+
it "can match first var" do
|
862
|
+
data = subject.extract("/path?page=1")
|
863
|
+
data["page"].should == "1"
|
864
|
+
data["per_page"].should == nil
|
865
|
+
data.keys.sort.should == ['page', 'per_page']
|
866
|
+
end
|
867
|
+
|
868
|
+
it "can match second var" do
|
869
|
+
data = subject.extract("/path?per_page=1")
|
870
|
+
data["page"].should == nil
|
871
|
+
data["per_page"].should == "1"
|
872
|
+
data.keys.sort.should == ['page', 'per_page']
|
873
|
+
end
|
874
|
+
|
875
|
+
it "can match both vars" do
|
876
|
+
data = subject.extract("/path?page=2&per_page=1")
|
877
|
+
data["page"].should == "2"
|
878
|
+
data["per_page"].should == "1"
|
879
|
+
data.keys.sort.should == ['page', 'per_page']
|
880
|
+
end
|
881
|
+
end
|
756
882
|
end
|
883
|
+
|
757
884
|
describe "Partial expand with symbols" do
|
758
885
|
context "partial_expand with two simple values" do
|
759
|
-
subject{
|
886
|
+
subject {
|
760
887
|
Addressable::Template.new("http://example.com/{one}/{two}/")
|
761
888
|
}
|
762
889
|
it "builds a new pattern" do
|
@@ -765,7 +892,7 @@ describe Addressable::Template do
|
|
765
892
|
end
|
766
893
|
end
|
767
894
|
context "partial_expand query with missing param in middle" do
|
768
|
-
subject{
|
895
|
+
subject {
|
769
896
|
Addressable::Template.new("http://example.com/{?one,two,three}/")
|
770
897
|
}
|
771
898
|
it "builds a new pattern" do
|
@@ -774,7 +901,7 @@ describe Addressable::Template do
|
|
774
901
|
end
|
775
902
|
end
|
776
903
|
context "partial_expand with query string" do
|
777
|
-
subject{
|
904
|
+
subject {
|
778
905
|
Addressable::Template.new("http://example.com/{?two,one}/")
|
779
906
|
}
|
780
907
|
it "builds a new pattern" do
|
@@ -783,7 +910,7 @@ describe Addressable::Template do
|
|
783
910
|
end
|
784
911
|
end
|
785
912
|
context "partial_expand with path operator" do
|
786
|
-
subject{
|
913
|
+
subject {
|
787
914
|
Addressable::Template.new("http://example.com{/one,two}/")
|
788
915
|
}
|
789
916
|
it "builds a new pattern" do
|
@@ -794,7 +921,7 @@ describe Addressable::Template do
|
|
794
921
|
end
|
795
922
|
describe "Partial expand with strings" do
|
796
923
|
context "partial_expand with two simple values" do
|
797
|
-
subject{
|
924
|
+
subject {
|
798
925
|
Addressable::Template.new("http://example.com/{one}/{two}/")
|
799
926
|
}
|
800
927
|
it "builds a new pattern" do
|
@@ -803,7 +930,7 @@ describe Addressable::Template do
|
|
803
930
|
end
|
804
931
|
end
|
805
932
|
context "partial_expand query with missing param in middle" do
|
806
|
-
subject{
|
933
|
+
subject {
|
807
934
|
Addressable::Template.new("http://example.com/{?one,two,three}/")
|
808
935
|
}
|
809
936
|
it "builds a new pattern" do
|
@@ -812,7 +939,7 @@ describe Addressable::Template do
|
|
812
939
|
end
|
813
940
|
end
|
814
941
|
context "partial_expand with query string" do
|
815
|
-
subject{
|
942
|
+
subject {
|
816
943
|
Addressable::Template.new("http://example.com/{?two,one}/")
|
817
944
|
}
|
818
945
|
it "builds a new pattern" do
|
@@ -821,7 +948,7 @@ describe Addressable::Template do
|
|
821
948
|
end
|
822
949
|
end
|
823
950
|
context "partial_expand with path operator" do
|
824
|
-
subject{
|
951
|
+
subject {
|
825
952
|
Addressable::Template.new("http://example.com{/one,two}/")
|
826
953
|
}
|
827
954
|
it "builds a new pattern" do
|
@@ -832,7 +959,7 @@ describe Addressable::Template do
|
|
832
959
|
end
|
833
960
|
describe "Expand" do
|
834
961
|
context "expand with a processor" do
|
835
|
-
subject{
|
962
|
+
subject {
|
836
963
|
Addressable::Template.new("http://example.com/search/{query}/")
|
837
964
|
}
|
838
965
|
it "processes spaces" do
|
@@ -848,7 +975,7 @@ describe Addressable::Template do
|
|
848
975
|
end
|
849
976
|
end
|
850
977
|
context "partial_expand query with missing param in middle" do
|
851
|
-
subject{
|
978
|
+
subject {
|
852
979
|
Addressable::Template.new("http://example.com/{?one,two,three}/")
|
853
980
|
}
|
854
981
|
it "builds a new pattern" do
|
@@ -857,7 +984,7 @@ describe Addressable::Template do
|
|
857
984
|
end
|
858
985
|
end
|
859
986
|
context "partial_expand with query string" do
|
860
|
-
subject{
|
987
|
+
subject {
|
861
988
|
Addressable::Template.new("http://example.com/{?two,one}/")
|
862
989
|
}
|
863
990
|
it "builds a new pattern" do
|
@@ -866,7 +993,7 @@ describe Addressable::Template do
|
|
866
993
|
end
|
867
994
|
end
|
868
995
|
context "partial_expand with path operator" do
|
869
|
-
subject{
|
996
|
+
subject {
|
870
997
|
Addressable::Template.new("http://example.com{/one,two}/")
|
871
998
|
}
|
872
999
|
it "builds a new pattern" do
|
@@ -889,8 +1016,8 @@ describe Addressable::Template do
|
|
889
1016
|
end
|
890
1017
|
it "can match empty" do
|
891
1018
|
data = subject.match("foo/baz")
|
892
|
-
data.mapping["foo"].should ==
|
893
|
-
data.mapping["bar"].should ==
|
1019
|
+
data.mapping["foo"].should == nil
|
1020
|
+
data.mapping["bar"].should == nil
|
894
1021
|
end
|
895
1022
|
it "lists vars" do
|
896
1023
|
subject.variables.should == ["foo", "bar"]
|
@@ -904,6 +1031,22 @@ describe Addressable::Template do
|
|
904
1031
|
data.mapping["foo"].should == "/test/banana"
|
905
1032
|
data.mapping["bar"].should == "baz"
|
906
1033
|
end
|
1034
|
+
it "can match empty level 2 #" do
|
1035
|
+
data = subject.match("foo/test/bananabaz")
|
1036
|
+
data.mapping["foo"].should == "/test/banana"
|
1037
|
+
data.mapping["bar"].should == nil
|
1038
|
+
data = subject.match("foo/test/banana#baz")
|
1039
|
+
data.mapping["foo"].should == "/test/banana"
|
1040
|
+
data.mapping["bar"].should == ""
|
1041
|
+
end
|
1042
|
+
it "can match empty level 2 +" do
|
1043
|
+
data = subject.match("foobaz")
|
1044
|
+
data.mapping["foo"].should == nil
|
1045
|
+
data.mapping["bar"].should == nil
|
1046
|
+
data = subject.match("foo#barbaz")
|
1047
|
+
data.mapping["foo"].should == nil
|
1048
|
+
data.mapping["bar"].should == "bar"
|
1049
|
+
end
|
907
1050
|
it "lists vars" do
|
908
1051
|
subject.variables.should == ["foo", "bar"]
|
909
1052
|
end
|
@@ -978,6 +1121,39 @@ describe Addressable::Template do
|
|
978
1121
|
subject.variables.should == %w(foo bar)
|
979
1122
|
end
|
980
1123
|
end
|
1124
|
+
|
1125
|
+
context "issue #137" do
|
1126
|
+
subject { Addressable::Template.new('/path{?page,per_page}') }
|
1127
|
+
|
1128
|
+
it "can match empty" do
|
1129
|
+
data = subject.match("/path")
|
1130
|
+
data.mapping["page"].should == nil
|
1131
|
+
data.mapping["per_page"].should == nil
|
1132
|
+
data.mapping.keys.sort.should == ['page', 'per_page']
|
1133
|
+
end
|
1134
|
+
|
1135
|
+
it "can match first var" do
|
1136
|
+
data = subject.match("/path?page=1")
|
1137
|
+
data.mapping["page"].should == "1"
|
1138
|
+
data.mapping["per_page"].should == nil
|
1139
|
+
data.mapping.keys.sort.should == ['page', 'per_page']
|
1140
|
+
end
|
1141
|
+
|
1142
|
+
it "can match second var" do
|
1143
|
+
data = subject.match("/path?per_page=1")
|
1144
|
+
data.mapping["page"].should == nil
|
1145
|
+
data.mapping["per_page"].should == "1"
|
1146
|
+
data.mapping.keys.sort.should == ['page', 'per_page']
|
1147
|
+
end
|
1148
|
+
|
1149
|
+
it "can match both vars" do
|
1150
|
+
data = subject.match("/path?page=2&per_page=1")
|
1151
|
+
data.mapping["page"].should == "2"
|
1152
|
+
data.mapping["per_page"].should == "1"
|
1153
|
+
data.mapping.keys.sort.should == ['page', 'per_page']
|
1154
|
+
end
|
1155
|
+
end
|
1156
|
+
|
981
1157
|
context "issue #71" do
|
982
1158
|
subject { Addressable::Template.new("http://cyberscore.dev/api/users{?username}") }
|
983
1159
|
it "can match" do
|
@@ -1084,10 +1260,10 @@ describe Addressable::Template::MatchData do
|
|
1084
1260
|
its(:template) { should == template }
|
1085
1261
|
its(:mapping) { should == { 'foo' => 'ab', 'bar' => 'cd' } }
|
1086
1262
|
its(:variables) { should == ['foo', 'bar'] }
|
1087
|
-
its(:keys) { should ==
|
1088
|
-
its(:names) { should ==
|
1263
|
+
its(:keys) { should == ['foo', 'bar'] }
|
1264
|
+
its(:names) { should == ['foo', 'bar'] }
|
1089
1265
|
its(:values) { should == ['ab', 'cd'] }
|
1090
|
-
its(:captures) { should ==
|
1266
|
+
its(:captures) { should == ['ab', 'cd'] }
|
1091
1267
|
its(:to_a) { should == ['ab/cd', 'ab', 'cd'] }
|
1092
1268
|
its(:to_s) { should == 'ab/cd' }
|
1093
1269
|
its(:string) { should == its.to_s }
|
@@ -17,6 +17,7 @@
|
|
17
17
|
require "spec_helper"
|
18
18
|
|
19
19
|
require "addressable/uri"
|
20
|
+
require "uri"
|
20
21
|
|
21
22
|
if !"".respond_to?("force_encoding")
|
22
23
|
class String
|
@@ -931,6 +932,17 @@ describe Addressable::URI, "when created with an authority and no port" do
|
|
931
932
|
end
|
932
933
|
end
|
933
934
|
|
935
|
+
describe Addressable::URI, "when created with a host with trailing dots" do
|
936
|
+
before do
|
937
|
+
@uri = Addressable::URI.new(:authority => "example...")
|
938
|
+
end
|
939
|
+
|
940
|
+
it "should have a stable normalized form" do
|
941
|
+
@uri.normalize.normalize.normalize.host.should ==
|
942
|
+
@uri.normalize.host
|
943
|
+
end
|
944
|
+
end
|
945
|
+
|
934
946
|
describe Addressable::URI, "when created with both a userinfo and a user" do
|
935
947
|
it "should raise an error" do
|
936
948
|
(lambda do
|
@@ -2019,6 +2031,38 @@ describe Addressable::URI, "when parsed from " +
|
|
2019
2031
|
end
|
2020
2032
|
end
|
2021
2033
|
|
2034
|
+
describe Addressable::URI, "when parsed from " +
|
2035
|
+
"'http://example.com?#'" do
|
2036
|
+
before do
|
2037
|
+
@uri = Addressable::URI.parse("http://example.com?#")
|
2038
|
+
end
|
2039
|
+
|
2040
|
+
it "should correctly convert to a hash" do
|
2041
|
+
@uri.to_hash.should == {
|
2042
|
+
:scheme => "http",
|
2043
|
+
:user => nil,
|
2044
|
+
:password => nil,
|
2045
|
+
:host => "example.com",
|
2046
|
+
:port => nil,
|
2047
|
+
:path => "",
|
2048
|
+
:query => "",
|
2049
|
+
:fragment => ""
|
2050
|
+
}
|
2051
|
+
end
|
2052
|
+
|
2053
|
+
it "should have a request URI of '/?'" do
|
2054
|
+
@uri.request_uri.should == "/?"
|
2055
|
+
end
|
2056
|
+
|
2057
|
+
it "should normalize to 'http://example.com/'" do
|
2058
|
+
@uri.normalize.to_s.should == "http://example.com/"
|
2059
|
+
end
|
2060
|
+
|
2061
|
+
it "should have an origin of 'http://example.com'" do
|
2062
|
+
@uri.origin.should == "http://example.com"
|
2063
|
+
end
|
2064
|
+
end
|
2065
|
+
|
2022
2066
|
describe Addressable::URI, "when parsed from " +
|
2023
2067
|
"'http://@example.com/'" do
|
2024
2068
|
before do
|
@@ -2136,7 +2180,7 @@ describe Addressable::URI, "when parsed from " +
|
|
2136
2180
|
it "should not raise an exception when normalized" do
|
2137
2181
|
(lambda do
|
2138
2182
|
@uri.normalize
|
2139
|
-
end).should_not raise_error
|
2183
|
+
end).should_not raise_error
|
2140
2184
|
end
|
2141
2185
|
|
2142
2186
|
it "should be considered to be in normal form" do
|
@@ -2188,7 +2232,7 @@ describe Addressable::URI, "when parsed from " +
|
|
2188
2232
|
it "should not raise an exception when normalized" do
|
2189
2233
|
(lambda do
|
2190
2234
|
@uri.normalize
|
2191
|
-
end).should_not raise_error
|
2235
|
+
end).should_not raise_error
|
2192
2236
|
end
|
2193
2237
|
|
2194
2238
|
it "should be considered to be in normal form" do
|
@@ -2212,7 +2256,7 @@ describe Addressable::URI, "when parsed from " +
|
|
2212
2256
|
it "should not raise an exception when normalized" do
|
2213
2257
|
(lambda do
|
2214
2258
|
@uri.normalize
|
2215
|
-
end).should_not raise_error
|
2259
|
+
end).should_not raise_error
|
2216
2260
|
end
|
2217
2261
|
|
2218
2262
|
it "should be considered to be in normal form" do
|
@@ -2589,7 +2633,7 @@ describe Addressable::URI, "when parsed from " +
|
|
2589
2633
|
end
|
2590
2634
|
|
2591
2635
|
it "should normalize to 'http://example.com/'" do
|
2592
|
-
@uri.normalize.should
|
2636
|
+
@uri.normalize.to_s.should == "http://example.com/"
|
2593
2637
|
end
|
2594
2638
|
|
2595
2639
|
it "should have an origin of 'http://example.com'" do
|
@@ -2597,6 +2641,31 @@ describe Addressable::URI, "when parsed from " +
|
|
2597
2641
|
end
|
2598
2642
|
end
|
2599
2643
|
|
2644
|
+
describe Addressable::URI, "when parsed from " +
|
2645
|
+
"'http://example.com/%2E/'" do
|
2646
|
+
before do
|
2647
|
+
@uri = Addressable::URI.parse("http://example.com/%2E/")
|
2648
|
+
end
|
2649
|
+
|
2650
|
+
it "should be considered to be in normal form" do
|
2651
|
+
pending(
|
2652
|
+
'path segment normalization should happen before ' +
|
2653
|
+
'percent escaping normalization'
|
2654
|
+
) do
|
2655
|
+
@uri.normalize.should be_eql(@uri)
|
2656
|
+
end
|
2657
|
+
end
|
2658
|
+
|
2659
|
+
it "should normalize to 'http://example.com/%2E/'" do
|
2660
|
+
pending(
|
2661
|
+
'path segment normalization should happen before ' +
|
2662
|
+
'percent escaping normalization'
|
2663
|
+
) do
|
2664
|
+
@uri.normalize.should == "http://example.com/%2E/"
|
2665
|
+
end
|
2666
|
+
end
|
2667
|
+
end
|
2668
|
+
|
2600
2669
|
describe Addressable::URI, "when parsed from " +
|
2601
2670
|
"'http://example.com/..'" do
|
2602
2671
|
before do
|
@@ -2612,7 +2681,7 @@ describe Addressable::URI, "when parsed from " +
|
|
2612
2681
|
end
|
2613
2682
|
|
2614
2683
|
it "should normalize to 'http://example.com/'" do
|
2615
|
-
@uri.normalize.should
|
2684
|
+
@uri.normalize.to_s.should == "http://example.com/"
|
2616
2685
|
end
|
2617
2686
|
end
|
2618
2687
|
|
@@ -2631,7 +2700,7 @@ describe Addressable::URI, "when parsed from " +
|
|
2631
2700
|
end
|
2632
2701
|
|
2633
2702
|
it "should normalize to 'http://example.com/'" do
|
2634
|
-
@uri.normalize.should
|
2703
|
+
@uri.normalize.to_s.should == "http://example.com/"
|
2635
2704
|
end
|
2636
2705
|
end
|
2637
2706
|
|
@@ -2650,7 +2719,7 @@ describe Addressable::URI, "when parsed from " +
|
|
2650
2719
|
end
|
2651
2720
|
|
2652
2721
|
it "should normalize to 'http://example.com/'" do
|
2653
|
-
@uri.normalize.should
|
2722
|
+
@uri.normalize.to_s.should == "http://example.com/"
|
2654
2723
|
end
|
2655
2724
|
end
|
2656
2725
|
|
@@ -2669,7 +2738,7 @@ describe Addressable::URI, "when parsed from " +
|
|
2669
2738
|
end
|
2670
2739
|
|
2671
2740
|
it "should normalize to 'http://example.com/'" do
|
2672
|
-
@uri.normalize.should
|
2741
|
+
@uri.normalize.to_s.should == "http://example.com/"
|
2673
2742
|
end
|
2674
2743
|
end
|
2675
2744
|
|
@@ -2688,7 +2757,7 @@ describe Addressable::URI, "when parsed from " +
|
|
2688
2757
|
end
|
2689
2758
|
|
2690
2759
|
it "should normalize to 'http://example.com/'" do
|
2691
|
-
@uri.normalize.should
|
2760
|
+
@uri.normalize.to_s.should == "http://example.com/"
|
2692
2761
|
end
|
2693
2762
|
end
|
2694
2763
|
|
@@ -2707,7 +2776,7 @@ describe Addressable::URI, "when parsed from " +
|
|
2707
2776
|
end
|
2708
2777
|
|
2709
2778
|
it "should normalize to 'http://example.com/'" do
|
2710
|
-
@uri.normalize.should
|
2779
|
+
@uri.normalize.to_s.should == "http://example.com/"
|
2711
2780
|
end
|
2712
2781
|
end
|
2713
2782
|
|
@@ -2722,7 +2791,7 @@ describe Addressable::URI, "when parsed from '/a/b/c/./../../g'" do
|
|
2722
2791
|
|
2723
2792
|
# Section 5.2.4 of RFC 3986
|
2724
2793
|
it "should normalize to '/a/g'" do
|
2725
|
-
@uri.normalize.should
|
2794
|
+
@uri.normalize.to_s.should == "/a/g"
|
2726
2795
|
end
|
2727
2796
|
end
|
2728
2797
|
|
@@ -2737,7 +2806,7 @@ describe Addressable::URI, "when parsed from 'mid/content=5/../6'" do
|
|
2737
2806
|
|
2738
2807
|
# Section 5.2.4 of RFC 3986
|
2739
2808
|
it "should normalize to 'mid/6'" do
|
2740
|
-
@uri.normalize.should
|
2809
|
+
@uri.normalize.to_s.should == "mid/6"
|
2741
2810
|
end
|
2742
2811
|
end
|
2743
2812
|
|
@@ -2752,7 +2821,7 @@ describe Addressable::URI, "when parsed from " +
|
|
2752
2821
|
end
|
2753
2822
|
|
2754
2823
|
it "should normalize to 'http://www.example.com//'" do
|
2755
|
-
@uri.normalize.should
|
2824
|
+
@uri.normalize.to_s.should == "http://www.example.com//"
|
2756
2825
|
end
|
2757
2826
|
end
|
2758
2827
|
|
@@ -4346,6 +4415,10 @@ describe Addressable::URI, "when parsed from '?'" do
|
|
4346
4415
|
@uri = Addressable::URI.parse("?")
|
4347
4416
|
end
|
4348
4417
|
|
4418
|
+
it "should normalize to ''" do
|
4419
|
+
@uri.normalize.to_s.should == ""
|
4420
|
+
end
|
4421
|
+
|
4349
4422
|
it "should have the correct return type" do
|
4350
4423
|
@uri.query_values.should == {}
|
4351
4424
|
@uri.query_values(Hash).should == {}
|
@@ -4490,6 +4563,11 @@ describe Addressable::URI, "when parsed from " +
|
|
4490
4563
|
{'one' => ['two', 'three', 'four']}
|
4491
4564
|
end
|
4492
4565
|
end
|
4566
|
+
|
4567
|
+
it "should handle assignment with keys of mixed type" do
|
4568
|
+
@uri.query_values = @uri.query_values(Hash).merge({:one => 'three'})
|
4569
|
+
@uri.query_values(Hash).should == {'one' => 'three'}
|
4570
|
+
end
|
4493
4571
|
end
|
4494
4572
|
|
4495
4573
|
describe Addressable::URI, "when parsed from " +
|
@@ -5335,6 +5413,16 @@ describe Addressable::URI, "when normalizing a string but leaving some character
|
|
5335
5413
|
Addressable::URI.normalize_component("%58X%59Y%5AZ", "0-9a-zXY", "Y").should ==
|
5336
5414
|
"XX%59Y%5A%5A"
|
5337
5415
|
end
|
5416
|
+
|
5417
|
+
it "should not modify the character class" do
|
5418
|
+
character_class = "0-9a-zXY"
|
5419
|
+
|
5420
|
+
character_class_copy = character_class.dup
|
5421
|
+
|
5422
|
+
Addressable::URI.normalize_component("%58X%59Y%5AZ", character_class, "Y")
|
5423
|
+
|
5424
|
+
character_class.should == character_class_copy
|
5425
|
+
end
|
5338
5426
|
end
|
5339
5427
|
|
5340
5428
|
describe Addressable::URI, "when encoding a string with existing encodings to upcase" do
|
@@ -5379,6 +5467,10 @@ describe Addressable::URI, "when unencoding a multibyte string" do
|
|
5379
5467
|
Addressable::URI.unencode_component("g%C3%BCnther").should == "günther"
|
5380
5468
|
end
|
5381
5469
|
|
5470
|
+
it "should consistently use UTF-8 internally" do
|
5471
|
+
Addressable::URI.unencode_component("ski=%BA%DAɫ").should == "ski=\xBA\xDAɫ"
|
5472
|
+
end
|
5473
|
+
|
5382
5474
|
it "should result in correct percent encoded sequence as a URI" do
|
5383
5475
|
Addressable::URI.unencode(
|
5384
5476
|
"/path?g%C3%BCnther", ::Addressable::URI
|
@@ -5642,6 +5734,18 @@ describe Addressable::URI, "when given the input " +
|
|
5642
5734
|
end
|
5643
5735
|
end
|
5644
5736
|
|
5737
|
+
describe Addressable::URI, "when given the input " +
|
5738
|
+
"::URI.parse('http://example.com')" do
|
5739
|
+
before do
|
5740
|
+
@input = ::URI.parse('http://example.com')
|
5741
|
+
end
|
5742
|
+
|
5743
|
+
it "should heuristically parse to 'http://example.com'" do
|
5744
|
+
@uri = Addressable::URI.heuristic_parse(@input)
|
5745
|
+
@uri.to_s.should == "http://example.com"
|
5746
|
+
end
|
5747
|
+
end
|
5748
|
+
|
5645
5749
|
describe Addressable::URI, "when assigning query values" do
|
5646
5750
|
before do
|
5647
5751
|
@uri = Addressable::URI.new
|
@@ -5753,7 +5857,7 @@ describe Addressable::URI, "when assigning query values" do
|
|
5753
5857
|
describe 'when a hash with mixed types is assigned to query_values' do
|
5754
5858
|
it 'should not raise an error' do
|
5755
5859
|
pending 'Issue #94' do
|
5756
|
-
expect { subject.query_values = { "page" => "1", :page => 2 } }.to_not raise_error
|
5860
|
+
expect { subject.query_values = { "page" => "1", :page => 2 } }.to_not raise_error
|
5757
5861
|
end
|
5758
5862
|
end
|
5759
5863
|
end
|
@@ -5805,7 +5909,7 @@ describe Addressable::URI, "when assigning path values" do
|
|
5805
5909
|
(lambda do
|
5806
5910
|
@uri.path = "uuid:0b3ecf60-3f93-11df-a9c3-001f5bfffe12"
|
5807
5911
|
@uri.scheme = "urn"
|
5808
|
-
end).should_not raise_error
|
5912
|
+
end).should_not raise_error
|
5809
5913
|
end
|
5810
5914
|
end
|
5811
5915
|
|
data/spec/spec_helper.rb
CHANGED
data/tasks/rubyforge.rake
CHANGED
@@ -24,22 +24,6 @@ namespace :gem do
|
|
24
24
|
end
|
25
25
|
end
|
26
26
|
|
27
|
-
namespace :doc do
|
28
|
-
desc "Publish RDoc to RubyForge"
|
29
|
-
task :release => ["doc"] do
|
30
|
-
require "rake/contrib/sshpublisher"
|
31
|
-
require "yaml"
|
32
|
-
|
33
|
-
config = YAML.load(
|
34
|
-
File.read(File.expand_path('~/.rubyforge/user-config.yml'))
|
35
|
-
)
|
36
|
-
host = "#{config['username']}@rubyforge.org"
|
37
|
-
remote_dir = RUBY_FORGE_PATH + "/api"
|
38
|
-
local_dir = "doc"
|
39
|
-
Rake::SshDirPublisher.new(host, remote_dir, local_dir).upload
|
40
|
-
end
|
41
|
-
end
|
42
|
-
|
43
27
|
namespace :spec do
|
44
28
|
desc "Publish specdoc to RubyForge"
|
45
29
|
task :release => ["spec:specdoc"] do
|
data/website/index.html
CHANGED
@@ -78,11 +78,11 @@
|
|
78
78
|
</a>
|
79
79
|
</li>
|
80
80
|
<li>
|
81
|
-
<a href="http://github.com/sporkmonger/addressable
|
81
|
+
<a href="http://github.com/sporkmonger/addressable">
|
82
82
|
GitHub Page
|
83
83
|
</a>
|
84
84
|
</li>
|
85
|
-
<li><a href="/
|
85
|
+
<li><a href="http://rubydoc.info/gems/addressable">API</a></li>
|
86
86
|
<li><a href="/specdoc/">Specifications</a></li>
|
87
87
|
<li><a href="/coverage/">Code Coverage</a></li>
|
88
88
|
</ul>
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: addressable
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.3.
|
4
|
+
version: 2.3.6
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Bob Aman
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2014-03-24 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rake
|