fields-addressable 2.2.3.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/CHANGELOG +106 -0
- data/LICENSE +20 -0
- data/README +60 -0
- data/Rakefile +42 -0
- data/lib/addressable/idna.rb +4871 -0
- data/lib/addressable/template.rb +1049 -0
- data/lib/addressable/uri.rb +2291 -0
- data/lib/addressable/version.rb +36 -0
- data/spec/addressable/idna_spec.rb +194 -0
- data/spec/addressable/template_spec.rb +2152 -0
- data/spec/addressable/uri_spec.rb +4566 -0
- data/tasks/clobber.rake +2 -0
- data/tasks/gem.rake +84 -0
- data/tasks/git.rake +40 -0
- data/tasks/metrics.rake +22 -0
- data/tasks/rdoc.rake +26 -0
- data/tasks/rubyforge.rake +89 -0
- data/tasks/spec.rake +47 -0
- data/tasks/yard.rake +26 -0
- data/website/index.html +110 -0
- metadata +149 -0
@@ -0,0 +1,36 @@
|
|
1
|
+
# encoding:utf-8
|
2
|
+
#--
|
3
|
+
# Addressable, Copyright (c) 2006-2010 Bob Aman
|
4
|
+
#
|
5
|
+
# Permission is hereby granted, free of charge, to any person obtaining
|
6
|
+
# a copy of this software and associated documentation files (the
|
7
|
+
# "Software"), to deal in the Software without restriction, including
|
8
|
+
# without limitation the rights to use, copy, modify, merge, publish,
|
9
|
+
# distribute, sublicense, and/or sell copies of the Software, and to
|
10
|
+
# permit persons to whom the Software is furnished to do so, subject to
|
11
|
+
# the following conditions:
|
12
|
+
#
|
13
|
+
# The above copyright notice and this permission notice shall be
|
14
|
+
# included in all copies or substantial portions of the Software.
|
15
|
+
#
|
16
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
18
|
+
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
20
|
+
# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
21
|
+
# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
22
|
+
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
23
|
+
#++
|
24
|
+
|
25
|
+
# Used to prevent the class/module from being loaded more than once
|
26
|
+
if !defined?(Addressable::VERSION)
|
27
|
+
module Addressable
|
28
|
+
module VERSION #:nodoc:
|
29
|
+
MAJOR = 2
|
30
|
+
MINOR = 2
|
31
|
+
TINY = 4
|
32
|
+
|
33
|
+
STRING = [MAJOR, MINOR, TINY].join('.')
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -0,0 +1,194 @@
|
|
1
|
+
# encoding:utf-8
|
2
|
+
#--
|
3
|
+
# Addressable, Copyright (c) 2006-2007 Bob Aman
|
4
|
+
#
|
5
|
+
# Permission is hereby granted, free of charge, to any person obtaining
|
6
|
+
# a copy of this software and associated documentation files (the
|
7
|
+
# "Software"), to deal in the Software without restriction, including
|
8
|
+
# without limitation the rights to use, copy, modify, merge, publish,
|
9
|
+
# distribute, sublicense, and/or sell copies of the Software, and to
|
10
|
+
# permit persons to whom the Software is furnished to do so, subject to
|
11
|
+
# the following conditions:
|
12
|
+
#
|
13
|
+
# The above copyright notice and this permission notice shall be
|
14
|
+
# included in all copies or substantial portions of the Software.
|
15
|
+
#
|
16
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
18
|
+
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
20
|
+
# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
21
|
+
# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
22
|
+
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
23
|
+
#++
|
24
|
+
|
25
|
+
require "addressable/idna"
|
26
|
+
|
27
|
+
describe Addressable::IDNA, "when converting from unicode to ASCII" do
|
28
|
+
it "should convert 'www.google.com' correctly" do
|
29
|
+
Addressable::IDNA.to_ascii("www.google.com").should == "www.google.com"
|
30
|
+
end
|
31
|
+
|
32
|
+
it "should convert 'www.詹姆斯.com' correctly" do
|
33
|
+
Addressable::IDNA.to_ascii(
|
34
|
+
"www.詹姆斯.com"
|
35
|
+
).should == "www.xn--8ws00zhy3a.com"
|
36
|
+
end
|
37
|
+
|
38
|
+
it "should convert 'www.Iñtërnâtiônàlizætiøn.com' correctly" do
|
39
|
+
"www.Iñtërnâtiônàlizætiøn.com"
|
40
|
+
Addressable::IDNA.to_ascii(
|
41
|
+
"www.I\xC3\xB1t\xC3\xABrn\xC3\xA2ti\xC3\xB4" +
|
42
|
+
"n\xC3\xA0liz\xC3\xA6ti\xC3\xB8n.com"
|
43
|
+
).should == "www.xn--itrntinliztin-vdb0a5exd8ewcye.com"
|
44
|
+
end
|
45
|
+
|
46
|
+
it "should convert 'www.Iñtërnâtiônàlizætiøn.com' correctly" do
|
47
|
+
Addressable::IDNA.to_ascii(
|
48
|
+
"www.In\xCC\x83te\xCC\x88rna\xCC\x82tio\xCC\x82n" +
|
49
|
+
"a\xCC\x80liz\xC3\xA6ti\xC3\xB8n.com"
|
50
|
+
).should == "www.xn--itrntinliztin-vdb0a5exd8ewcye.com"
|
51
|
+
end
|
52
|
+
|
53
|
+
it "should convert " +
|
54
|
+
"'www.ほんとうにながいわけのわからないどめいんめいのらべるまだながくしないとたりない.w3.mag.keio.ac.jp' " +
|
55
|
+
"correctly" do
|
56
|
+
Addressable::IDNA.to_ascii(
|
57
|
+
"www.\343\201\273\343\202\223\343\201\250\343\201\206\343\201\253\343" +
|
58
|
+
"\201\252\343\201\214\343\201\204\343\202\217\343\201\221\343\201\256" +
|
59
|
+
"\343\202\217\343\201\213\343\202\211\343\201\252\343\201\204\343\201" +
|
60
|
+
"\251\343\202\201\343\201\204\343\202\223\343\202\201\343\201\204\343" +
|
61
|
+
"\201\256\343\202\211\343\201\271\343\202\213\343\201\276\343\201\240" +
|
62
|
+
"\343\201\252\343\201\214\343\201\217\343\201\227\343\201\252\343\201" +
|
63
|
+
"\204\343\201\250\343\201\237\343\202\212\343\201\252\343\201\204." +
|
64
|
+
"w3.mag.keio.ac.jp"
|
65
|
+
).should ==
|
66
|
+
"www.xn--n8jaaaaai5bhf7as8fsfk3jnknefdde3" +
|
67
|
+
"fg11amb5gzdb4wi9bya3kc6lra.w3.mag.keio.ac.jp"
|
68
|
+
end
|
69
|
+
|
70
|
+
it "should convert " +
|
71
|
+
"'www.ほんとうにながいわけのわからないどめいんめいのらべるまだながくしないとたりない.w3.mag.keio.ac.jp' " +
|
72
|
+
"correctly" do
|
73
|
+
Addressable::IDNA.to_ascii(
|
74
|
+
"www.\343\201\273\343\202\223\343\201\250\343\201\206\343\201\253\343" +
|
75
|
+
"\201\252\343\201\213\343\202\231\343\201\204\343\202\217\343\201\221" +
|
76
|
+
"\343\201\256\343\202\217\343\201\213\343\202\211\343\201\252\343\201" +
|
77
|
+
"\204\343\201\250\343\202\231\343\202\201\343\201\204\343\202\223\343" +
|
78
|
+
"\202\201\343\201\204\343\201\256\343\202\211\343\201\270\343\202\231" +
|
79
|
+
"\343\202\213\343\201\276\343\201\237\343\202\231\343\201\252\343\201" +
|
80
|
+
"\213\343\202\231\343\201\217\343\201\227\343\201\252\343\201\204\343" +
|
81
|
+
"\201\250\343\201\237\343\202\212\343\201\252\343\201\204." +
|
82
|
+
"w3.mag.keio.ac.jp"
|
83
|
+
).should ==
|
84
|
+
"www.xn--n8jaaaaai5bhf7as8fsfk3jnknefdde3" +
|
85
|
+
"fg11amb5gzdb4wi9bya3kc6lra.w3.mag.keio.ac.jp"
|
86
|
+
end
|
87
|
+
|
88
|
+
it "should convert '点心和烤鸭.w3.mag.keio.ac.jp' correctly" do
|
89
|
+
Addressable::IDNA.to_ascii(
|
90
|
+
"点心和烤鸭.w3.mag.keio.ac.jp"
|
91
|
+
).should == "xn--0trv4xfvn8el34t.w3.mag.keio.ac.jp"
|
92
|
+
end
|
93
|
+
|
94
|
+
it "should convert '가각갂갃간갅갆갇갈갉힢힣.com' correctly" do
|
95
|
+
Addressable::IDNA.to_ascii(
|
96
|
+
"가각갂갃간갅갆갇갈갉힢힣.com"
|
97
|
+
).should == "xn--o39acdefghijk5883jma.com"
|
98
|
+
end
|
99
|
+
|
100
|
+
it "should convert " +
|
101
|
+
"'\347\242\274\346\250\231\346\272\226\350" +
|
102
|
+
"\220\254\345\234\213\347\242\274.com' correctly" do
|
103
|
+
Addressable::IDNA.to_ascii(
|
104
|
+
"\347\242\274\346\250\231\346\272\226\350" +
|
105
|
+
"\220\254\345\234\213\347\242\274.com"
|
106
|
+
).should == "xn--9cs565brid46mda086o.com"
|
107
|
+
end
|
108
|
+
|
109
|
+
it "should convert 'リ宠퐱〹.com' correctly" do
|
110
|
+
Addressable::IDNA.to_ascii(
|
111
|
+
"\357\276\230\345\256\240\355\220\261\343\200\271.com"
|
112
|
+
).should == "xn--eek174hoxfpr4k.com"
|
113
|
+
end
|
114
|
+
|
115
|
+
it "should convert 'リ宠퐱卄.com' correctly" do
|
116
|
+
Addressable::IDNA.to_ascii(
|
117
|
+
"\343\203\252\345\256\240\355\220\261\345\215\204.com"
|
118
|
+
).should == "xn--eek174hoxfpr4k.com"
|
119
|
+
end
|
120
|
+
|
121
|
+
it "should convert 'ᆵ' correctly" do
|
122
|
+
Addressable::IDNA.to_ascii(
|
123
|
+
"\341\206\265"
|
124
|
+
).should == "xn--4ud"
|
125
|
+
end
|
126
|
+
|
127
|
+
it "should convert 'ᆵ' correctly" do
|
128
|
+
Addressable::IDNA.to_ascii(
|
129
|
+
"\357\276\257"
|
130
|
+
).should == "xn--4ud"
|
131
|
+
end
|
132
|
+
end
|
133
|
+
|
134
|
+
describe Addressable::IDNA, "when converting from ASCII to unicode" do
|
135
|
+
it "should convert 'www.google.com' correctly" do
|
136
|
+
Addressable::IDNA.to_unicode("www.google.com").should == "www.google.com"
|
137
|
+
end
|
138
|
+
|
139
|
+
it "should convert 'www.詹姆斯.com' correctly" do
|
140
|
+
Addressable::IDNA.to_unicode(
|
141
|
+
"www.xn--8ws00zhy3a.com"
|
142
|
+
).should == "www.詹姆斯.com"
|
143
|
+
end
|
144
|
+
|
145
|
+
it "should convert 'www.iñtërnâtiônàlizætiøn.com' correctly" do
|
146
|
+
Addressable::IDNA.to_unicode(
|
147
|
+
"www.xn--itrntinliztin-vdb0a5exd8ewcye.com"
|
148
|
+
).should == "www.iñtërnâtiônàlizætiøn.com"
|
149
|
+
end
|
150
|
+
|
151
|
+
it "should convert " +
|
152
|
+
"'www.ほんとうにながいわけのわからないどめいんめいのらべるまだながくしないとたりない.w3.mag.keio.ac.jp' " +
|
153
|
+
"correctly" do
|
154
|
+
Addressable::IDNA.to_unicode(
|
155
|
+
"www.xn--n8jaaaaai5bhf7as8fsfk3jnknefdde3" +
|
156
|
+
"fg11amb5gzdb4wi9bya3kc6lra.w3.mag.keio.ac.jp"
|
157
|
+
).should ==
|
158
|
+
"www.ほんとうにながいわけのわからないどめいんめいのらべるまだながくしないとたりない.w3.mag.keio.ac.jp"
|
159
|
+
end
|
160
|
+
|
161
|
+
it "should convert '点心和烤鸭.w3.mag.keio.ac.jp' correctly" do
|
162
|
+
Addressable::IDNA.to_unicode(
|
163
|
+
"xn--0trv4xfvn8el34t.w3.mag.keio.ac.jp"
|
164
|
+
).should == "点心和烤鸭.w3.mag.keio.ac.jp"
|
165
|
+
end
|
166
|
+
|
167
|
+
it "should convert '가각갂갃간갅갆갇갈갉힢힣.com' correctly" do
|
168
|
+
Addressable::IDNA.to_unicode(
|
169
|
+
"xn--o39acdefghijk5883jma.com"
|
170
|
+
).should == "가각갂갃간갅갆갇갈갉힢힣.com"
|
171
|
+
end
|
172
|
+
|
173
|
+
it "should convert " +
|
174
|
+
"'\347\242\274\346\250\231\346\272\226\350" +
|
175
|
+
"\220\254\345\234\213\347\242\274.com' correctly" do
|
176
|
+
Addressable::IDNA.to_unicode(
|
177
|
+
"xn--9cs565brid46mda086o.com"
|
178
|
+
).should ==
|
179
|
+
"\347\242\274\346\250\231\346\272\226\350" +
|
180
|
+
"\220\254\345\234\213\347\242\274.com"
|
181
|
+
end
|
182
|
+
|
183
|
+
it "should convert 'リ宠퐱卄.com' correctly" do
|
184
|
+
Addressable::IDNA.to_unicode(
|
185
|
+
"xn--eek174hoxfpr4k.com"
|
186
|
+
).should == "\343\203\252\345\256\240\355\220\261\345\215\204.com"
|
187
|
+
end
|
188
|
+
|
189
|
+
it "should convert 'ᆵ' correctly" do
|
190
|
+
Addressable::IDNA.to_unicode(
|
191
|
+
"xn--4ud"
|
192
|
+
).should == "\341\206\265"
|
193
|
+
end
|
194
|
+
end
|
@@ -0,0 +1,2152 @@
|
|
1
|
+
# encoding:utf-8
|
2
|
+
#--
|
3
|
+
# Addressable, Copyright (c) 2006-2007 Bob Aman
|
4
|
+
#
|
5
|
+
# Permission is hereby granted, free of charge, to any person obtaining
|
6
|
+
# a copy of this software and associated documentation files (the
|
7
|
+
# "Software"), to deal in the Software without restriction, including
|
8
|
+
# without limitation the rights to use, copy, modify, merge, publish,
|
9
|
+
# distribute, sublicense, and/or sell copies of the Software, and to
|
10
|
+
# permit persons to whom the Software is furnished to do so, subject to
|
11
|
+
# the following conditions:
|
12
|
+
#
|
13
|
+
# The above copyright notice and this permission notice shall be
|
14
|
+
# included in all copies or substantial portions of the Software.
|
15
|
+
#
|
16
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
18
|
+
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
20
|
+
# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
21
|
+
# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
22
|
+
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
23
|
+
#++
|
24
|
+
|
25
|
+
require "addressable/template"
|
26
|
+
|
27
|
+
if !"".respond_to?("force_encoding")
|
28
|
+
class String
|
29
|
+
def force_encoding(encoding)
|
30
|
+
@encoding = encoding
|
31
|
+
end
|
32
|
+
|
33
|
+
def encoding
|
34
|
+
@encoding ||= Encoding::ASCII_8BIT
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
class Encoding
|
39
|
+
def initialize(name)
|
40
|
+
@name = name
|
41
|
+
end
|
42
|
+
|
43
|
+
def to_s
|
44
|
+
return @name
|
45
|
+
end
|
46
|
+
|
47
|
+
UTF_8 = Encoding.new("UTF-8")
|
48
|
+
ASCII_8BIT = Encoding.new("US-ASCII")
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
52
|
+
class ExampleProcessor
|
53
|
+
def self.validate(name, value)
|
54
|
+
return !!(value =~ /^[\w ]+$/) if name == "query"
|
55
|
+
return true
|
56
|
+
end
|
57
|
+
|
58
|
+
def self.transform(name, value)
|
59
|
+
return value.gsub(/ /, "+") if name == "query"
|
60
|
+
return value
|
61
|
+
end
|
62
|
+
|
63
|
+
def self.restore(name, value)
|
64
|
+
return value.gsub(/\+/, " ") if name == "query"
|
65
|
+
return value.tr("A-Za-z", "N-ZA-Mn-za-m") if name == "rot13"
|
66
|
+
return value
|
67
|
+
end
|
68
|
+
|
69
|
+
def self.match(name)
|
70
|
+
return ".*?" if name == "first"
|
71
|
+
return ".*"
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
class SlashlessProcessor
|
76
|
+
def self.match(name)
|
77
|
+
return "[^/\\n]*"
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
class NoOpProcessor
|
82
|
+
def self.transform(name, value)
|
83
|
+
value
|
84
|
+
end
|
85
|
+
end
|
86
|
+
|
87
|
+
describe Addressable::Template do
|
88
|
+
it "should raise a TypeError for invalid patterns" do
|
89
|
+
(lambda do
|
90
|
+
Addressable::Template.new(42)
|
91
|
+
end).should raise_error(TypeError, "Can't convert Fixnum into String.")
|
92
|
+
end
|
93
|
+
end
|
94
|
+
|
95
|
+
describe Addressable::Template, "created with the pattern '/'" do
|
96
|
+
before do
|
97
|
+
@template = Addressable::Template.new("/")
|
98
|
+
end
|
99
|
+
|
100
|
+
it "should have no variables" do
|
101
|
+
@template.variables.should be_empty
|
102
|
+
end
|
103
|
+
|
104
|
+
it "should have the correct mapping when extracting from '/'" do
|
105
|
+
@template.extract("/").should == {}
|
106
|
+
end
|
107
|
+
end
|
108
|
+
|
109
|
+
describe Addressable::URI, "when parsed from '/one/'" do
|
110
|
+
before do
|
111
|
+
@uri = Addressable::URI.parse("/one/")
|
112
|
+
end
|
113
|
+
|
114
|
+
it "should not match the pattern '/two/'" do
|
115
|
+
Addressable::Template.new("/two/").extract(@uri).should == nil
|
116
|
+
end
|
117
|
+
|
118
|
+
it "should have the correct mapping when extracting values " +
|
119
|
+
"using the pattern '/{number}/'" do
|
120
|
+
Addressable::Template.new(
|
121
|
+
"/{number}/"
|
122
|
+
).extract(@uri).should == {"number" => "one"}
|
123
|
+
end
|
124
|
+
end
|
125
|
+
|
126
|
+
describe Addressable::Template, "created with the pattern '/{number}/'" do
|
127
|
+
before do
|
128
|
+
@template = Addressable::Template.new("/{number}/")
|
129
|
+
end
|
130
|
+
|
131
|
+
it "should have the variables ['number']" do
|
132
|
+
@template.variables.should == ["number"]
|
133
|
+
end
|
134
|
+
|
135
|
+
it "should not match the pattern '/'" do
|
136
|
+
@template.match("/").should == nil
|
137
|
+
end
|
138
|
+
|
139
|
+
it "should match the pattern '/two/'" do
|
140
|
+
@template.match("/two/").mapping.should == {"number" => "two"}
|
141
|
+
end
|
142
|
+
end
|
143
|
+
|
144
|
+
describe Addressable::Template,
|
145
|
+
"created with the pattern '/{number}/{number}/'" do
|
146
|
+
before do
|
147
|
+
@template = Addressable::Template.new("/{number}/{number}/")
|
148
|
+
end
|
149
|
+
|
150
|
+
it "should have one variable" do
|
151
|
+
@template.variables.should == ["number"]
|
152
|
+
end
|
153
|
+
|
154
|
+
it "should have the correct mapping when extracting from '/1/1/'" do
|
155
|
+
@template.extract("/1/1/").should == {"number" => "1"}
|
156
|
+
end
|
157
|
+
|
158
|
+
it "should not match '/1/2/'" do
|
159
|
+
@template.match("/1/2/").should == nil
|
160
|
+
end
|
161
|
+
|
162
|
+
it "should not match '/2/1/'" do
|
163
|
+
@template.match("/2/1/").should == nil
|
164
|
+
end
|
165
|
+
|
166
|
+
it "should not match '/1/'" do
|
167
|
+
@template.match("/1/").should == nil
|
168
|
+
end
|
169
|
+
|
170
|
+
it "should not match '/1/1/1/'" do
|
171
|
+
@template.match("/1/1/1/").should == nil
|
172
|
+
end
|
173
|
+
|
174
|
+
it "should not match '/1/2/3/'" do
|
175
|
+
@template.match("/1/2/3/").should == nil
|
176
|
+
end
|
177
|
+
end
|
178
|
+
|
179
|
+
describe Addressable::Template,
|
180
|
+
"created with the pattern '/{number}{-prefix|.|number}'" do
|
181
|
+
before do
|
182
|
+
@template = Addressable::Template.new("/{number}{-prefix|.|number}")
|
183
|
+
end
|
184
|
+
|
185
|
+
it "should have one variable" do
|
186
|
+
@template.variables.should == ["number"]
|
187
|
+
end
|
188
|
+
|
189
|
+
it "should have the correct mapping when extracting from '/1.1'" do
|
190
|
+
@template.extract("/1.1").should == {"number" => "1"}
|
191
|
+
end
|
192
|
+
|
193
|
+
it "should have the correct mapping when extracting from '/99.99'" do
|
194
|
+
@template.extract("/99.99").should == {"number" => "99"}
|
195
|
+
end
|
196
|
+
|
197
|
+
it "should not match '/1.2'" do
|
198
|
+
@template.match("/1.2").should == nil
|
199
|
+
end
|
200
|
+
|
201
|
+
it "should not match '/2.1'" do
|
202
|
+
@template.match("/2.1").should == nil
|
203
|
+
end
|
204
|
+
|
205
|
+
it "should not match '/1'" do
|
206
|
+
@template.match("/1").should == nil
|
207
|
+
end
|
208
|
+
|
209
|
+
it "should not match '/1.1.1'" do
|
210
|
+
@template.match("/1.1.1").should == nil
|
211
|
+
end
|
212
|
+
|
213
|
+
it "should not match '/1.23'" do
|
214
|
+
@template.match("/1.23").should == nil
|
215
|
+
end
|
216
|
+
end
|
217
|
+
|
218
|
+
describe Addressable::Template,
|
219
|
+
"created with the pattern '/{number}/{-suffix|/|number}'" do
|
220
|
+
before do
|
221
|
+
@template = Addressable::Template.new("/{number}/{-suffix|/|number}")
|
222
|
+
end
|
223
|
+
|
224
|
+
it "should have one variable" do
|
225
|
+
@template.variables.should == ["number"]
|
226
|
+
end
|
227
|
+
|
228
|
+
it "should have the correct mapping when extracting from '/1/1/'" do
|
229
|
+
@template.extract("/1/1/").should == {"number" => "1"}
|
230
|
+
end
|
231
|
+
|
232
|
+
it "should have the correct mapping when extracting from '/99/99/'" do
|
233
|
+
@template.extract("/99/99/").should == {"number" => "99"}
|
234
|
+
end
|
235
|
+
|
236
|
+
it "should not match '/1/1'" do
|
237
|
+
@template.match("/1/1").should == nil
|
238
|
+
end
|
239
|
+
|
240
|
+
it "should not match '/11/'" do
|
241
|
+
@template.match("/11/").should == nil
|
242
|
+
end
|
243
|
+
|
244
|
+
it "should not match '/1/2/'" do
|
245
|
+
@template.match("/1/2/").should == nil
|
246
|
+
end
|
247
|
+
|
248
|
+
it "should not match '/2/1/'" do
|
249
|
+
@template.match("/2/1/").should == nil
|
250
|
+
end
|
251
|
+
|
252
|
+
it "should not match '/1/'" do
|
253
|
+
@template.match("/1/").should == nil
|
254
|
+
end
|
255
|
+
|
256
|
+
it "should not match '/1/1/1/'" do
|
257
|
+
@template.match("/1/1/1/").should == nil
|
258
|
+
end
|
259
|
+
|
260
|
+
it "should not match '/1/23/'" do
|
261
|
+
@template.match("/1/23/").should == nil
|
262
|
+
end
|
263
|
+
end
|
264
|
+
|
265
|
+
describe Addressable::Template,
|
266
|
+
"created with the pattern '/{number}/?{-join|&|number}'" do
|
267
|
+
before do
|
268
|
+
@template = Addressable::Template.new(
|
269
|
+
"/{number}/?{-join|&|number,letter}"
|
270
|
+
)
|
271
|
+
end
|
272
|
+
|
273
|
+
it "should have one variable" do
|
274
|
+
@template.variables.should == ["number", "letter"]
|
275
|
+
end
|
276
|
+
|
277
|
+
it "should have the correct mapping when extracting from '/1/?number=1'" do
|
278
|
+
@template.extract("/1/?number=1").should == {"number" => "1"}
|
279
|
+
end
|
280
|
+
|
281
|
+
it "should have the correct mapping when extracting " +
|
282
|
+
"from '/99/?number=99'" do
|
283
|
+
@template.extract("/99/?number=99").should == {"number" => "99"}
|
284
|
+
end
|
285
|
+
|
286
|
+
it "should have the correct mapping when extracting " +
|
287
|
+
"from '/1/?number=1&letter=a'" do
|
288
|
+
@template.extract("/1/?number=1&letter=a").should == {
|
289
|
+
"number" => "1", "letter" => "a"
|
290
|
+
}
|
291
|
+
end
|
292
|
+
|
293
|
+
it "should not match '/1/?number=1&bogus=foo'" do
|
294
|
+
@template.match("/1/?number=1&bogus=foo").should == nil
|
295
|
+
end
|
296
|
+
|
297
|
+
it "should not match '/1/?number=2'" do
|
298
|
+
@template.match("/1/?number=2").should == nil
|
299
|
+
end
|
300
|
+
|
301
|
+
it "should not match '/2/?number=1'" do
|
302
|
+
@template.match("/2/?number=1").should == nil
|
303
|
+
end
|
304
|
+
|
305
|
+
it "should not match '/1/?'" do
|
306
|
+
@template.match("/1/?").should == nil
|
307
|
+
end
|
308
|
+
end
|
309
|
+
|
310
|
+
describe Addressable::Template,
|
311
|
+
"created with the pattern '/{number}/{-list|/|number}/'" do
|
312
|
+
before do
|
313
|
+
@template = Addressable::Template.new("/{number}/{-list|/|number}/")
|
314
|
+
end
|
315
|
+
|
316
|
+
it "should have one variable" do
|
317
|
+
@template.variables.should == ["number"]
|
318
|
+
end
|
319
|
+
|
320
|
+
it "should not match '/1/1/'" do
|
321
|
+
@template.match("/1/1/").should == nil
|
322
|
+
end
|
323
|
+
|
324
|
+
it "should not match '/1/2/'" do
|
325
|
+
@template.match("/1/2/").should == nil
|
326
|
+
end
|
327
|
+
|
328
|
+
it "should not match '/2/1/'" do
|
329
|
+
@template.match("/2/1/").should == nil
|
330
|
+
end
|
331
|
+
|
332
|
+
it "should not match '/1/1/1/'" do
|
333
|
+
@template.match("/1/1/1/").should == nil
|
334
|
+
end
|
335
|
+
|
336
|
+
it "should not match '/1/1/1/1/'" do
|
337
|
+
@template.match("/1/1/1/1/").should == nil
|
338
|
+
end
|
339
|
+
end
|
340
|
+
|
341
|
+
describe Addressable::Template, "created with the pattern " +
|
342
|
+
"'http://www.example.com/?{-join|&|query,number}'" do
|
343
|
+
before do
|
344
|
+
@template = Addressable::Template.new(
|
345
|
+
"http://www.example.com/?{-join|&|query,number}"
|
346
|
+
)
|
347
|
+
end
|
348
|
+
|
349
|
+
it "when inspected, should have the correct class name" do
|
350
|
+
@template.inspect.should include("Addressable::Template")
|
351
|
+
end
|
352
|
+
|
353
|
+
it "when inspected, should have the correct object id" do
|
354
|
+
@template.inspect.should include("%#0x" % @template.object_id)
|
355
|
+
end
|
356
|
+
|
357
|
+
it "should have the variables ['query', 'number']" do
|
358
|
+
@template.variables.should == ["query", "number"]
|
359
|
+
end
|
360
|
+
|
361
|
+
it "should not match the pattern 'http://www.example.com/'" do
|
362
|
+
@template.match("http://www.example.com/").should == nil
|
363
|
+
end
|
364
|
+
|
365
|
+
it "should match the pattern 'http://www.example.com/?'" do
|
366
|
+
@template.match("http://www.example.com/?").mapping.should == {}
|
367
|
+
end
|
368
|
+
|
369
|
+
it "should match the pattern " +
|
370
|
+
"'http://www.example.com/?query=mycelium'" do
|
371
|
+
match = @template.match(
|
372
|
+
"http://www.example.com/?query=mycelium"
|
373
|
+
)
|
374
|
+
match.variables.should == ["query", "number"]
|
375
|
+
match.values.should == ["mycelium", nil]
|
376
|
+
match.mapping.should == {"query" => "mycelium"}
|
377
|
+
match.inspect.should =~ /MatchData/
|
378
|
+
end
|
379
|
+
|
380
|
+
it "should match the pattern " +
|
381
|
+
"'http://www.example.com/?query=mycelium&number=100'" do
|
382
|
+
@template.match(
|
383
|
+
"http://www.example.com/?query=mycelium&number=100"
|
384
|
+
).mapping.should == {"query" => "mycelium", "number" => "100"}
|
385
|
+
end
|
386
|
+
end
|
387
|
+
|
388
|
+
describe Addressable::URI, "when parsed from '/one/two/'" do
|
389
|
+
before do
|
390
|
+
@uri = Addressable::URI.parse("/one/two/")
|
391
|
+
end
|
392
|
+
|
393
|
+
it "should not match the pattern '/{number}/' " +
|
394
|
+
"with the SlashlessProcessor" do
|
395
|
+
Addressable::Template.new(
|
396
|
+
"/{number}/"
|
397
|
+
).extract(@uri, SlashlessProcessor).should == nil
|
398
|
+
end
|
399
|
+
|
400
|
+
it "should have the correct mapping when extracting values " +
|
401
|
+
"using the pattern '/{number}/' without a processor" do
|
402
|
+
Addressable::Template.new("/{number}/").extract(@uri).should == {
|
403
|
+
"number" => "one/two"
|
404
|
+
}
|
405
|
+
end
|
406
|
+
|
407
|
+
it "should have the correct mapping when extracting values " +
|
408
|
+
"using the pattern '/{first}/{second}/' with the SlashlessProcessor" do
|
409
|
+
Addressable::Template.new(
|
410
|
+
"/{first}/{second}/"
|
411
|
+
).extract(@uri, SlashlessProcessor).should == {
|
412
|
+
"first" => "one",
|
413
|
+
"second" => "two"
|
414
|
+
}
|
415
|
+
end
|
416
|
+
end
|
417
|
+
|
418
|
+
describe Addressable::URI, "when parsed from " +
|
419
|
+
"'http://example.com/search/an+example+search+query/'" do
|
420
|
+
before do
|
421
|
+
@uri = Addressable::URI.parse(
|
422
|
+
"http://example.com/search/an+example+search+query/")
|
423
|
+
end
|
424
|
+
|
425
|
+
it "should have the correct mapping when extracting values using " +
|
426
|
+
"the pattern 'http://example.com/search/{query}/' with the " +
|
427
|
+
"ExampleProcessor" do
|
428
|
+
Addressable::Template.new(
|
429
|
+
"http://example.com/search/{query}/"
|
430
|
+
).extract(@uri, ExampleProcessor).should == {
|
431
|
+
"query" => "an example search query"
|
432
|
+
}
|
433
|
+
end
|
434
|
+
|
435
|
+
it "should have the correct mapping when extracting values " +
|
436
|
+
"using the pattern " +
|
437
|
+
"'http://example.com/search/{-list|+|query}/'" do
|
438
|
+
Addressable::Template.new(
|
439
|
+
"http://example.com/search/{-list|+|query}/"
|
440
|
+
).extract(@uri).should == {
|
441
|
+
"query" => ["an", "example", "search", "query"]
|
442
|
+
}
|
443
|
+
end
|
444
|
+
|
445
|
+
it "should return nil when extracting values using " +
|
446
|
+
"a non-matching pattern" do
|
447
|
+
Addressable::Template.new(
|
448
|
+
"http://bogus.com/{thingy}/"
|
449
|
+
).extract(@uri).should == nil
|
450
|
+
end
|
451
|
+
end
|
452
|
+
|
453
|
+
describe Addressable::URI, "when parsed from " +
|
454
|
+
"'http://example.com/a/b/c/'" do
|
455
|
+
before do
|
456
|
+
@uri = Addressable::URI.parse(
|
457
|
+
"http://example.com/a/b/c/")
|
458
|
+
end
|
459
|
+
|
460
|
+
it "should have the correct mapping when extracting values " +
|
461
|
+
"using the pattern " +
|
462
|
+
"'http://example.com/{first}/{second}/' with the ExampleProcessor" do
|
463
|
+
Addressable::Template.new(
|
464
|
+
"http://example.com/{first}/{second}/"
|
465
|
+
).extract(@uri, ExampleProcessor).should == {
|
466
|
+
"first" => "a",
|
467
|
+
"second" => "b/c"
|
468
|
+
}
|
469
|
+
end
|
470
|
+
|
471
|
+
it "should have the correct mapping when extracting values " +
|
472
|
+
"using the pattern " +
|
473
|
+
"'http://example.com/{first}/{-list|/|second}/'" do
|
474
|
+
Addressable::Template.new(
|
475
|
+
"http://example.com/{first}/{-list|/|second}/"
|
476
|
+
).extract(@uri).should == {
|
477
|
+
"first" => "a",
|
478
|
+
"second" => ["b", "c"]
|
479
|
+
}
|
480
|
+
end
|
481
|
+
|
482
|
+
it "should have the correct mapping when extracting values " +
|
483
|
+
"using the pattern " +
|
484
|
+
"'http://example.com/{first}/{-list|/|rot13}/' " +
|
485
|
+
"with the ExampleProcessor" do
|
486
|
+
Addressable::Template.new(
|
487
|
+
"http://example.com/{first}/{-list|/|rot13}/"
|
488
|
+
).extract(@uri, ExampleProcessor).should == {
|
489
|
+
"first" => "a",
|
490
|
+
"rot13" => ["o", "p"]
|
491
|
+
}
|
492
|
+
end
|
493
|
+
|
494
|
+
it "should have the correct mapping when extracting values " +
|
495
|
+
"using the pattern " +
|
496
|
+
"'http://example.com/{-list|/|rot13}/' " +
|
497
|
+
"with the ExampleProcessor" do
|
498
|
+
Addressable::Template.new(
|
499
|
+
"http://example.com/{-list|/|rot13}/"
|
500
|
+
).extract(@uri, ExampleProcessor).should == {
|
501
|
+
"rot13" => ["n", "o", "p"]
|
502
|
+
}
|
503
|
+
end
|
504
|
+
|
505
|
+
it "should not map to anything when extracting values " +
|
506
|
+
"using the pattern " +
|
507
|
+
"'http://example.com/{-list|/|rot13}/'" do
|
508
|
+
Addressable::Template.new(
|
509
|
+
"http://example.com/{-join|/|a,b,c}/"
|
510
|
+
).extract(@uri).should == nil
|
511
|
+
end
|
512
|
+
end
|
513
|
+
|
514
|
+
describe Addressable::URI, "when parsed from " +
|
515
|
+
"'http://example.com/?a=one&b=two&c=three'" do
|
516
|
+
before do
|
517
|
+
@uri = Addressable::URI.parse("http://example.com/?a=one&b=two&c=three")
|
518
|
+
end
|
519
|
+
|
520
|
+
it "should have the correct mapping when extracting values " +
|
521
|
+
"using the pattern " +
|
522
|
+
"'http://example.com/?{-join|&|a,b,c}'" do
|
523
|
+
Addressable::Template.new(
|
524
|
+
"http://example.com/?{-join|&|a,b,c}"
|
525
|
+
).extract(@uri).should == {
|
526
|
+
"a" => "one",
|
527
|
+
"b" => "two",
|
528
|
+
"c" => "three"
|
529
|
+
}
|
530
|
+
end
|
531
|
+
end
|
532
|
+
|
533
|
+
describe Addressable::URI, "when parsed from " +
|
534
|
+
"'http://example.com/?rot13=frperg'" do
|
535
|
+
before do
|
536
|
+
@uri = Addressable::URI.parse("http://example.com/?rot13=frperg")
|
537
|
+
end
|
538
|
+
|
539
|
+
it "should have the correct mapping when extracting values " +
|
540
|
+
"using the pattern " +
|
541
|
+
"'http://example.com/?{-join|&|rot13}' with the ExampleProcessor" do
|
542
|
+
Addressable::Template.new(
|
543
|
+
"http://example.com/?{-join|&|rot13}"
|
544
|
+
).extract(@uri, ExampleProcessor).should == {
|
545
|
+
"rot13" => "secret"
|
546
|
+
}
|
547
|
+
end
|
548
|
+
end
|
549
|
+
|
550
|
+
describe Addressable::URI, "when parsed from " +
|
551
|
+
"'http://example.org///something///'" do
|
552
|
+
before do
|
553
|
+
@uri = Addressable::URI.parse("http://example.org///something///")
|
554
|
+
end
|
555
|
+
|
556
|
+
it "should have the correct mapping when extracting values " +
|
557
|
+
"using the pattern 'http://example.org{-prefix|/|parts}/'" do
|
558
|
+
Addressable::Template.new(
|
559
|
+
"http://example.org{-prefix|/|parts}/"
|
560
|
+
).extract(@uri).should == {
|
561
|
+
"parts" => ["", "", "something", "", ""]
|
562
|
+
}
|
563
|
+
end
|
564
|
+
|
565
|
+
it "should have the correct mapping when extracting values " +
|
566
|
+
"using the pattern 'http://example.org/{-suffix|/|parts}'" do
|
567
|
+
Addressable::Template.new(
|
568
|
+
"http://example.org/{-suffix|/|parts}"
|
569
|
+
).extract(@uri).should == {
|
570
|
+
"parts" => ["", "", "something", "", ""]
|
571
|
+
}
|
572
|
+
end
|
573
|
+
|
574
|
+
it "should have the correct mapping when extracting values " +
|
575
|
+
"using the pattern 'http://example.org/{-list|/|parts}'" do
|
576
|
+
Addressable::Template.new(
|
577
|
+
"http://example.org/{-list|/|parts}"
|
578
|
+
).extract(@uri).should == {
|
579
|
+
"parts" => ["", "", "something", "", ""]
|
580
|
+
}
|
581
|
+
end
|
582
|
+
end
|
583
|
+
|
584
|
+
describe Addressable::URI, "when parsed from " +
|
585
|
+
"'http://example.com/one/spacer/two/'" do
|
586
|
+
before do
|
587
|
+
@uri = Addressable::URI.parse("http://example.com/one/spacer/two/")
|
588
|
+
end
|
589
|
+
|
590
|
+
it "should have the correct mapping when extracting values " +
|
591
|
+
"using the pattern " +
|
592
|
+
"'http://example.com/{first}/spacer/{second}/'" do
|
593
|
+
Addressable::Template.new(
|
594
|
+
"http://example.com/{first}/spacer/{second}/"
|
595
|
+
).extract(@uri).should == {
|
596
|
+
"first" => "one",
|
597
|
+
"second" => "two"
|
598
|
+
}
|
599
|
+
end
|
600
|
+
|
601
|
+
it "should have the correct mapping when extracting values " +
|
602
|
+
"using the pattern " +
|
603
|
+
"'http://example.com{-prefix|/|stuff}/'" do
|
604
|
+
Addressable::Template.new(
|
605
|
+
"http://example.com{-prefix|/|stuff}/"
|
606
|
+
).extract(@uri).should == {
|
607
|
+
"stuff" => ["one", "spacer", "two"]
|
608
|
+
}
|
609
|
+
end
|
610
|
+
|
611
|
+
it "should have the correct mapping when extracting values " +
|
612
|
+
"using the pattern " +
|
613
|
+
"'http://example.com/o{-prefix|/|stuff}/'" do
|
614
|
+
Addressable::Template.new(
|
615
|
+
"http://example.com/o{-prefix|/|stuff}/"
|
616
|
+
).extract(@uri).should == nil
|
617
|
+
end
|
618
|
+
|
619
|
+
it "should have the correct mapping when extracting values " +
|
620
|
+
"using the pattern " +
|
621
|
+
"'http://example.com/{first}/spacer{-prefix|/|stuff}/'" do
|
622
|
+
Addressable::Template.new(
|
623
|
+
"http://example.com/{first}/spacer{-prefix|/|stuff}/"
|
624
|
+
).extract(@uri).should == {
|
625
|
+
"first" => "one",
|
626
|
+
"stuff" => "two"
|
627
|
+
}
|
628
|
+
end
|
629
|
+
|
630
|
+
it "should not match anything when extracting values " +
|
631
|
+
"using the incorrect suffix pattern " +
|
632
|
+
"'http://example.com/{-prefix|/|stuff}/'" do
|
633
|
+
Addressable::Template.new(
|
634
|
+
"http://example.com/{-prefix|/|stuff}/"
|
635
|
+
).extract(@uri).should == nil
|
636
|
+
end
|
637
|
+
|
638
|
+
it "should have the correct mapping when extracting values " +
|
639
|
+
"using the pattern " +
|
640
|
+
"'http://example.com{-prefix|/|rot13}/' with the ExampleProcessor" do
|
641
|
+
Addressable::Template.new(
|
642
|
+
"http://example.com{-prefix|/|rot13}/"
|
643
|
+
).extract(@uri, ExampleProcessor).should == {
|
644
|
+
"rot13" => ["bar", "fcnpre", "gjb"]
|
645
|
+
}
|
646
|
+
end
|
647
|
+
|
648
|
+
it "should have the correct mapping when extracting values " +
|
649
|
+
"using the pattern " +
|
650
|
+
"'http://example.com{-prefix|/|rot13}' with the ExampleProcessor" do
|
651
|
+
Addressable::Template.new(
|
652
|
+
"http://example.com{-prefix|/|rot13}"
|
653
|
+
).extract(@uri, ExampleProcessor).should == {
|
654
|
+
"rot13" => ["bar", "fcnpre", "gjb", ""]
|
655
|
+
}
|
656
|
+
end
|
657
|
+
|
658
|
+
it "should not match anything when extracting values " +
|
659
|
+
"using the incorrect suffix pattern " +
|
660
|
+
"'http://example.com/{-prefix|/|rot13}' with the ExampleProcessor" do
|
661
|
+
Addressable::Template.new(
|
662
|
+
"http://example.com/{-prefix|/|rot13}"
|
663
|
+
).extract(@uri, ExampleProcessor).should == nil
|
664
|
+
end
|
665
|
+
|
666
|
+
it "should have the correct mapping when extracting values " +
|
667
|
+
"using the pattern " +
|
668
|
+
"'http://example.com/{-suffix|/|stuff}'" do
|
669
|
+
Addressable::Template.new(
|
670
|
+
"http://example.com/{-suffix|/|stuff}"
|
671
|
+
).extract(@uri).should == {
|
672
|
+
"stuff" => ["one", "spacer", "two"]
|
673
|
+
}
|
674
|
+
end
|
675
|
+
|
676
|
+
it "should have the correct mapping when extracting values " +
|
677
|
+
"using the pattern " +
|
678
|
+
"'http://example.com/{-suffix|/|stuff}o'" do
|
679
|
+
Addressable::Template.new(
|
680
|
+
"http://example.com/{-suffix|/|stuff}o"
|
681
|
+
).extract(@uri).should == nil
|
682
|
+
end
|
683
|
+
|
684
|
+
it "should have the correct mapping when extracting values " +
|
685
|
+
"using the pattern " +
|
686
|
+
"'http://example.com/o{-suffix|/|stuff}'" do
|
687
|
+
Addressable::Template.new(
|
688
|
+
"http://example.com/o{-suffix|/|stuff}"
|
689
|
+
).extract(@uri).should == {"stuff"=>["ne", "spacer", "two"]}
|
690
|
+
end
|
691
|
+
|
692
|
+
it "should have the correct mapping when extracting values " +
|
693
|
+
"using the pattern " +
|
694
|
+
"'http://example.com/{first}/spacer/{-suffix|/|stuff}'" do
|
695
|
+
Addressable::Template.new(
|
696
|
+
"http://example.com/{first}/spacer/{-suffix|/|stuff}"
|
697
|
+
).extract(@uri).should == {
|
698
|
+
"first" => "one",
|
699
|
+
"stuff" => "two"
|
700
|
+
}
|
701
|
+
end
|
702
|
+
|
703
|
+
it "should not match anything when extracting values " +
|
704
|
+
"using the incorrect suffix pattern " +
|
705
|
+
"'http://example.com/{-suffix|/|stuff}/'" do
|
706
|
+
Addressable::Template.new(
|
707
|
+
"http://example.com/{-suffix|/|stuff}/"
|
708
|
+
).extract(@uri).should == nil
|
709
|
+
end
|
710
|
+
|
711
|
+
it "should have the correct mapping when extracting values " +
|
712
|
+
"using the pattern " +
|
713
|
+
"'http://example.com/{-suffix|/|rot13}' with the ExampleProcessor" do
|
714
|
+
Addressable::Template.new(
|
715
|
+
"http://example.com/{-suffix|/|rot13}"
|
716
|
+
).extract(@uri, ExampleProcessor).should == {
|
717
|
+
"rot13" => ["bar", "fcnpre", "gjb"]
|
718
|
+
}
|
719
|
+
end
|
720
|
+
|
721
|
+
it "should have the correct mapping when extracting values " +
|
722
|
+
"using the pattern " +
|
723
|
+
"'http://example.com{-suffix|/|rot13}' with the ExampleProcessor" do
|
724
|
+
Addressable::Template.new(
|
725
|
+
"http://example.com{-suffix|/|rot13}"
|
726
|
+
).extract(@uri, ExampleProcessor).should == {
|
727
|
+
"rot13" => ["", "bar", "fcnpre", "gjb"]
|
728
|
+
}
|
729
|
+
end
|
730
|
+
|
731
|
+
it "should not match anything when extracting values " +
|
732
|
+
"using the incorrect suffix pattern " +
|
733
|
+
"'http://example.com/{-suffix|/|rot13}/' with the ExampleProcessor" do
|
734
|
+
Addressable::Template.new(
|
735
|
+
"http://example.com/{-suffix|/|rot13}/"
|
736
|
+
).extract(@uri, ExampleProcessor).should == nil
|
737
|
+
end
|
738
|
+
end
|
739
|
+
|
740
|
+
describe Addressable::URI, "when parsed from " +
|
741
|
+
"'http://example.com/?email=bob@sporkmonger.com'" do
|
742
|
+
before do
|
743
|
+
@uri = Addressable::URI.parse(
|
744
|
+
"http://example.com/?email=bob@sporkmonger.com"
|
745
|
+
)
|
746
|
+
end
|
747
|
+
|
748
|
+
it "should not match anything when extracting values " +
|
749
|
+
"using the incorrect opt pattern " +
|
750
|
+
"'http://example.com/?email={-opt|bogus@bogus.com|test}'" do
|
751
|
+
Addressable::Template.new(
|
752
|
+
"http://example.com/?email={-opt|bogus@bogus.com|test}"
|
753
|
+
).extract(@uri).should == nil
|
754
|
+
end
|
755
|
+
|
756
|
+
it "should not match anything when extracting values " +
|
757
|
+
"using the incorrect neg pattern " +
|
758
|
+
"'http://example.com/?email={-neg|bogus@bogus.com|test}'" do
|
759
|
+
Addressable::Template.new(
|
760
|
+
"http://example.com/?email={-neg|bogus@bogus.com|test}"
|
761
|
+
).extract(@uri).should == nil
|
762
|
+
end
|
763
|
+
|
764
|
+
it "should indicate a match when extracting values " +
|
765
|
+
"using the opt pattern " +
|
766
|
+
"'http://example.com/?email={-opt|bob@sporkmonger.com|test}'" do
|
767
|
+
Addressable::Template.new(
|
768
|
+
"http://example.com/?email={-opt|bob@sporkmonger.com|test}"
|
769
|
+
).extract(@uri).should == {}
|
770
|
+
end
|
771
|
+
|
772
|
+
it "should indicate a match when extracting values " +
|
773
|
+
"using the neg pattern " +
|
774
|
+
"'http://example.com/?email={-neg|bob@sporkmonger.com|test}'" do
|
775
|
+
Addressable::Template.new(
|
776
|
+
"http://example.com/?email={-neg|bob@sporkmonger.com|test}"
|
777
|
+
).extract(@uri).should == {}
|
778
|
+
end
|
779
|
+
end
|
780
|
+
|
781
|
+
describe Addressable::URI, "when parsed from " +
|
782
|
+
"'http://example.com/?email='" do
|
783
|
+
before do
|
784
|
+
@uri = Addressable::URI.parse(
|
785
|
+
"http://example.com/?email="
|
786
|
+
)
|
787
|
+
end
|
788
|
+
|
789
|
+
it "should indicate a match when extracting values " +
|
790
|
+
"using the opt pattern " +
|
791
|
+
"'http://example.com/?email={-opt|bob@sporkmonger.com|test}'" do
|
792
|
+
Addressable::Template.new(
|
793
|
+
"http://example.com/?email={-opt|bob@sporkmonger.com|test}"
|
794
|
+
).extract(@uri).should == {}
|
795
|
+
end
|
796
|
+
|
797
|
+
it "should indicate a match when extracting values " +
|
798
|
+
"using the neg pattern " +
|
799
|
+
"'http://example.com/?email={-neg|bob@sporkmonger.com|test}'" do
|
800
|
+
Addressable::Template.new(
|
801
|
+
"http://example.com/?email={-neg|bob@sporkmonger.com|test}"
|
802
|
+
).extract(@uri).should == {}
|
803
|
+
end
|
804
|
+
end
|
805
|
+
|
806
|
+
describe Addressable::URI, "when parsed from " +
|
807
|
+
"'http://example.com/a/b/c/?one=1&two=2#foo'" do
|
808
|
+
before do
|
809
|
+
@uri = Addressable::URI.parse(
|
810
|
+
"http://example.com/a/b/c/?one=1&two=2#foo"
|
811
|
+
)
|
812
|
+
end
|
813
|
+
|
814
|
+
it "should have the correct mapping when extracting values " +
|
815
|
+
"using the pattern " +
|
816
|
+
"'http://{host}/{-suffix|/|segments}?{-join|&|one,two}\#{fragment}'" do
|
817
|
+
Addressable::Template.new(
|
818
|
+
"http://{host}/{-suffix|/|segments}?{-join|&|one,two}\#{fragment}"
|
819
|
+
).extract(@uri).should == {
|
820
|
+
"host" => "example.com",
|
821
|
+
"segments" => ["a", "b", "c"],
|
822
|
+
"one" => "1",
|
823
|
+
"two" => "2",
|
824
|
+
"fragment" => "foo"
|
825
|
+
}
|
826
|
+
end
|
827
|
+
|
828
|
+
it "should not match when extracting values " +
|
829
|
+
"using the pattern " +
|
830
|
+
"'http://{host}/{-suffix|/|segments}?{-join|&|one}\#{fragment}'" do
|
831
|
+
Addressable::Template.new(
|
832
|
+
"http://{host}/{-suffix|/|segments}?{-join|&|one}\#{fragment}"
|
833
|
+
).extract(@uri).should == nil
|
834
|
+
end
|
835
|
+
|
836
|
+
it "should not match when extracting values " +
|
837
|
+
"using the pattern " +
|
838
|
+
"'http://{host}/{-suffix|/|segments}?{-join|&|bogus}\#{fragment}'" do
|
839
|
+
Addressable::Template.new(
|
840
|
+
"http://{host}/{-suffix|/|segments}?{-join|&|bogus}\#{fragment}"
|
841
|
+
).extract(@uri).should == nil
|
842
|
+
end
|
843
|
+
|
844
|
+
it "should not match when extracting values " +
|
845
|
+
"using the pattern " +
|
846
|
+
"'http://{host}/{-suffix|/|segments}?" +
|
847
|
+
"{-join|&|one,bogus}\#{fragment}'" do
|
848
|
+
Addressable::Template.new(
|
849
|
+
"http://{host}/{-suffix|/|segments}?{-join|&|one,bogus}\#{fragment}"
|
850
|
+
).extract(@uri).should == nil
|
851
|
+
end
|
852
|
+
|
853
|
+
it "should not match when extracting values " +
|
854
|
+
"using the pattern " +
|
855
|
+
"'http://{host}/{-suffix|/|segments}?" +
|
856
|
+
"{-join|&|one,two,bogus}\#{fragment}'" do
|
857
|
+
Addressable::Template.new(
|
858
|
+
"http://{host}/{-suffix|/|segments}?{-join|&|one,two,bogus}\#{fragment}"
|
859
|
+
).extract(@uri).should == {
|
860
|
+
"host" => "example.com",
|
861
|
+
"segments" => ["a", "b", "c"],
|
862
|
+
"one" => "1",
|
863
|
+
"two" => "2",
|
864
|
+
"fragment" => "foo"
|
865
|
+
}
|
866
|
+
end
|
867
|
+
end
|
868
|
+
|
869
|
+
describe Addressable::URI, "when given a pattern with bogus operators" do
|
870
|
+
before do
|
871
|
+
@uri = Addressable::URI.parse("http://example.com/a/b/c/")
|
872
|
+
end
|
873
|
+
|
874
|
+
it "should raise an InvalidTemplateOperatorError" do
|
875
|
+
(lambda do
|
876
|
+
Addressable::Template.new(
|
877
|
+
"http://example.com/{-bogus|/|a,b,c}/"
|
878
|
+
).extract(@uri)
|
879
|
+
end).should raise_error(
|
880
|
+
Addressable::Template::InvalidTemplateOperatorError
|
881
|
+
)
|
882
|
+
end
|
883
|
+
|
884
|
+
it "should raise an InvalidTemplateOperatorError" do
|
885
|
+
(lambda do
|
886
|
+
Addressable::Template.new(
|
887
|
+
"http://example.com{-prefix|/|a,b,c}/"
|
888
|
+
).extract(@uri)
|
889
|
+
end).should raise_error(
|
890
|
+
Addressable::Template::InvalidTemplateOperatorError
|
891
|
+
)
|
892
|
+
end
|
893
|
+
|
894
|
+
it "should raise an InvalidTemplateOperatorError" do
|
895
|
+
(lambda do
|
896
|
+
Addressable::Template.new(
|
897
|
+
"http://example.com/{-suffix|/|a,b,c}"
|
898
|
+
).extract(@uri)
|
899
|
+
end).should raise_error(
|
900
|
+
Addressable::Template::InvalidTemplateOperatorError
|
901
|
+
)
|
902
|
+
end
|
903
|
+
|
904
|
+
it "should raise an InvalidTemplateOperatorError" do
|
905
|
+
(lambda do
|
906
|
+
Addressable::Template.new(
|
907
|
+
"http://example.com/{-list|/|a,b,c}/"
|
908
|
+
).extract(@uri)
|
909
|
+
end).should raise_error(
|
910
|
+
Addressable::Template::InvalidTemplateOperatorError
|
911
|
+
)
|
912
|
+
end
|
913
|
+
end
|
914
|
+
|
915
|
+
describe Addressable::URI, "when given a mapping that contains an Array" do
|
916
|
+
before do
|
917
|
+
@mapping = {"query" => "an example search query".split(" ")}
|
918
|
+
end
|
919
|
+
|
920
|
+
it "should result in 'http://example.com/search/an+example+search+query/'" +
|
921
|
+
" when used to expand 'http://example.com/search/{-list|+|query}/'" do
|
922
|
+
Addressable::Template.new(
|
923
|
+
"http://example.com/search/{-list|+|query}/"
|
924
|
+
).expand(@mapping).to_str.should ==
|
925
|
+
"http://example.com/search/an+example+search+query/"
|
926
|
+
end
|
927
|
+
|
928
|
+
it "should result in 'http://example.com/search/an+example+search+query/'" +
|
929
|
+
" when used to expand 'http://example.com/search/{-list|+|query}/'" +
|
930
|
+
" with a NoOpProcessor" do
|
931
|
+
Addressable::Template.new(
|
932
|
+
"http://example.com/search/{-list|+|query}/"
|
933
|
+
).expand(@mapping, NoOpProcessor).to_str.should ==
|
934
|
+
"http://example.com/search/an+example+search+query/"
|
935
|
+
end
|
936
|
+
end
|
937
|
+
|
938
|
+
describe Addressable::URI, "when given an empty mapping" do
|
939
|
+
before do
|
940
|
+
@mapping = {}
|
941
|
+
end
|
942
|
+
|
943
|
+
it "should result in 'http://example.com/search/'" +
|
944
|
+
" when used to expand 'http://example.com/search/{-list|+|query}'" do
|
945
|
+
Addressable::Template.new(
|
946
|
+
"http://example.com/search/{-list|+|query}"
|
947
|
+
).expand(@mapping).to_str.should == "http://example.com/search/"
|
948
|
+
end
|
949
|
+
|
950
|
+
it "should result in 'http://example.com'" +
|
951
|
+
" when used to expand 'http://example.com{-prefix|/|foo}'" do
|
952
|
+
Addressable::Template.new(
|
953
|
+
"http://example.com{-prefix|/|foo}"
|
954
|
+
).expand(@mapping).to_str.should == "http://example.com"
|
955
|
+
end
|
956
|
+
|
957
|
+
it "should result in 'http://example.com'" +
|
958
|
+
" when used to expand 'http://example.com{-suffix|/|foo}'" do
|
959
|
+
Addressable::Template.new(
|
960
|
+
"http://example.com{-suffix|/|foo}"
|
961
|
+
).expand(@mapping).to_str.should == "http://example.com"
|
962
|
+
end
|
963
|
+
end
|
964
|
+
|
965
|
+
describe Addressable::URI, "when given the template pattern " +
|
966
|
+
"'http://example.com/search/{query}/' " +
|
967
|
+
"to be processed with the ExampleProcessor" do
|
968
|
+
before do
|
969
|
+
@pattern = "http://example.com/search/{query}/"
|
970
|
+
end
|
971
|
+
|
972
|
+
it "should expand to " +
|
973
|
+
"'http://example.com/search/an+example+search+query/' " +
|
974
|
+
"with a mapping of {\"query\" => \"an example search query\"} " do
|
975
|
+
Addressable::Template.new(
|
976
|
+
"http://example.com/search/{query}/"
|
977
|
+
).expand({
|
978
|
+
"query" => "an example search query"
|
979
|
+
}, ExampleProcessor).to_s.should ==
|
980
|
+
"http://example.com/search/an+example+search+query/"
|
981
|
+
end
|
982
|
+
|
983
|
+
it "should raise an error " +
|
984
|
+
"with a mapping of {\"query\" => \"invalid!\"}" do
|
985
|
+
(lambda do
|
986
|
+
Addressable::Template.new(
|
987
|
+
"http://example.com/search/{query}/"
|
988
|
+
).expand({"query" => "invalid!"}, ExampleProcessor).to_s
|
989
|
+
end).should raise_error(Addressable::Template::InvalidTemplateValueError)
|
990
|
+
end
|
991
|
+
end
|
992
|
+
|
993
|
+
# Section 3.3.1 of the URI Template draft v 01
|
994
|
+
describe Addressable::URI, "when given the mapping supplied in " +
|
995
|
+
"Section 3.3.1 of the URI Template draft v 01" do
|
996
|
+
before do
|
997
|
+
@mapping = {
|
998
|
+
"a" => "fred",
|
999
|
+
"b" => "barney",
|
1000
|
+
"c" => "cheeseburger",
|
1001
|
+
"d" => "one two three",
|
1002
|
+
"e" => "20% tricky",
|
1003
|
+
"f" => "",
|
1004
|
+
"20" => "this-is-spinal-tap",
|
1005
|
+
"scheme" => "https",
|
1006
|
+
"p" => "quote=to+be+or+not+to+be",
|
1007
|
+
"q" => "hullo#world"
|
1008
|
+
}
|
1009
|
+
end
|
1010
|
+
|
1011
|
+
it "should result in 'http://example.org/page1#fred' " +
|
1012
|
+
"when used to expand 'http://example.org/page1\#{a}'" do
|
1013
|
+
Addressable::Template.new(
|
1014
|
+
"http://example.org/page1\#{a}"
|
1015
|
+
).expand(@mapping).to_s.should == "http://example.org/page1#fred"
|
1016
|
+
end
|
1017
|
+
|
1018
|
+
it "should result in 'http://example.org/fred/barney/' " +
|
1019
|
+
"when used to expand 'http://example.org/{a}/{b}/'" do
|
1020
|
+
Addressable::Template.new(
|
1021
|
+
"http://example.org/{a}/{b}/"
|
1022
|
+
).expand(@mapping).to_s.should == "http://example.org/fred/barney/"
|
1023
|
+
end
|
1024
|
+
|
1025
|
+
it "should result in 'http://example.org/fredbarney/' " +
|
1026
|
+
"when used to expand 'http://example.org/{a}{b}/'" do
|
1027
|
+
Addressable::Template.new(
|
1028
|
+
"http://example.org/{a}{b}/"
|
1029
|
+
).expand(@mapping).to_s.should == "http://example.org/fredbarney/"
|
1030
|
+
end
|
1031
|
+
|
1032
|
+
it "should result in " +
|
1033
|
+
"'http://example.com/order/cheeseburger/cheeseburger/cheeseburger/' " +
|
1034
|
+
"when used to expand 'http://example.com/order/{c}/{c}/{c}/'" do
|
1035
|
+
Addressable::Template.new(
|
1036
|
+
"http://example.com/order/{c}/{c}/{c}/"
|
1037
|
+
).expand(@mapping).to_s.should ==
|
1038
|
+
"http://example.com/order/cheeseburger/cheeseburger/cheeseburger/"
|
1039
|
+
end
|
1040
|
+
|
1041
|
+
it "should result in 'http://example.org/one%20two%20three' " +
|
1042
|
+
"when used to expand 'http://example.org/{d}'" do
|
1043
|
+
Addressable::Template.new(
|
1044
|
+
"http://example.org/{d}"
|
1045
|
+
).expand(@mapping).to_s.should ==
|
1046
|
+
"http://example.org/one%20two%20three"
|
1047
|
+
end
|
1048
|
+
|
1049
|
+
it "should result in 'http://example.org/20%25%20tricky' " +
|
1050
|
+
"when used to expand 'http://example.org/{e}'" do
|
1051
|
+
Addressable::Template.new(
|
1052
|
+
"http://example.org/{e}"
|
1053
|
+
).expand(@mapping).to_s.should ==
|
1054
|
+
"http://example.org/20%25%20tricky"
|
1055
|
+
end
|
1056
|
+
|
1057
|
+
it "should result in 'http://example.com//' " +
|
1058
|
+
"when used to expand 'http://example.com/{f}/'" do
|
1059
|
+
Addressable::Template.new(
|
1060
|
+
"http://example.com/{f}/"
|
1061
|
+
).expand(@mapping).to_s.should ==
|
1062
|
+
"http://example.com//"
|
1063
|
+
end
|
1064
|
+
|
1065
|
+
it "should result in " +
|
1066
|
+
"'https://this-is-spinal-tap.example.org?date=&option=fred' " +
|
1067
|
+
"when used to expand " +
|
1068
|
+
"'{scheme}://{20}.example.org?date={wilma}&option={a}'" do
|
1069
|
+
Addressable::Template.new(
|
1070
|
+
"{scheme}://{20}.example.org?date={wilma}&option={a}"
|
1071
|
+
).expand(@mapping).to_s.should ==
|
1072
|
+
"https://this-is-spinal-tap.example.org?date=&option=fred"
|
1073
|
+
end
|
1074
|
+
|
1075
|
+
# The v 01 draft conflicts with the v 03 draft here.
|
1076
|
+
# The Addressable implementation uses v 03.
|
1077
|
+
it "should result in " +
|
1078
|
+
"'http://example.org?quote%3Dto%2Bbe%2Bor%2Bnot%2Bto%2Bbe' " +
|
1079
|
+
"when used to expand 'http://example.org?{p}'" do
|
1080
|
+
Addressable::Template.new(
|
1081
|
+
"http://example.org?{p}"
|
1082
|
+
).expand(@mapping).to_s.should ==
|
1083
|
+
"http://example.org?quote%3Dto%2Bbe%2Bor%2Bnot%2Bto%2Bbe"
|
1084
|
+
end
|
1085
|
+
|
1086
|
+
# The v 01 draft conflicts with the v 03 draft here.
|
1087
|
+
# The Addressable implementation uses v 03.
|
1088
|
+
it "should result in 'http://example.com/hullo%23world' " +
|
1089
|
+
"when used to expand 'http://example.com/{q}'" do
|
1090
|
+
Addressable::Template.new(
|
1091
|
+
"http://example.com/{q}"
|
1092
|
+
).expand(@mapping).to_s.should == "http://example.com/hullo%23world"
|
1093
|
+
end
|
1094
|
+
end
|
1095
|
+
|
1096
|
+
# Section 4.5 of the URI Template draft v 03
|
1097
|
+
describe Addressable::URI, "when given the mapping supplied in " +
|
1098
|
+
"Section 4.5 of the URI Template draft v 03" do
|
1099
|
+
before do
|
1100
|
+
@mapping = {
|
1101
|
+
"foo" => "ϓ",
|
1102
|
+
"bar" => "fred",
|
1103
|
+
"baz" => "10,20,30",
|
1104
|
+
"qux" => ["10","20","30"],
|
1105
|
+
"corge" => [],
|
1106
|
+
"grault" => "",
|
1107
|
+
"garply" => "a/b/c",
|
1108
|
+
"waldo" => "ben & jerrys",
|
1109
|
+
"fred" => ["fred", "", "wilma"],
|
1110
|
+
"plugh" => ["ẛ", "ṡ"],
|
1111
|
+
"1-a_b.c" => "200"
|
1112
|
+
}
|
1113
|
+
end
|
1114
|
+
|
1115
|
+
it "should result in 'http://example.org/?q=fred' " +
|
1116
|
+
"when used to expand 'http://example.org/?q={bar}'" do
|
1117
|
+
Addressable::Template.new(
|
1118
|
+
"http://example.org/?q={bar}"
|
1119
|
+
).expand(@mapping).to_s.should == "http://example.org/?q=fred"
|
1120
|
+
end
|
1121
|
+
|
1122
|
+
it "should result in '/' " +
|
1123
|
+
"when used to expand '/{xyzzy}'" do
|
1124
|
+
Addressable::Template.new(
|
1125
|
+
"/{xyzzy}"
|
1126
|
+
).expand(@mapping).to_s.should == "/"
|
1127
|
+
end
|
1128
|
+
|
1129
|
+
it "should result in " +
|
1130
|
+
"'http://example.org/?foo=%CE%8E&bar=fred&baz=10%2C20%2C30' " +
|
1131
|
+
"when used to expand " +
|
1132
|
+
"'http://example.org/?{-join|&|foo,bar,xyzzy,baz}'" do
|
1133
|
+
Addressable::Template.new(
|
1134
|
+
"http://example.org/?{-join|&|foo,bar,xyzzy,baz}"
|
1135
|
+
).expand(@mapping).to_s.should ==
|
1136
|
+
"http://example.org/?foo=%CE%8E&bar=fred&baz=10%2C20%2C30"
|
1137
|
+
end
|
1138
|
+
|
1139
|
+
it "should result in 'http://example.org/?d=10,20,30' " +
|
1140
|
+
"when used to expand 'http://example.org/?d={-list|,|qux}'" do
|
1141
|
+
Addressable::Template.new(
|
1142
|
+
"http://example.org/?d={-list|,|qux}"
|
1143
|
+
).expand(
|
1144
|
+
@mapping
|
1145
|
+
).to_s.should == "http://example.org/?d=10,20,30"
|
1146
|
+
end
|
1147
|
+
|
1148
|
+
it "should result in 'http://example.org/?d=10&d=20&d=30' " +
|
1149
|
+
"when used to expand 'http://example.org/?d={-list|&d=|qux}'" do
|
1150
|
+
Addressable::Template.new(
|
1151
|
+
"http://example.org/?d={-list|&d=|qux}"
|
1152
|
+
).expand(
|
1153
|
+
@mapping
|
1154
|
+
).to_s.should == "http://example.org/?d=10&d=20&d=30"
|
1155
|
+
end
|
1156
|
+
|
1157
|
+
it "should result in 'http://example.org/fredfred/a%2Fb%2Fc' " +
|
1158
|
+
"when used to expand 'http://example.org/{bar}{bar}/{garply}'" do
|
1159
|
+
Addressable::Template.new(
|
1160
|
+
"http://example.org/{bar}{bar}/{garply}"
|
1161
|
+
).expand(
|
1162
|
+
@mapping
|
1163
|
+
).to_s.should == "http://example.org/fredfred/a%2Fb%2Fc"
|
1164
|
+
end
|
1165
|
+
|
1166
|
+
it "should result in 'http://example.org/fred/fred//wilma' " +
|
1167
|
+
"when used to expand 'http://example.org/{bar}{-prefix|/|fred}'" do
|
1168
|
+
Addressable::Template.new(
|
1169
|
+
"http://example.org/{bar}{-prefix|/|fred}"
|
1170
|
+
).expand(
|
1171
|
+
@mapping
|
1172
|
+
).to_s.should == "http://example.org/fred/fred//wilma"
|
1173
|
+
end
|
1174
|
+
|
1175
|
+
it "should result in ':%E1%B9%A1:%E1%B9%A1:' " +
|
1176
|
+
"when used to expand '{-neg|:|corge}{-suffix|:|plugh}'" do
|
1177
|
+
Addressable::Template.new(
|
1178
|
+
"{-neg|:|corge}{-suffix|:|plugh}"
|
1179
|
+
).expand(
|
1180
|
+
@mapping
|
1181
|
+
).to_s.should == ":%E1%B9%A1:%E1%B9%A1:"
|
1182
|
+
end
|
1183
|
+
|
1184
|
+
it "should result in '../ben%20%26%20jerrys/' " +
|
1185
|
+
"when used to expand '../{waldo}/'" do
|
1186
|
+
Addressable::Template.new(
|
1187
|
+
"../{waldo}/"
|
1188
|
+
).expand(
|
1189
|
+
@mapping
|
1190
|
+
).to_s.should == "../ben%20%26%20jerrys/"
|
1191
|
+
end
|
1192
|
+
|
1193
|
+
it "should result in 'telnet:192.0.2.16:80' " +
|
1194
|
+
"when used to expand 'telnet:192.0.2.16{-opt|:80|grault}'" do
|
1195
|
+
Addressable::Template.new(
|
1196
|
+
"telnet:192.0.2.16{-opt|:80|grault}"
|
1197
|
+
).expand(
|
1198
|
+
@mapping
|
1199
|
+
).to_s.should == "telnet:192.0.2.16:80"
|
1200
|
+
end
|
1201
|
+
|
1202
|
+
it "should result in ':200:' " +
|
1203
|
+
"when used to expand ':{1-a_b.c}:'" do
|
1204
|
+
Addressable::Template.new(
|
1205
|
+
":{1-a_b.c}:"
|
1206
|
+
).expand(
|
1207
|
+
@mapping
|
1208
|
+
).to_s.should == ":200:"
|
1209
|
+
end
|
1210
|
+
end
|
1211
|
+
|
1212
|
+
describe Addressable::URI, "when given a mapping that contains a " +
|
1213
|
+
"template-var within a value" do
|
1214
|
+
before do
|
1215
|
+
@mapping = {
|
1216
|
+
"a" => "{b}",
|
1217
|
+
"b" => "barney",
|
1218
|
+
}
|
1219
|
+
end
|
1220
|
+
|
1221
|
+
it "should result in 'http://example.com/%7Bb%7D/barney/' " +
|
1222
|
+
"when used to expand 'http://example.com/{a}/{b}/'" do
|
1223
|
+
Addressable::Template.new(
|
1224
|
+
"http://example.com/{a}/{b}/"
|
1225
|
+
).expand(
|
1226
|
+
@mapping
|
1227
|
+
).to_s.should == "http://example.com/%7Bb%7D/barney/"
|
1228
|
+
end
|
1229
|
+
|
1230
|
+
it "should result in 'http://example.com//%7Bb%7D/' " +
|
1231
|
+
"when used to expand 'http://example.com/{-opt|foo|foo}/{a}/'" do
|
1232
|
+
Addressable::Template.new(
|
1233
|
+
"http://example.com/{-opt|foo|foo}/{a}/"
|
1234
|
+
).expand(
|
1235
|
+
@mapping
|
1236
|
+
).to_s.should == "http://example.com//%7Bb%7D/"
|
1237
|
+
end
|
1238
|
+
|
1239
|
+
it "should result in 'http://example.com//%7Bb%7D/' " +
|
1240
|
+
"when used to expand 'http://example.com/{-neg|foo|b}/{a}/'" do
|
1241
|
+
Addressable::Template.new(
|
1242
|
+
"http://example.com/{-neg|foo|b}/{a}/"
|
1243
|
+
).expand(
|
1244
|
+
@mapping
|
1245
|
+
).to_s.should == "http://example.com//%7Bb%7D/"
|
1246
|
+
end
|
1247
|
+
|
1248
|
+
it "should result in 'http://example.com//barney/%7Bb%7D/' " +
|
1249
|
+
"when used to expand 'http://example.com/{-prefix|/|b}/{a}/'" do
|
1250
|
+
Addressable::Template.new(
|
1251
|
+
"http://example.com/{-prefix|/|b}/{a}/"
|
1252
|
+
).expand(
|
1253
|
+
@mapping
|
1254
|
+
).to_s.should == "http://example.com//barney/%7Bb%7D/"
|
1255
|
+
end
|
1256
|
+
|
1257
|
+
it "should result in 'http://example.com/barney//%7Bb%7D/' " +
|
1258
|
+
"when used to expand 'http://example.com/{-suffix|/|b}/{a}/'" do
|
1259
|
+
Addressable::Template.new(
|
1260
|
+
"http://example.com/{-suffix|/|b}/{a}/"
|
1261
|
+
).expand(
|
1262
|
+
@mapping
|
1263
|
+
).to_s.should == "http://example.com/barney//%7Bb%7D/"
|
1264
|
+
end
|
1265
|
+
|
1266
|
+
it "should result in 'http://example.com/%7Bb%7D/?b=barney&c=42' " +
|
1267
|
+
"when used to expand 'http://example.com/{a}/?{-join|&|b,c=42}'" do
|
1268
|
+
Addressable::Template.new(
|
1269
|
+
"http://example.com/{a}/?{-join|&|b,c=42}"
|
1270
|
+
).expand(
|
1271
|
+
@mapping
|
1272
|
+
).to_s.should == "http://example.com/%7Bb%7D/?b=barney&c=42"
|
1273
|
+
end
|
1274
|
+
|
1275
|
+
it "should result in 'http://example.com/42/?b=barney' " +
|
1276
|
+
"when used to expand 'http://example.com/{c=42}/?{-join|&|b}'" do
|
1277
|
+
Addressable::Template.new(
|
1278
|
+
"http://example.com/{c=42}/?{-join|&|b}"
|
1279
|
+
).expand(@mapping).to_s.should == "http://example.com/42/?b=barney"
|
1280
|
+
end
|
1281
|
+
end
|
1282
|
+
|
1283
|
+
describe Addressable::URI, "when given a single variable mapping" do
|
1284
|
+
before do
|
1285
|
+
@mapping = {
|
1286
|
+
"foo" => "fred"
|
1287
|
+
}
|
1288
|
+
end
|
1289
|
+
|
1290
|
+
it "should result in 'fred' when used to expand '{foo}'" do
|
1291
|
+
Addressable::Template.new(
|
1292
|
+
"{foo}"
|
1293
|
+
).expand(@mapping).to_s.should == "fred"
|
1294
|
+
end
|
1295
|
+
|
1296
|
+
it "should result in 'wilma' when used to expand '{bar=wilma}'" do
|
1297
|
+
Addressable::Template.new(
|
1298
|
+
"{bar=wilma}"
|
1299
|
+
).expand(@mapping).to_s.should == "wilma"
|
1300
|
+
end
|
1301
|
+
|
1302
|
+
it "should result in '' when used to expand '{baz}'" do
|
1303
|
+
Addressable::Template.new(
|
1304
|
+
"{baz}"
|
1305
|
+
).expand(@mapping).to_s.should == ""
|
1306
|
+
end
|
1307
|
+
end
|
1308
|
+
|
1309
|
+
describe Addressable::URI, "when given a simple mapping" do
|
1310
|
+
before do
|
1311
|
+
@mapping = {
|
1312
|
+
"foo" => "fred",
|
1313
|
+
"bar" => "barney",
|
1314
|
+
"baz" => ""
|
1315
|
+
}
|
1316
|
+
end
|
1317
|
+
|
1318
|
+
it "should result in 'foo=fred&bar=barney&baz=' when used to expand " +
|
1319
|
+
"'{-join|&|foo,bar,baz,qux}'" do
|
1320
|
+
Addressable::Template.new(
|
1321
|
+
"{-join|&|foo,bar,baz,qux}"
|
1322
|
+
).expand(@mapping).to_s.should == "foo=fred&bar=barney&baz="
|
1323
|
+
end
|
1324
|
+
|
1325
|
+
it "should result in 'bar=barney' when used to expand " +
|
1326
|
+
"'{-join|&|bar}'" do
|
1327
|
+
Addressable::Template.new(
|
1328
|
+
"{-join|&|bar}"
|
1329
|
+
).expand(@mapping).to_s.should == "bar=barney"
|
1330
|
+
end
|
1331
|
+
|
1332
|
+
it "should result in '' when used to expand " +
|
1333
|
+
"'{-join|&|qux}'" do
|
1334
|
+
Addressable::Template.new(
|
1335
|
+
"{-join|&|qux}"
|
1336
|
+
).expand(@mapping).to_s.should == ""
|
1337
|
+
end
|
1338
|
+
end
|
1339
|
+
|
1340
|
+
describe Addressable::URI, "extracting defaults from a pattern" do
|
1341
|
+
before do
|
1342
|
+
@template = Addressable::Template.new("{foo}{bar=baz}{-opt|found|cond}")
|
1343
|
+
end
|
1344
|
+
|
1345
|
+
it "should extract default value" do
|
1346
|
+
@template.variable_defaults.should == {"bar" => "baz"}
|
1347
|
+
end
|
1348
|
+
end
|
1349
|
+
|
1350
|
+
describe Addressable::URI, "when given a mapping with symbol keys" do
|
1351
|
+
before do
|
1352
|
+
@mapping = { :name => "fred" }
|
1353
|
+
end
|
1354
|
+
|
1355
|
+
it "should result in 'fred' when used to expand '{foo}'" do
|
1356
|
+
Addressable::Template.new(
|
1357
|
+
"{name}"
|
1358
|
+
).expand(@mapping).to_s.should == "fred"
|
1359
|
+
end
|
1360
|
+
end
|
1361
|
+
|
1362
|
+
describe Addressable::URI, "when given a mapping with bogus keys" do
|
1363
|
+
before do
|
1364
|
+
@mapping = { Object.new => "fred" }
|
1365
|
+
end
|
1366
|
+
|
1367
|
+
it "should raise an error" do
|
1368
|
+
(lambda do
|
1369
|
+
Addressable::Template.new(
|
1370
|
+
"{name}"
|
1371
|
+
).expand(@mapping)
|
1372
|
+
end).should raise_error(TypeError)
|
1373
|
+
end
|
1374
|
+
end
|
1375
|
+
|
1376
|
+
describe Addressable::URI, "when given a mapping with numeric values" do
|
1377
|
+
before do
|
1378
|
+
@mapping = { :id => 123 }
|
1379
|
+
end
|
1380
|
+
|
1381
|
+
it "should result in 'fred' when used to expand '{foo}'" do
|
1382
|
+
Addressable::Template.new(
|
1383
|
+
"{id}"
|
1384
|
+
).expand(@mapping).to_s.should == "123"
|
1385
|
+
end
|
1386
|
+
end
|
1387
|
+
|
1388
|
+
describe Addressable::URI, "when given a mapping containing values " +
|
1389
|
+
"that are already percent-encoded" do
|
1390
|
+
before do
|
1391
|
+
@mapping = {
|
1392
|
+
"a" => "%7Bb%7D"
|
1393
|
+
}
|
1394
|
+
end
|
1395
|
+
|
1396
|
+
it "should result in 'http://example.com/%257Bb%257D/' " +
|
1397
|
+
"when used to expand 'http://example.com/{a}/'" do
|
1398
|
+
Addressable::Template.new(
|
1399
|
+
"http://example.com/{a}/"
|
1400
|
+
).expand(@mapping).to_s.should == "http://example.com/%257Bb%257D/"
|
1401
|
+
end
|
1402
|
+
end
|
1403
|
+
|
1404
|
+
describe Addressable::URI, "when given a pattern with bogus operators" do
|
1405
|
+
it "should raise an InvalidTemplateOperatorError" do
|
1406
|
+
(lambda do
|
1407
|
+
Addressable::Template.new(
|
1408
|
+
"http://example.com/{-bogus|/|a,b,c}/"
|
1409
|
+
).expand({
|
1410
|
+
"a" => "a", "b" => "b", "c" => "c"
|
1411
|
+
})
|
1412
|
+
end).should raise_error(
|
1413
|
+
Addressable::Template::InvalidTemplateOperatorError
|
1414
|
+
)
|
1415
|
+
end
|
1416
|
+
|
1417
|
+
it "should raise an InvalidTemplateOperatorError" do
|
1418
|
+
(lambda do
|
1419
|
+
Addressable::Template.new(
|
1420
|
+
"http://example.com/{-prefix|/|a,b,c}/"
|
1421
|
+
).expand({
|
1422
|
+
"a" => "a", "b" => "b", "c" => "c"
|
1423
|
+
})
|
1424
|
+
end).should raise_error(
|
1425
|
+
Addressable::Template::InvalidTemplateOperatorError
|
1426
|
+
)
|
1427
|
+
end
|
1428
|
+
|
1429
|
+
it "should raise an InvalidTemplateOperatorError" do
|
1430
|
+
(lambda do
|
1431
|
+
Addressable::Template.new(
|
1432
|
+
"http://example.com/{-suffix|/|a,b,c}/"
|
1433
|
+
).expand({
|
1434
|
+
"a" => "a", "b" => "b", "c" => "c"
|
1435
|
+
})
|
1436
|
+
end).should raise_error(
|
1437
|
+
Addressable::Template::InvalidTemplateOperatorError
|
1438
|
+
)
|
1439
|
+
end
|
1440
|
+
|
1441
|
+
it "should raise an InvalidTemplateOperatorError" do
|
1442
|
+
(lambda do
|
1443
|
+
Addressable::Template.new(
|
1444
|
+
"http://example.com/{-join|/|a,b,c}/"
|
1445
|
+
).expand({
|
1446
|
+
"a" => ["a"], "b" => ["b"], "c" => "c"
|
1447
|
+
})
|
1448
|
+
end).should raise_error(
|
1449
|
+
Addressable::Template::InvalidTemplateOperatorError
|
1450
|
+
)
|
1451
|
+
end
|
1452
|
+
|
1453
|
+
it "should raise an InvalidTemplateOperatorError" do
|
1454
|
+
(lambda do
|
1455
|
+
Addressable::Template.new(
|
1456
|
+
"http://example.com/{-list|/|a,b,c}/"
|
1457
|
+
).expand({
|
1458
|
+
"a" => ["a"], "b" => ["b"], "c" => "c"
|
1459
|
+
})
|
1460
|
+
end).should raise_error(
|
1461
|
+
Addressable::Template::InvalidTemplateOperatorError
|
1462
|
+
)
|
1463
|
+
end
|
1464
|
+
end
|
1465
|
+
|
1466
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1467
|
+
before do
|
1468
|
+
@initial_template = Addressable::Template.new(
|
1469
|
+
"http://example.com/{one}/{two}/"
|
1470
|
+
)
|
1471
|
+
@partial_template = @initial_template.partial_expand({"one" => "1"})
|
1472
|
+
end
|
1473
|
+
|
1474
|
+
it "should produce the same result when fully expanded" do
|
1475
|
+
@initial_template.expand({"one" => "1", "two" => "2"}).should ==
|
1476
|
+
@partial_template.expand({"two" => "2"})
|
1477
|
+
end
|
1478
|
+
|
1479
|
+
it "should raise an error if the template is expanded with bogus values" do
|
1480
|
+
(lambda do
|
1481
|
+
@initial_template.expand({"one" => Object.new, "two" => Object.new})
|
1482
|
+
end).should raise_error(TypeError)
|
1483
|
+
(lambda do
|
1484
|
+
@partial_template.expand({"two" => Object.new})
|
1485
|
+
end).should raise_error(TypeError)
|
1486
|
+
end
|
1487
|
+
end
|
1488
|
+
|
1489
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1490
|
+
before do
|
1491
|
+
@initial_template = Addressable::Template.new(
|
1492
|
+
"http://example.com/{one}/{two}/"
|
1493
|
+
)
|
1494
|
+
@partial_template = @initial_template.partial_expand({"two" => "2"})
|
1495
|
+
end
|
1496
|
+
|
1497
|
+
it "should produce the same result when fully expanded" do
|
1498
|
+
@initial_template.expand({"one" => "1", "two" => "2"}).should ==
|
1499
|
+
@partial_template.expand({"one" => "1"})
|
1500
|
+
end
|
1501
|
+
end
|
1502
|
+
|
1503
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1504
|
+
before do
|
1505
|
+
@initial_template = Addressable::Template.new(
|
1506
|
+
"http://example.com/{one}/{two}/"
|
1507
|
+
)
|
1508
|
+
@partial_template = @initial_template.partial_expand({"two" => "2"})
|
1509
|
+
end
|
1510
|
+
|
1511
|
+
it "should produce the same result when fully expanded" do
|
1512
|
+
@initial_template.expand({"one" => "1", "two" => "2"}).should ==
|
1513
|
+
@partial_template.expand({"one" => "1"})
|
1514
|
+
end
|
1515
|
+
end
|
1516
|
+
|
1517
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1518
|
+
before do
|
1519
|
+
@initial_template = Addressable::Template.new(
|
1520
|
+
"http://example.com/{one=1}/{two=2}/"
|
1521
|
+
)
|
1522
|
+
@partial_template = @initial_template.partial_expand({"one" => "3"})
|
1523
|
+
end
|
1524
|
+
|
1525
|
+
it "should produce the same result when fully expanded" do
|
1526
|
+
@initial_template.expand({"one" => "3", "two" => "4"}).should ==
|
1527
|
+
@partial_template.expand({"two" => "4"})
|
1528
|
+
end
|
1529
|
+
|
1530
|
+
it "should produce the correct result when fully expanded" do
|
1531
|
+
@partial_template.expand({}).should === "http://example.com/3/2/"
|
1532
|
+
end
|
1533
|
+
end
|
1534
|
+
|
1535
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1536
|
+
before do
|
1537
|
+
@initial_template = Addressable::Template.new(
|
1538
|
+
"http://example.com/{one=1}/{two=2}/"
|
1539
|
+
)
|
1540
|
+
@partial_template = @initial_template.partial_expand({"two" => "4"})
|
1541
|
+
end
|
1542
|
+
|
1543
|
+
it "should produce the same result when fully expanded" do
|
1544
|
+
@initial_template.expand({"one" => "3", "two" => "4"}).should ==
|
1545
|
+
@partial_template.expand({"one" => "3"})
|
1546
|
+
end
|
1547
|
+
|
1548
|
+
it "should produce the correct result when fully expanded" do
|
1549
|
+
@partial_template.expand({}).should === "http://example.com/1/4/"
|
1550
|
+
end
|
1551
|
+
end
|
1552
|
+
|
1553
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1554
|
+
before do
|
1555
|
+
@initial_template = Addressable::Template.new(
|
1556
|
+
"http://example.com/{-opt|found|one,two,three}"
|
1557
|
+
)
|
1558
|
+
@partial_template = @initial_template.partial_expand({})
|
1559
|
+
end
|
1560
|
+
|
1561
|
+
it "should produce the same result when fully expanded" do
|
1562
|
+
@initial_template.expand({"one" => "1"}).to_str.should ==
|
1563
|
+
@partial_template.expand({"two" => "2"}).to_str
|
1564
|
+
end
|
1565
|
+
|
1566
|
+
it "should produce the correct result when fully expanded" do
|
1567
|
+
@partial_template.expand({}).to_str.should == "http://example.com/"
|
1568
|
+
end
|
1569
|
+
|
1570
|
+
it "should produce the correct result when fully expanded" do
|
1571
|
+
@partial_template.expand({"one" => "1"}).to_str.should ==
|
1572
|
+
"http://example.com/found"
|
1573
|
+
end
|
1574
|
+
|
1575
|
+
it "should produce the correct result when fully expanded" do
|
1576
|
+
@partial_template.expand({"two" => "2"}).to_str.should ==
|
1577
|
+
"http://example.com/found"
|
1578
|
+
end
|
1579
|
+
|
1580
|
+
it "should produce the correct result when fully expanded" do
|
1581
|
+
@partial_template.expand({"three" => "3"}).to_str.should ==
|
1582
|
+
"http://example.com/found"
|
1583
|
+
end
|
1584
|
+
|
1585
|
+
it "should produce the correct result when fully expanded" do
|
1586
|
+
@partial_template.expand({"four" => "4"}).to_str.should ==
|
1587
|
+
"http://example.com/"
|
1588
|
+
end
|
1589
|
+
|
1590
|
+
it "should produce the correct result when fully expanded" do
|
1591
|
+
@partial_template.expand({"one" => "1", "two" => "2"}).to_str.should ==
|
1592
|
+
"http://example.com/found"
|
1593
|
+
end
|
1594
|
+
end
|
1595
|
+
|
1596
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1597
|
+
before do
|
1598
|
+
@initial_template = Addressable::Template.new(
|
1599
|
+
"http://example.com/{-opt|found|one,two,three}"
|
1600
|
+
)
|
1601
|
+
@partial_template = @initial_template.partial_expand({"one" => "1"})
|
1602
|
+
end
|
1603
|
+
|
1604
|
+
it "should produce the same result when fully expanded" do
|
1605
|
+
@initial_template.expand({"one" => "1"}).to_str.should ==
|
1606
|
+
@partial_template.expand({"two" => "2"}).to_str
|
1607
|
+
end
|
1608
|
+
|
1609
|
+
it "should produce the correct result when fully expanded" do
|
1610
|
+
@partial_template.expand({}).to_str.should == "http://example.com/found"
|
1611
|
+
end
|
1612
|
+
|
1613
|
+
it "should produce the correct pattern" do
|
1614
|
+
@partial_template.pattern.should == "http://example.com/found"
|
1615
|
+
end
|
1616
|
+
end
|
1617
|
+
|
1618
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1619
|
+
before do
|
1620
|
+
@initial_template = Addressable::Template.new(
|
1621
|
+
"http://example.com/{-neg|notfound|one,two,three}"
|
1622
|
+
)
|
1623
|
+
@partial_template = @initial_template.partial_expand({})
|
1624
|
+
end
|
1625
|
+
|
1626
|
+
it "should produce the same result when fully expanded" do
|
1627
|
+
@initial_template.expand({"one" => "1"}).to_str.should ==
|
1628
|
+
@partial_template.expand({"two" => "2"}).to_str
|
1629
|
+
end
|
1630
|
+
|
1631
|
+
it "should produce the correct result when fully expanded" do
|
1632
|
+
@partial_template.expand({}).to_str.should == "http://example.com/notfound"
|
1633
|
+
end
|
1634
|
+
|
1635
|
+
it "should produce the correct result when fully expanded" do
|
1636
|
+
@partial_template.expand({"one" => "1"}).to_str.should ==
|
1637
|
+
"http://example.com/"
|
1638
|
+
end
|
1639
|
+
|
1640
|
+
it "should produce the correct result when fully expanded" do
|
1641
|
+
@partial_template.expand({"two" => "2"}).to_str.should ==
|
1642
|
+
"http://example.com/"
|
1643
|
+
end
|
1644
|
+
|
1645
|
+
it "should produce the correct result when fully expanded" do
|
1646
|
+
@partial_template.expand({"three" => "3"}).to_str.should ==
|
1647
|
+
"http://example.com/"
|
1648
|
+
end
|
1649
|
+
|
1650
|
+
it "should produce the correct result when fully expanded" do
|
1651
|
+
@partial_template.expand({"four" => "4"}).to_str.should ==
|
1652
|
+
"http://example.com/notfound"
|
1653
|
+
end
|
1654
|
+
|
1655
|
+
it "should produce the correct result when fully expanded" do
|
1656
|
+
@partial_template.expand({"one" => "1", "two" => "2"}).to_str.should ==
|
1657
|
+
"http://example.com/"
|
1658
|
+
end
|
1659
|
+
end
|
1660
|
+
|
1661
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1662
|
+
before do
|
1663
|
+
@initial_template = Addressable::Template.new(
|
1664
|
+
"http://example.com/{-neg|notfound|one,two,three}"
|
1665
|
+
)
|
1666
|
+
@partial_template = @initial_template.partial_expand({"one" => "1"})
|
1667
|
+
end
|
1668
|
+
|
1669
|
+
it "should produce the same result when fully expanded" do
|
1670
|
+
@initial_template.expand({"one" => "1"}).to_str.should ==
|
1671
|
+
@partial_template.expand({"two" => "2"}).to_str
|
1672
|
+
end
|
1673
|
+
|
1674
|
+
it "should produce the correct result when fully expanded" do
|
1675
|
+
@partial_template.expand({}).to_str.should == "http://example.com/"
|
1676
|
+
end
|
1677
|
+
|
1678
|
+
it "should produce the correct pattern" do
|
1679
|
+
@partial_template.pattern.should == "http://example.com/"
|
1680
|
+
end
|
1681
|
+
end
|
1682
|
+
|
1683
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1684
|
+
before do
|
1685
|
+
@initial_template = Addressable::Template.new(
|
1686
|
+
"http://example.com/?{-prefix|x=|one}"
|
1687
|
+
)
|
1688
|
+
@partial_template = @initial_template.partial_expand({})
|
1689
|
+
end
|
1690
|
+
|
1691
|
+
it "should produce the same result when fully expanded" do
|
1692
|
+
@initial_template.expand({"one" => "1"}).to_str.should ==
|
1693
|
+
@partial_template.expand({"one" => "1"}).to_str
|
1694
|
+
end
|
1695
|
+
|
1696
|
+
it "should produce the correct result when fully expanded" do
|
1697
|
+
@partial_template.expand({}).to_str.should == "http://example.com/?"
|
1698
|
+
end
|
1699
|
+
|
1700
|
+
it "should produce the correct result when fully expanded" do
|
1701
|
+
@partial_template.expand({"one" => "1"}).to_str.should ==
|
1702
|
+
"http://example.com/?x=1"
|
1703
|
+
end
|
1704
|
+
|
1705
|
+
it "should produce the correct result when fully expanded" do
|
1706
|
+
@partial_template.expand({"two" => "2"}).to_str.should ==
|
1707
|
+
"http://example.com/?"
|
1708
|
+
end
|
1709
|
+
|
1710
|
+
it "should produce the correct result when fully expanded" do
|
1711
|
+
@partial_template.expand({"one" => "1", "two" => "2"}).to_str.should ==
|
1712
|
+
"http://example.com/?x=1"
|
1713
|
+
end
|
1714
|
+
end
|
1715
|
+
|
1716
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1717
|
+
before do
|
1718
|
+
@initial_template = Addressable::Template.new(
|
1719
|
+
"http://example.com/?{-prefix|x=|one}"
|
1720
|
+
)
|
1721
|
+
@partial_template = @initial_template.partial_expand({"one" => "1"})
|
1722
|
+
end
|
1723
|
+
|
1724
|
+
it "should produce the same result when fully expanded" do
|
1725
|
+
@initial_template.expand({"one" => "1"}).to_str.should ==
|
1726
|
+
@partial_template.expand({}).to_str
|
1727
|
+
end
|
1728
|
+
|
1729
|
+
it "should produce the correct result when fully expanded" do
|
1730
|
+
@partial_template.expand({}).to_str.should == "http://example.com/?x=1"
|
1731
|
+
end
|
1732
|
+
|
1733
|
+
it "should produce the correct pattern" do
|
1734
|
+
@partial_template.pattern.should == "http://example.com/?x=1"
|
1735
|
+
end
|
1736
|
+
end
|
1737
|
+
|
1738
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1739
|
+
before do
|
1740
|
+
@initial_template = Addressable::Template.new(
|
1741
|
+
"http://example.com/?{-suffix|=x|one}"
|
1742
|
+
)
|
1743
|
+
@partial_template = @initial_template.partial_expand({})
|
1744
|
+
end
|
1745
|
+
|
1746
|
+
it "should produce the same result when fully expanded" do
|
1747
|
+
@initial_template.expand({"one" => "1"}).to_str.should ==
|
1748
|
+
@partial_template.expand({"one" => "1"}).to_str
|
1749
|
+
end
|
1750
|
+
|
1751
|
+
it "should produce the correct result when fully expanded" do
|
1752
|
+
@partial_template.expand({}).to_str.should == "http://example.com/?"
|
1753
|
+
end
|
1754
|
+
|
1755
|
+
it "should produce the correct result when fully expanded" do
|
1756
|
+
@partial_template.expand({"one" => "1"}).to_str.should ==
|
1757
|
+
"http://example.com/?1=x"
|
1758
|
+
end
|
1759
|
+
|
1760
|
+
it "should produce the correct result when fully expanded" do
|
1761
|
+
@partial_template.expand({"two" => "2"}).to_str.should ==
|
1762
|
+
"http://example.com/?"
|
1763
|
+
end
|
1764
|
+
|
1765
|
+
it "should produce the correct result when fully expanded" do
|
1766
|
+
@partial_template.expand({"one" => "1", "two" => "2"}).to_str.should ==
|
1767
|
+
"http://example.com/?1=x"
|
1768
|
+
end
|
1769
|
+
end
|
1770
|
+
|
1771
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1772
|
+
before do
|
1773
|
+
@initial_template = Addressable::Template.new(
|
1774
|
+
"http://example.com/?{-suffix|=x|one}"
|
1775
|
+
)
|
1776
|
+
@partial_template = @initial_template.partial_expand({"one" => "1"})
|
1777
|
+
end
|
1778
|
+
|
1779
|
+
it "should produce the same result when fully expanded" do
|
1780
|
+
@initial_template.expand({"one" => "1"}).to_str.should ==
|
1781
|
+
@partial_template.expand({}).to_str
|
1782
|
+
end
|
1783
|
+
|
1784
|
+
it "should produce the correct result when fully expanded" do
|
1785
|
+
@partial_template.expand({}).to_str.should == "http://example.com/?1=x"
|
1786
|
+
end
|
1787
|
+
|
1788
|
+
it "should produce the correct pattern" do
|
1789
|
+
@partial_template.pattern.should == "http://example.com/?1=x"
|
1790
|
+
end
|
1791
|
+
end
|
1792
|
+
|
1793
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1794
|
+
before do
|
1795
|
+
@initial_template = Addressable::Template.new(
|
1796
|
+
"http://example.com/?{-join|&|one}"
|
1797
|
+
)
|
1798
|
+
@partial_template = @initial_template.partial_expand({})
|
1799
|
+
end
|
1800
|
+
|
1801
|
+
it "should produce the same result when fully expanded" do
|
1802
|
+
@initial_template.expand({"one" => "1"}).to_str.should ==
|
1803
|
+
@partial_template.expand({"one" => "1"}).to_str
|
1804
|
+
end
|
1805
|
+
|
1806
|
+
it "should produce the correct result when fully expanded" do
|
1807
|
+
@partial_template.expand({}).to_str.should == "http://example.com/?"
|
1808
|
+
end
|
1809
|
+
|
1810
|
+
it "should produce the correct result when fully expanded" do
|
1811
|
+
@partial_template.pattern.should == @initial_template.pattern
|
1812
|
+
end
|
1813
|
+
end
|
1814
|
+
|
1815
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1816
|
+
before do
|
1817
|
+
@initial_template = Addressable::Template.new(
|
1818
|
+
"http://example.com/?{-join|&|one,two}"
|
1819
|
+
)
|
1820
|
+
@partial_template = @initial_template.partial_expand({"one" => "1"})
|
1821
|
+
end
|
1822
|
+
|
1823
|
+
it "should produce the same result when fully expanded" do
|
1824
|
+
@initial_template.expand({"one" => "1", "two" => "2"}).to_str.should ==
|
1825
|
+
@partial_template.expand({"two" => "2"}).to_str
|
1826
|
+
end
|
1827
|
+
|
1828
|
+
it "should produce the correct result when fully expanded" do
|
1829
|
+
@partial_template.expand({}).to_str.should == "http://example.com/?one=1"
|
1830
|
+
end
|
1831
|
+
end
|
1832
|
+
|
1833
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1834
|
+
before do
|
1835
|
+
@initial_template = Addressable::Template.new(
|
1836
|
+
"http://example.com/?{-join|&|one,two}"
|
1837
|
+
)
|
1838
|
+
@partial_template = @initial_template.partial_expand({"two" => "2"})
|
1839
|
+
end
|
1840
|
+
|
1841
|
+
it "should produce the same result when fully expanded" do
|
1842
|
+
@initial_template.expand({"one" => "1", "two" => "2"}).to_str.should ==
|
1843
|
+
@partial_template.expand({"one" => "1"}).to_str
|
1844
|
+
end
|
1845
|
+
|
1846
|
+
it "should produce the correct result when fully expanded" do
|
1847
|
+
@partial_template.expand({}).to_str.should == "http://example.com/?two=2"
|
1848
|
+
end
|
1849
|
+
end
|
1850
|
+
|
1851
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1852
|
+
before do
|
1853
|
+
@initial_template = Addressable::Template.new(
|
1854
|
+
"http://example.com/?{-join|&|one,two,three}"
|
1855
|
+
)
|
1856
|
+
@partial_template = @initial_template.partial_expand({"one" => "1"})
|
1857
|
+
end
|
1858
|
+
|
1859
|
+
it "should produce the same result when fully expanded" do
|
1860
|
+
@initial_template.expand({
|
1861
|
+
"one" => "1", "two" => "2", "three" => "3"
|
1862
|
+
}).to_str.should ==
|
1863
|
+
@partial_template.expand({"two" => "2", "three" => "3"}).to_str
|
1864
|
+
end
|
1865
|
+
|
1866
|
+
it "should produce the correct result when fully expanded" do
|
1867
|
+
@partial_template.expand({}).to_str.should == "http://example.com/?one=1"
|
1868
|
+
end
|
1869
|
+
|
1870
|
+
it "should produce the correct result when fully expanded" do
|
1871
|
+
@partial_template.expand({"two" => "2"}).to_str.should ==
|
1872
|
+
"http://example.com/?one=1&two=2"
|
1873
|
+
end
|
1874
|
+
|
1875
|
+
it "should produce the correct result when fully expanded" do
|
1876
|
+
@partial_template.expand({"three" => "3"}).to_str.should ==
|
1877
|
+
"http://example.com/?one=1&three=3"
|
1878
|
+
end
|
1879
|
+
end
|
1880
|
+
|
1881
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1882
|
+
before do
|
1883
|
+
@initial_template = Addressable::Template.new(
|
1884
|
+
"http://example.com/?{-join|&|one,two,three}"
|
1885
|
+
)
|
1886
|
+
@partial_template = @initial_template.partial_expand({"two" => "2"})
|
1887
|
+
end
|
1888
|
+
|
1889
|
+
it "should produce the same result when fully expanded" do
|
1890
|
+
@initial_template.expand({
|
1891
|
+
"one" => "1", "two" => "2", "three" => "3"
|
1892
|
+
}).to_str.should ==
|
1893
|
+
@partial_template.expand({"one" => "1", "three" => "3"}).to_str
|
1894
|
+
end
|
1895
|
+
|
1896
|
+
it "should produce the correct result when fully expanded" do
|
1897
|
+
@partial_template.expand({}).to_str.should == "http://example.com/?two=2"
|
1898
|
+
end
|
1899
|
+
|
1900
|
+
it "should produce the correct result when fully expanded" do
|
1901
|
+
@partial_template.expand({"one" => "1"}).to_str.should ==
|
1902
|
+
"http://example.com/?one=1&two=2"
|
1903
|
+
end
|
1904
|
+
|
1905
|
+
it "should produce the correct result when fully expanded" do
|
1906
|
+
@partial_template.expand({"three" => "3"}).to_str.should ==
|
1907
|
+
"http://example.com/?two=2&three=3"
|
1908
|
+
end
|
1909
|
+
end
|
1910
|
+
|
1911
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1912
|
+
before do
|
1913
|
+
@initial_template = Addressable::Template.new(
|
1914
|
+
"http://example.com/?{-join|&|one,two,three}"
|
1915
|
+
)
|
1916
|
+
@partial_template = @initial_template.partial_expand({"three" => "3"})
|
1917
|
+
end
|
1918
|
+
|
1919
|
+
it "should produce the same result when fully expanded" do
|
1920
|
+
@initial_template.expand({
|
1921
|
+
"one" => "1", "two" => "2", "three" => "3"
|
1922
|
+
}).to_str.should ==
|
1923
|
+
@partial_template.expand({"one" => "1", "two" => "2"}).to_str
|
1924
|
+
end
|
1925
|
+
|
1926
|
+
it "should produce the correct result when fully expanded" do
|
1927
|
+
@partial_template.expand({}).to_str.should == "http://example.com/?three=3"
|
1928
|
+
end
|
1929
|
+
|
1930
|
+
it "should produce the correct result when fully expanded" do
|
1931
|
+
@partial_template.expand({"one" => "1"}).to_str.should ==
|
1932
|
+
"http://example.com/?one=1&three=3"
|
1933
|
+
end
|
1934
|
+
|
1935
|
+
it "should produce the correct result when fully expanded" do
|
1936
|
+
@partial_template.expand({"two" => "2"}).to_str.should ==
|
1937
|
+
"http://example.com/?two=2&three=3"
|
1938
|
+
end
|
1939
|
+
end
|
1940
|
+
|
1941
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1942
|
+
before do
|
1943
|
+
@initial_template = Addressable::Template.new(
|
1944
|
+
"http://example.com/?{-join|&|one,two,three}"
|
1945
|
+
)
|
1946
|
+
@partial_template = @initial_template.partial_expand({
|
1947
|
+
"one" => "1", "two" => "2"
|
1948
|
+
})
|
1949
|
+
end
|
1950
|
+
|
1951
|
+
it "should produce the same result when fully expanded" do
|
1952
|
+
@initial_template.expand({
|
1953
|
+
"one" => "1", "two" => "2", "three" => "3"
|
1954
|
+
}).to_str.should ==
|
1955
|
+
@partial_template.expand({"three" => "3"}).to_str
|
1956
|
+
end
|
1957
|
+
|
1958
|
+
it "should produce the correct result when fully expanded" do
|
1959
|
+
@partial_template.expand({}).to_str.should ==
|
1960
|
+
"http://example.com/?one=1&two=2"
|
1961
|
+
end
|
1962
|
+
|
1963
|
+
it "should produce the correct result when fully expanded" do
|
1964
|
+
@partial_template.expand({"three" => "3"}).to_str.should ==
|
1965
|
+
"http://example.com/?one=1&two=2&three=3"
|
1966
|
+
end
|
1967
|
+
end
|
1968
|
+
|
1969
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1970
|
+
before do
|
1971
|
+
@initial_template = Addressable::Template.new(
|
1972
|
+
"http://example.com/?{-join|&|one,two,three}"
|
1973
|
+
)
|
1974
|
+
@partial_template = @initial_template.partial_expand({
|
1975
|
+
"one" => "1", "three" => "3"
|
1976
|
+
})
|
1977
|
+
end
|
1978
|
+
|
1979
|
+
it "should produce the same result when fully expanded" do
|
1980
|
+
@initial_template.expand({
|
1981
|
+
"one" => "1", "two" => "2", "three" => "3"
|
1982
|
+
}).to_str.should ==
|
1983
|
+
@partial_template.expand({"two" => "2"}).to_str
|
1984
|
+
end
|
1985
|
+
|
1986
|
+
it "should produce the correct result when fully expanded" do
|
1987
|
+
@partial_template.expand({}).to_str.should ==
|
1988
|
+
"http://example.com/?one=1&three=3"
|
1989
|
+
end
|
1990
|
+
|
1991
|
+
it "should produce the correct result when fully expanded" do
|
1992
|
+
@partial_template.expand({"two" => "2"}).to_str.should ==
|
1993
|
+
"http://example.com/?one=1&two=2&three=3"
|
1994
|
+
end
|
1995
|
+
end
|
1996
|
+
|
1997
|
+
describe Addressable::Template, "with a partially expanded template" do
|
1998
|
+
before do
|
1999
|
+
@initial_template = Addressable::Template.new(
|
2000
|
+
"http://example.com/?{-join|&|one,two,three}"
|
2001
|
+
)
|
2002
|
+
@partial_template = @initial_template.partial_expand({
|
2003
|
+
"two" => "2", "three" => "3"
|
2004
|
+
})
|
2005
|
+
end
|
2006
|
+
|
2007
|
+
it "should produce the same result when fully expanded" do
|
2008
|
+
@initial_template.expand({
|
2009
|
+
"one" => "1", "two" => "2", "three" => "3"
|
2010
|
+
}).to_str.should ==
|
2011
|
+
@partial_template.expand({"one" => "1"}).to_str
|
2012
|
+
end
|
2013
|
+
|
2014
|
+
it "should produce the correct result when fully expanded" do
|
2015
|
+
@partial_template.expand({}).to_str.should ==
|
2016
|
+
"http://example.com/?two=2&three=3"
|
2017
|
+
end
|
2018
|
+
|
2019
|
+
it "should produce the correct result when fully expanded" do
|
2020
|
+
@partial_template.expand({"one" => "1"}).to_str.should ==
|
2021
|
+
"http://example.com/?one=1&two=2&three=3"
|
2022
|
+
end
|
2023
|
+
end
|
2024
|
+
|
2025
|
+
describe Addressable::Template, "with a partially expanded template" do
|
2026
|
+
before do
|
2027
|
+
@initial_template = Addressable::Template.new(
|
2028
|
+
"http://example.com/?{-join|&|one,two,three}"
|
2029
|
+
)
|
2030
|
+
end
|
2031
|
+
|
2032
|
+
it "should raise an error when partially expanding a bogus operator" do
|
2033
|
+
(lambda do
|
2034
|
+
@initial_template.partial_expand({"one" => ["1"]})
|
2035
|
+
end).should raise_error(
|
2036
|
+
Addressable::Template::InvalidTemplateOperatorError
|
2037
|
+
)
|
2038
|
+
(lambda do
|
2039
|
+
@initial_template.partial_expand({"two" => "2", "three" => ["3"]})
|
2040
|
+
end).should raise_error(
|
2041
|
+
Addressable::Template::InvalidTemplateOperatorError
|
2042
|
+
)
|
2043
|
+
end
|
2044
|
+
end
|
2045
|
+
|
2046
|
+
describe Addressable::Template, "with a partially expanded template" do
|
2047
|
+
before do
|
2048
|
+
@initial_template = Addressable::Template.new(
|
2049
|
+
"http://example.com/{-list|/|numbers}/{-list|/|letters}/"
|
2050
|
+
)
|
2051
|
+
@partial_template = @initial_template.partial_expand({})
|
2052
|
+
end
|
2053
|
+
|
2054
|
+
it "should produce the same result when fully expanded" do
|
2055
|
+
@initial_template.expand({
|
2056
|
+
"numbers" => ["1", "2", "3"], "letters" => ["a", "b", "c"]
|
2057
|
+
}).to_str.should == @partial_template.expand({
|
2058
|
+
"numbers" => ["1", "2", "3"], "letters" => ["a", "b", "c"]
|
2059
|
+
}).to_str
|
2060
|
+
end
|
2061
|
+
|
2062
|
+
it "should produce the correct result when fully expanded" do
|
2063
|
+
@partial_template.expand({}).to_str.should == "http://example.com///"
|
2064
|
+
end
|
2065
|
+
|
2066
|
+
it "should produce the correct result when fully expanded" do
|
2067
|
+
@partial_template.pattern.should == @initial_template.pattern
|
2068
|
+
end
|
2069
|
+
end
|
2070
|
+
|
2071
|
+
describe Addressable::Template, "with a partially expanded template" do
|
2072
|
+
before do
|
2073
|
+
@initial_template = Addressable::Template.new(
|
2074
|
+
"http://example.com/{-list|/|numbers}/{-list|/|letters}/"
|
2075
|
+
)
|
2076
|
+
@partial_template = @initial_template.partial_expand({
|
2077
|
+
"numbers" => ["1", "2", "3"]
|
2078
|
+
})
|
2079
|
+
end
|
2080
|
+
|
2081
|
+
it "should produce the same result when fully expanded" do
|
2082
|
+
@initial_template.expand({
|
2083
|
+
"numbers" => ["1", "2", "3"], "letters" => ["a", "b", "c"]
|
2084
|
+
}).to_str.should == @partial_template.expand({
|
2085
|
+
"letters" => ["a", "b", "c"]
|
2086
|
+
}).to_str
|
2087
|
+
end
|
2088
|
+
|
2089
|
+
it "should produce the correct result when fully expanded" do
|
2090
|
+
@partial_template.expand({}).to_str.should == "http://example.com/1/2/3//"
|
2091
|
+
end
|
2092
|
+
end
|
2093
|
+
|
2094
|
+
describe Addressable::Template, "with a partially expanded template" do
|
2095
|
+
before do
|
2096
|
+
@initial_template = Addressable::Template.new(
|
2097
|
+
"http://example.com/{-list|/|numbers}/{-list|/|letters}/"
|
2098
|
+
)
|
2099
|
+
@partial_template = @initial_template.partial_expand({
|
2100
|
+
"letters" => ["a", "b", "c"]
|
2101
|
+
})
|
2102
|
+
end
|
2103
|
+
|
2104
|
+
it "should produce the same result when fully expanded" do
|
2105
|
+
@initial_template.expand({
|
2106
|
+
"numbers" => ["1", "2", "3"], "letters" => ["a", "b", "c"]
|
2107
|
+
}).to_str.should == @partial_template.expand({
|
2108
|
+
"numbers" => ["1", "2", "3"]
|
2109
|
+
}).to_str
|
2110
|
+
end
|
2111
|
+
|
2112
|
+
it "should produce the correct result when fully expanded" do
|
2113
|
+
@partial_template.expand({}).to_str.should == "http://example.com//a/b/c/"
|
2114
|
+
end
|
2115
|
+
end
|
2116
|
+
|
2117
|
+
describe Addressable::Template, "with a partially expanded template" do
|
2118
|
+
before do
|
2119
|
+
@initial_template = Addressable::Template.new(
|
2120
|
+
"http://example.com/{-list|/|numbers}/{-list|/|letters}/"
|
2121
|
+
)
|
2122
|
+
end
|
2123
|
+
|
2124
|
+
it "should raise an error when partially expanding a bogus operator" do
|
2125
|
+
(lambda do
|
2126
|
+
@initial_template.partial_expand({"numbers" => "1"})
|
2127
|
+
end).should raise_error(
|
2128
|
+
Addressable::Template::InvalidTemplateOperatorError
|
2129
|
+
)
|
2130
|
+
(lambda do
|
2131
|
+
@initial_template.partial_expand({"letters" => "a"})
|
2132
|
+
end).should raise_error(
|
2133
|
+
Addressable::Template::InvalidTemplateOperatorError
|
2134
|
+
)
|
2135
|
+
end
|
2136
|
+
end
|
2137
|
+
|
2138
|
+
describe Addressable::Template, "with a partially expanded template" do
|
2139
|
+
before do
|
2140
|
+
@initial_template = Addressable::Template.new(
|
2141
|
+
"http://example.com/{-bogus|/|one,two}/"
|
2142
|
+
)
|
2143
|
+
end
|
2144
|
+
|
2145
|
+
it "should raise an error when partially expanding a bogus operator" do
|
2146
|
+
(lambda do
|
2147
|
+
@initial_template.partial_expand({"one" => "1"})
|
2148
|
+
end).should raise_error(
|
2149
|
+
Addressable::Template::InvalidTemplateOperatorError
|
2150
|
+
)
|
2151
|
+
end
|
2152
|
+
end
|