Skip to content
This repository
Browse code

Ensure shortcuts inside resources also generates helpers.

  • Loading branch information...
commit 4a90ecb3adff8426aeddee0594c2b68f408e4af1 1 parent edba51c
José Valim authored August 24, 2010
87  actionpack/lib/action_dispatch/routing/mapper.rb
@@ -43,9 +43,9 @@ def constraint_args(constraint, request)
43 43
       class Mapping #:nodoc:
44 44
         IGNORE_OPTIONS = [:to, :as, :via, :on, :constraints, :defaults, :only, :except, :anchor, :shallow, :shallow_path, :shallow_prefix]
45 45
 
46  
-        def initialize(set, scope, args)
47  
-          @set, @scope    = set, scope
48  
-          @path, @options = extract_path_and_options(args)
  46
+        def initialize(set, scope, path, options)
  47
+          @set, @scope, @options = set, scope, options
  48
+          @path = normalize_path(path)
49 49
           normalize_options!
50 50
         end
51 51
 
@@ -54,31 +54,16 @@ def to_route
54 54
         end
55 55
 
56 56
         private
57  
-          def extract_path_and_options(args)
58  
-            options = args.extract_options!
59  
-
60  
-            if using_to_shorthand?(args, options)
61  
-              path, to = options.find { |name, value| name.is_a?(String) }
62  
-              options.merge!(:to => to).delete(path) if path
63  
-            else
64  
-              path = args.first
65  
-            end
66  
-
67  
-            if path.match(':controller')
68  
-              raise ArgumentError, ":controller segment is not allowed within a namespace block" if @scope[:module]
69  
-
70  
-              # Add a default constraint for :controller path segments that matches namespaced
71  
-              # controllers with default routes like :controller/:action/:id(.:format), e.g:
72  
-              # GET /admin/products/show/1
73  
-              # => { :controller => 'admin/products', :action => 'show', :id => '1' }
74  
-              options.reverse_merge!(:controller => /.+?/)
75  
-            end
76  
-
77  
-            [ normalize_path(path), options ]
78  
-          end
79 57
 
80 58
           def normalize_options!
81 59
             path_without_format = @path.sub(/\(\.:format\)$/, '')
  60
+            @options = (@scope[:options] || {}).merge(@options)
  61
+
  62
+            if @scope[:as] && !@options[:as].blank?
  63
+              @options[:as] = "#{@scope[:as]}_#{@options[:as]}"
  64
+            elsif @scope[:as] && @options[:as] == ""
  65
+              @options[:as] = @scope[:as].to_s
  66
+            end
82 67
 
83 68
             if using_match_shorthand?(path_without_format, @options)
84 69
               to_shorthand    = @options[:to].blank?
@@ -89,11 +74,6 @@ def normalize_options!
89 74
             @options.merge!(default_controller_and_action(to_shorthand))
90 75
           end
91 76
 
92  
-          # match "account" => "account#index"
93  
-          def using_to_shorthand?(args, options)
94  
-            args.empty? && options.present?
95  
-          end
96  
-
97 77
           # match "account/overview"
98 78
           def using_match_shorthand?(path, options)
99 79
             path && options.except(:via, :anchor, :to, :as).empty? && path =~ %r{^/[\w\/]+$}
@@ -101,7 +81,19 @@ def using_match_shorthand?(path, options)
101 81
 
102 82
           def normalize_path(path)
103 83
             raise ArgumentError, "path is required" if @scope[:path].blank? && path.blank?
104  
-            Mapper.normalize_path("#{@scope[:path]}/#{path}")
  84
+            path = Mapper.normalize_path("#{@scope[:path]}/#{path}")
  85
+
  86
+            if path.match(':controller')
  87
+              raise ArgumentError, ":controller segment is not allowed within a namespace block" if @scope[:module]
  88
+
  89
+              # Add a default constraint for :controller path segments that matches namespaced
  90
+              # controllers with default routes like :controller/:action/:id(.:format), e.g:
  91
+              # GET /admin/products/show/1
  92
