Chowlett
Chowlett

Reputation: 46667

Rails 3 routes with extended regex :constraints - bug?

I have the following route in my Rails 3 app.

post 'games/:id/:task/:card_id' => 'games#perform', :as => :perform

...which allows, obviously, such requests as button_to("Foo", {card_id=>2, :action=>:perform, :task=>"foo"}), mapping to the URL /games/1/foo/2.

I'd like to restrict the set of tasks the route matches. The Rails API docs indicate that "Constraints can include the ‘ignorecase’ and ‘extended syntax’ regular expression modifiers". However, the following works as expected:

post 'games/:id/:task/:card_id' => 'games#perform', :as => :perform, :constraints => {:task => /(foo|bar)/}

But the following doesn't:

post 'games/:id/:task/:card_id' => 'games#perform', :as => :perform, :constraints => {:task => /(foo|
                                                                                                 bar)/x}

In the latter case, the button_to link above produces the URL: /games/perform?card_id=2&task=foo.

Is this a bug, or am I doing something wrong?

Upvotes: 1

Views: 829

Answers (1)

smathy
smathy

Reputation: 27971

Yeah, there's a bug in the RegexpWithNamedGroups processing for Ruby 1.8.x because it fakes the named regexp groups syntax of 1.9 in a way that is incompatible with regexp modifiers.

The problem here is that with 1.8 Rails uses a simple index of the paren group within the regexp to map to the name. When you add a modifier to a regexp, internally this creates an additional group which throws the index off by one.

Workaround right now is to use 1.9, or no modifier.

Upvotes: 1

Related Questions