On 13 May 2012, at 04:10, Rodrigo Rosenfeld Rosas wrote:

> What I was suggesting is that we changed the generated routes.rb so that the 
> Rails 1 style route could be written as
> 
> match ':controller(/:action(/:id))'

Whether you write it with or without :format it ends up being the same route - 
the mapper checks for the presence of the :format key in the path. The 
generator adds the :format to make it explicitly visible what's happening.

Some history on why there's an optional format would probably useful here. We 
used to generate both formatted routes and non-formatted routes, e.g. you'd 
have formatted_product_path(@product, :json) and product_path(@product). Upon 
investigation[1][2] it was discovered that this took up significant amount of 
memory and was changed to an optional segment[3] in the Rails 2.3 release.

> As well as mentioning and explaining the "format" option, like some of these 
> examples:
> 
> post '/products/:id.:format' => 'products#show', as: :field, constraints: 
> {id: /\d+/} # format is required
> post '/products/:id' => 'products#show', format: true, as: :field, 
> constraints: {id: /\d+/} # this is equivalent
> post '/products/:id.json' => 'products#show', format: :json # it only answers 
> to json format
> post '/products/:id' => 'products#show', format: :json # the same with a 
> shorter URL but still allowing you to cache the result and use the correct 
> content-type
> 
> But then I decided to test it and I was surprised that it doesn't make any 
> difference if you use caches_page.
> Also, there are more weird rules with regards to page or action caching. The 
> routes rules don't seem to be respected if you use caching.
> 
> Consider this example:
> 
> get '/products' => 'products#list', format: :json
> 
> try to GET /products with caches_page enabled and you won't get a 
> 'application/json' content-type in the next responses because it won't 
> probably even read the routes rules.

Page caching is explicitly designed to avoid hitting the Rails stack - you need 
to setup Apache or nginx to serve the cached files from the format-less path 
with the appropriate content type. Action caching should just avoid the page 
rendering - if you can reproduce a case where a JSON request is action cached 
and returns an incorrect content type when serving the cached file then please 
create a new issue in the tracker.

> Also, if you GET /products.html not only it accepts this request but the 
> content-type will be 'text/html' instead of 'application/json' (independent 
> from caching).

That's because you're defining a default format for the route not a constraint 
- either use a explicit constraint or use a regexp, e.g:

  get '/products' => 'products#list', :format => /json/

or

  get '/products' => 'products#list', :constraints => { :format => 'json' }

The mapper assumes non-significant keys in a route definition are defaults 
unless they're regexps.

> Also, consider this other example:
> 
> get '/products.json' => 'products#list', format: :json
> 
> This will also respond to '/products.json.html' for example, and I don't 
> think it should answer to anything else but '/products.json'. Also, the 
> content-type declared in the routes wouldn't be respected.

That's because :format is still being appended to the route - the mapper 
doesn't interpret the path you specify other than to look for segment keys and 
optional segments. If you're after a format-less path that only serves JSON 
then use this:

  get '/products' => 'products#list', :format => false, :defaults => { :format 
=> 'json' }

or if you want the extension then use this:

  get '/products.json' => 'products#list', :format => false, :defaults => { 
:format => 'json' }

The only way to turn off the :format segment being added is to either insert it 
yourself or pass :format => false.

> Maybe I'm the only one considering the current behavior an issue, but I'd 
> like to ask you to consider some changes in the routing rules with regards to 
> format to make them less loose.

If you can come up with a route that isn't supported or doesn't appear to be 
supported please open a new issue. You don't need to ping me on it - I normally 
take a look at all the routing issues that get created.


Andrew White

[1]: https://rails.lighthouseapp.com/projects/8994/tickets/1215
[2]: https://rails.lighthouseapp.com/projects/8994/tickets/1359
[3]: 
https://github.com/rails/rails/commit/fef6c32afe2276dffa0347e25808a86e7a101af1

-- 
You received this message because you are subscribed to the Google Groups "Ruby 
on Rails: Core" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to 
[email protected].
For more options, visit this group at 
http://groups.google.com/group/rubyonrails-core?hl=en.

Reply via email to