+              # => { :controller => 'admin/products', :action => 'show', :id => '1' }
  93
+              @options.reverse_merge!(:controller => /.+?/)
  94
+            end
  95
+
  96
+            path
105 97
           end
106 98
 
107 99
           def app
@@ -233,8 +225,8 @@ def root(options = {})
233 225
           match '/', options.reverse_merge(:as => :root)
234 226
         end
235 227
 
236  
-        def match(*args)
237  
-          mapping = Mapping.new(@set, @scope, args).to_route
  228
+        def match(path, options=nil)
  229
+          mapping = Mapping.new(@set, @scope, path, options || {}).to_route
238 230
           @set.add_route(*mapping)
239 231
           self
240 232
         end
@@ -389,21 +381,6 @@ def defaults(defaults = {})
389 381
           scope(:defaults => defaults) { yield }
390 382
         end
391 383
 
392  
-        def match(*args)
393  
-          options = args.extract_options!
394  
-
395  
-          options = (@scope[:options] || {}).merge(options)
396  
-
397  
-          if @scope[:as] && !options[:as].blank?
398  
-            options[:as] = "#{@scope[:as]}_#{options[:as]}"
399  
-          elsif @scope[:as] && options[:as] == ""
400  
-            options[:as] = @scope[:as].to_s
401  
-          end
402  
-
403  
-          args.push(options)
404  
-          super(*args)
405  
-        end
406  
-
407 384
         private
408 385
           def scope_options
409 386
             @scope_options ||= private_methods.grep(/^merge_(.+)_scope$/) { $1.to_sym }
@@ -957,10 +934,24 @@ def name_for_action(action, as=nil)
957 934
           end
958 935
       end
959 936
 
  937
+      module Shorthand
  938
+        def match(*args)
  939
+          if args.size == 1 && args.last.is_a?(Hash)
  940
+            options  = args.pop
  941
+            path, to = options.find { |name, value| name.is_a?(String) }
  942
+            options.merge!(:to => to).delete(path)
  943
+            super(path, options)
  944
+          else
  945
+            super
  946
+          end
  947
+        end
  948
+      end
  949
+
960 950
       include Base
961 951
       include HttpHelpers
962 952
       include Scoping
963 953
       include Resources
  954
+      include Shorthand
964 955
     end
965 956
   end
966 957
 end
8  actionpack/test/dispatch/routing_test.rb
@@ -203,9 +203,9 @@ def self.matches?(request)
203 203
       end
204 204
 
205 205
       resources :customers do
206  
-        get "recent" => "customers#recent", :as => :recent, :on => :collection
207  
-        get "profile" => "customers#profile", :as => :profile, :on => :member
208  
-        post "preview" => "customers#preview", :as => :preview, :on => :new
  206
+        get "recent" => "customers#recent", :on => :collection
  207
+        get "profile" => "customers#profile", :on => :member
  208
+        post "preview" => "customers#preview", :as => :another_preview, :on => :new
209 209
         resource :avatar do
210 210
           get "thumbnail(.:format)" => "avatars#thumbnail", :as => :thumbnail, :on => :member
211 211
         end
@@ -1564,7 +1564,7 @@ def test_custom_resource_routes_are_scoped
1564 1564
     with_test_routes do
1565 1565
       assert_equal '/customers/recent', recent_customers_path
1566 1566
       assert_equal '/customers/1/profile', profile_customer_path(:id => '1')
1567  
-      assert_equal '/customers/new/preview', preview_new_customer_path
  1567
+      assert_equal '/customers/new/preview', another_preview_new_customer_path
1568 1568
       assert_equal '/customers/1/avatar/thumbnail.jpg', thumbnail_customer_avatar_path(:customer_id => '1', :format => :jpg)
1569 1569
       assert_equal '/customers/1/invoices/outstanding', outstanding_customer_invoices_path(:customer_id => '1')
1570 1570
       assert_equal '/customers/1/invoices/2/print', print_customer_invoice_path(:customer_id => '1', :id => '2')

0 notes on commit 4a90ecb

Please sign in to comment.
Something went wrong with that request. Please try again.