# Unexpected routes behavior

**URL:** <https://www.ruby-forum.com/t/unexpected-routes-behavior/112956>\
**Category:** Rails\
**Created:** [August 24, 2007, 11:07pm UTC](https://www.ruby-forum.com/t/unexpected-routes-behavior/112956 "2007-08-24T23:07:36Z")\
**Posts on this page:** 5\
**Page:** 1

<div class="post-metadata">

**Author:** ![steve\_odom](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/6a8cbe/32.png) [@steve\_odom](https://www.ruby-forum.com/u/steve_odom)\
**Post date:** [August 24, 2007, 11:07pm UTC](https://www.ruby-forum.com/t/unexpected-routes-behavior/112956/1 "2007-08-24T23:07:36Z")

</div>

I must be doing something wrong in my routing.

In my routes I have…

map.with\_options :controller =\> ‘users’, :action =\> ‘revisions’ do |  
user|  
user.remedy\_revisions ‘users/:user\_id/  
revisions/:klass’, :klass =\> “remedy”  
user.symptom\_revisions ‘users/:user\_id/  
revisions/:klass’, :klass =\> “symptom”  
end

…which allows in my view to have two links like:

\<%= link\_to ‘remedy’, remedy\_revisions\_path(@user) -%\> |  
\<%= link\_to ‘symptom’, symptom\_revisions\_path(@user) -%\>

The problem is when clicked, the :klass param is always passed as  
“remedy”, even on the symptom\_revisions\_path.

If I move reverse the order of the 2 named routes, ala…  
map.with\_options :controller =\> ‘users’, :action =\> ‘revisions’ do |  
user|  
user.symptom\_revisions ‘users/:user\_id/  
revisions/:klass’, :klass =\> “symptom”  
user.remedy\_revisions ‘users/:user\_id/  
revisions/:klass’, :klass =\> “remedy”  
end

Then the symptom :klass param is always passed.

do I have the syntax wrong? I tried the routing lines as separate  
lines outside of the with\_options block, but same problem.

any ideas?

Steve

---

<div class="post-metadata">

**Author:** ![steve\_odom](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/6a8cbe/32.png) [@steve\_odom](https://www.ruby-forum.com/u/steve_odom)\
**Post date:** [August 24, 2007, 11:22pm UTC](https://www.ruby-forum.com/t/unexpected-routes-behavior/112956/2 "2007-08-24T23:22:38Z")

</div>

I found if I do the route this way…

map.with\_options :controller =\> ‘users’, :action =\> ‘revisions’ do |  
user|  
user.remedy\_revisions ‘user/:id/:klass/revisions’, :klass =\>  
‘remedy’  
user.symptom\_revisions ‘user/:id/:klass/revisions’, :klass =\>  
‘symptom’  
end

(putting the :klass parameter before the string literal ‘revisions’,)  
then it works fine.

Steve

---

<div class="post-metadata">

**Author:** ![steve\_odom](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/6a8cbe/32.png) [@steve\_odom](https://www.ruby-forum.com/u/steve_odom)\
**Post date:** [August 24, 2007, 11:39pm UTC](https://www.ruby-forum.com/t/unexpected-routes-behavior/112956/3 "2007-08-24T23:39:39Z")

</div>

Not quite. Now I’m getting this warning:

Route segment “:klass” cannot be optional because it precedes a  
required segment. This segment will be required.  
Route segment “:klass” cannot be optional because it precedes a  
required segment. This segment will be required.

Any suggestions?

Steve

---

<div class="post-metadata">

**Author:** ![steve\_odom](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/6a8cbe/32.png) [@steve\_odom](https://www.ruby-forum.com/u/steve_odom)\
**Post date:** [August 25, 2007, 3:28am UTC](https://www.ruby-forum.com/t/unexpected-routes-behavior/112956/4 "2007-08-25T03:28:14Z")

</div>

thanks, David. You’re exactly right. I was hoping to do it without  
passing in the additional parameter, but oh well.

Steve

---

<div class="post-metadata">

**Author:** ![steve\_odom](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/s/6a8cbe/32.png) [@steve\_odom](https://www.ruby-forum.com/u/steve_odom)\
**Post date:** [August 25, 2007, 1:02am UTC](https://www.ruby-forum.com/t/unexpected-routes-behavior/112956/5 "2007-08-25T01:02:02Z")

</div>

Hi –

On Fri, 24 Aug 2007, steve odom wrote:

> Steve
> 
> > end
> > 
> > > In my routes I have…
> > 
> > > revisions/:klass’, :klass =\> “symptom”  
> > > user.remedy\_revisions ‘users/:user\_id/  
> > > revisions/:klass’, :klass =\> “remedy”  
> > > end
> > 
> > > Then the symptom :klass param is always passed.
> > 
> > > do I have the syntax wrong? I tried the routing lines as separate  
> > > lines outside of the with\_options block, but same problem.
> > 
> > > any ideas?

My reading of this is as follows. Both your named routes are  
generating the same thing:

/users/1/revisions

When it comes time to recognize this path, it matches whichever of the  
two is listed first, and sets the optional :klass segment to whatever  
that one specifies as the default.

So you need the actual generation of the route to provide enough  
information so that the recognition engine can make the right choice.

What I would recommend would be a single named route, like this:

map.with\_options :controller =\> ‘users’,  
:action =\> ‘revisions’ do |user|  
user.revisions’/users/:user\_id/revisions/:klass’  
end

and then in the view:

\<%= link\_to ‘remedy’, revisions\_path(@user, “remedy”) -%\> |  
\<%= link\_to ‘symptom’, revisions\_path(@user, “symptom”) -%\>

which is short for:

revisions\_path(:user\_id =\> @user, :klass =\> “remedy”)

David

–

- Books:  
RAILS ROUTING (new! [http://www.awprofessional.com/title/0321509242](http://www.awprofessional.com/title/0321509242))  
RUBY FOR RAILS ([Ruby for Rails](http://www.manning.com/black))
- Ruby/Rails training  
& consulting: Ruby Power and Light, LLC ([http://www.rubypal.com](http://www.rubypal.com))
