http_router 0.3.9 → 0.3.10

Sign up to get free protection for your applications and to get access to all the features.
data/README.rdoc CHANGED
@@ -10,7 +10,7 @@ This is very new code. Lots of stuff probably doesn't work right. I will likely
10
10
 
11
11
  == Features
12
12
 
13
- * Supports variables, and globbing.
13
+ * Supports variables, and globbing, both named and unnamed.
14
14
  * Regex support for variables.
15
15
  * Request condition support.
16
16
  * Partial matches.
@@ -0,0 +1,9 @@
1
+ require 'http_router'
2
+
3
+ run HttpRouter.new {
4
+ get('/:').to { |env| [200, {'Content-type' => 'text/plain'}, ["my variables are\n#{env['router.params'].inspect}\n"]]}
5
+ }
6
+
7
+ # crapbook-pro:~ joshua$ curl http://127.0.0.1:3000/heyguys
8
+ # my variables are
9
+ # {:$1=>"heyguys"}
@@ -1,8 +1,8 @@
1
1
  class HttpRouter
2
2
  class Path
3
- attr_reader :parts, :route
4
- def initialize(route, path, parts)
5
- @route, @path, @parts = route, path, parts
3
+ attr_reader :parts, :route, :splitting_indexes
4
+ def initialize(route, path, parts, splitting_indexes)
5
+ @route, @path, @parts, @splitting_indexes = route, path, parts, splitting_indexes
6
6
  if duplicate_variable_names = variable_names.dup.uniq!
7
7
  raise AmbiguousVariableException.new("You have duplicate variable name present: #{duplicate_variable_names.join(', ')}")
8
8
  end
@@ -21,6 +21,7 @@ class HttpRouter
21
21
  def initialize(path, params, matched_path, remaining_path = nil)
22
22
  raise if matched_path.nil?
23
23
  super
24
+ path.splitting_indexes and path.splitting_indexes.each{|i| params[i] = params[i].split('/')}
24
25
  @params_as_hash = path.variable_names.zip(params).inject({}) {|h, (k,v)| h[k] = v; h }
25
26
  end
26
27
 
@@ -293,25 +293,46 @@ class HttpRouter
293
293
  path[-2, 2] == '/?' && path.slice!(-2, 2)
294
294
  end
295
295
 
296
+ def anonymous_variable(pos)
297
+ "$#{pos}"
298
+ end
299
+
296
300
  def compile_paths
297
301
  paths = HttpRouter::OptionalCompiler.new(@path).paths
298
302
  paths.map do |path|
303
+ splitting_indexes = []
304
+ variable_counter = 0
305
+ counter = 0
299
306
  original_path = path.dup
300
307
  split_path = router.split(path)
308
+ index = 0
301
309
  new_path = split_path.map do |part|
302
- case part
303
- when /^:([a-zA-Z_0-9]+)$/
304
- v_name = $1.to_sym
310
+ r = case part
311
+ when /^:([a-zA-Z_0-9]*)$/
312
+ v_name = ($1.empty? ? anonymous_variable(counter += 1) : $1).to_sym
305
313
  router.variable(v_name, @matches_with[v_name])
306
- when /^\*([a-zA-Z_0-9]+)$/
307
- v_name = $1.to_sym
308
- router.glob(v_name, @matches_with[v_name])
314
+ when /^\*([a-zA-Z_0-9]*)$/
315
+ if index != split_path.size - 1
316
+ v_name = ($1.empty? ? anonymous_variable(counter += 1) : $1).to_sym
317
+ splitting_indexes << variable_counter
318
+ remaining_path_parts = split_path[index + 1, split_path.size]
319
+ look_ahead_variable = remaining_path_parts.find{|p| p[0] == ?: || p[0] == ?*}
320
+ remaining_matcher = split_path[index + 1, look_ahead_variable ? remaining_path_parts.index(look_ahead_variable) : split_path.size].join('/')
321
+ remaining_path_parts.index(look_ahead_variable) if look_ahead_variable
322
+ router.variable(v_name, /^(#{@matches_with[v_name] || '[^\/]*?'}\/)+(?=#{Regexp.quote(remaining_matcher)})/)
323
+ else
324
+ v_name = ($1.empty? ? anonymous_variable(counter += 1) : $1).to_sym
325
+ router.glob(v_name, @matches_with[v_name])
326
+ end
309
327
  else
310
328
  generate_interstitial_parts(part)
311
329
  end
330
+ variable_counter += Array(r).select{|part| part.is_a?(Variable)}.size
331
+ index += 1
332
+ r
312
333
  end
313
334
  new_path.flatten!
314
- Path.new(self, original_path, new_path)
335
+ Path.new(self, original_path, new_path, splitting_indexes.empty? ? nil : splitting_indexes)
315
336
  end
316
337
  end
317
338
 
@@ -1,4 +1,4 @@
1
1
  # encoding: utf-8
2
2
  class HttpRouter #:nodoc
3
- VERSION = '0.3.9'
3
+ VERSION = '0.3.10'
4
4
  end
@@ -209,6 +209,19 @@ describe "HttpRouter#recognize" do
209
209
  @router.recognize(Rack::MockRequest.env_for('/foo/id')).dest.should == :test2
210
210
  end
211
211
 
212
+ it "should recognize /foo/: and map it to $1" do
213
+ @router.add("/foo/:").to(:test2)
214
+ @router.recognize(Rack::MockRequest.env_for('/foo/id')).dest.should == :test2
215
+ @router.recognize(Rack::MockRequest.env_for('/foo/id')).params_as_hash[:$1].should == 'id'
216
+ end
217
+
218
+ it "should recognize /foo/:/: and map it to $1 and $2" do
219
+ @router.add("/foo/:/:").to(:test2)
220
+ @router.recognize(Rack::MockRequest.env_for('/foo/id/what')).dest.should == :test2
221
+ @router.recognize(Rack::MockRequest.env_for('/foo/id/what')).params_as_hash[:$1].should == 'id'
222
+ @router.recognize(Rack::MockRequest.env_for('/foo/id/what')).params_as_hash[:$2].should == 'what'
223
+ end
224
+
212
225
  it "should recognize '/:variable'" do
213
226
  route = @router.add('/:variable').to(:test)
214
227
  response = @router.recognize(Rack::MockRequest.env_for('/%E6%AE%BA%E3%81%99'))
@@ -290,6 +303,13 @@ describe "HttpRouter#recognize" do
290
303
  response.params.should == [['one', 'two', 'three']]
291
304
  end
292
305
 
306
+ it "should recognize" do
307
+ route = @router.add('/test/*variable/test').to(:test)
308
+ response = @router.recognize(Rack::MockRequest.env_for('/test/one/two/three/test'))
309
+ response.route.should == route
310
+ response.params.should == [['one', 'two', 'three']]
311
+ end
312
+
293
313
  it "should recognize with a regexp" do
294
314
  route = @router.add('/test/*variable/anymore').matching(:variable => /\d+/).to(:test)
295
315
  response = @router.recognize(Rack::MockRequest.env_for('/test/123/345/567/anymore'))
@@ -298,6 +318,19 @@ describe "HttpRouter#recognize" do
298
318
  response = @router.recognize(Rack::MockRequest.env_for('/test/123/345/567'))
299
319
  response.should be_nil
300
320
  end
321
+
322
+ it "should recognize /foo/*/test and map it to $1" do
323
+ @router.add("/foo/*/test").to(:test2)
324
+ @router.recognize(Rack::MockRequest.env_for('/foo/id1/id2/test')).dest.should == :test2
325
+ @router.recognize(Rack::MockRequest.env_for('/foo/id1/id2/test')).params_as_hash[:$1].should == ['id1', 'id2']
326
+ end
327
+
328
+ it "should recognize /foo/*/what/: and map it to $1 and $2" do
329
+ @router.add("/foo/*/what/:").to(:test2)
330
+ @router.recognize(Rack::MockRequest.env_for('/foo/id1/id2/what/more')).dest.should == :test2
331
+ @router.recognize(Rack::MockRequest.env_for('/foo/id1/id2/what/more')).params_as_hash[:$1].should == ['id1', 'id2']
332
+ @router.recognize(Rack::MockRequest.env_for('/foo/id1/id2/what/more')).params_as_hash[:$2].should == 'more'
333
+ end
301
334
  end
302
335
 
303
336
  end
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: http_router
3
3
  version: !ruby/object:Gem::Version
4
- hash: 1
4
+ hash: 7
5
5
  prerelease: false
6
6
  segments:
7
7
  - 0
8
8
  - 3
9
- - 9
10
- version: 0.3.9
9
+ - 10
10
+ version: 0.3.10
11
11
  platform: ruby
12
12
  authors:
13
13
  - Joshua Hull
@@ -15,7 +15,7 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2010-08-05 00:00:00 -07:00
18
+ date: 2010-08-06 00:00:00 -07:00
19
19
  default_executable:
20
20
  dependencies:
21
21
  - !ruby/object:Gem::Dependency
@@ -151,6 +151,7 @@ files:
151
151
  - examples/static/images/cat1.jpg
152
152
  - examples/static/images/cat2.jpg
153
153
  - examples/static/images/cat3.jpg
154
+ - examples/unnamed_variable.ru
154
155
  - examples/variable.ru
155
156
  - examples/variable_with_regex.ru
156
157
  - ext/gem_rake.rb