2009-06-04 11 views
8

Quiero que mis Rails 2.3.2 aplicación para responder y generar URL de este modo:rieles recursos REST utilizando to_param para un campo que contiene caracteres de separación

/websites/asd.com 
/websites/asd.com/dns_records/new 

En mi config/routes.rb, que tengo:

map.resources :websites, :has_many => :dns_records 
map.resources :dns_records, :belongs_to => :website 

que pueda entonces tener acceso a recursos tales como:

/websites/1 
/websites/1/dns_records 

Mediante la modificación de mi modelo de sitio web, que pueda g enerate mejores URL como estas:

class Website < ActiveRecord::Base 
    def to_param 
     domain_name 
    end 
    ... 
end 

# app/views/websites/index.erb 
<% @websites.each do |w| %> 
<%= link_to "Show #{w}", website_path(w) %> 
<% end %> 

# Produces a link to: 
/websites/example_without_periods_in_name 

Sin embargo, para los nombres de dominio que contienen '.' personajes, Rails se pone triste. Creo que esto es porque el '.' El carácter se define en ActionController :: Routing :: SEPARATORS, que enumera los caracteres especiales para dividir la URL. Esto te permite hacer cosas como /websites/1.xml.

SO, ¿hay una manera limpia de permitir '.' caracteres en URL RESTful?

He intentado redefinir ActionController :: Routing :: SEPARATORS para que no incluya '.', Que es una manera totalmente incorrecta de resolver el problema. Esto arruina las URL generadas al agregarles ".: Format".

También sé que puedo agregar: requirements => {: id => regexp} a mi config/routes.rb para que coincida con un nombre de dominio que incluya '.' (sin esto, params [: id] se establece en la parte del nombre de dominio antes del primer '.'), pero esto no ayuda a generar URL/rutas de manera REST.

Muchas gracias :) Nick

Respuesta

4

solucionado el problema, con una gran gracias a http://poocs.net/2007/11/14/special-characters-and-nested-routes (y ver http://dev.rubyonrails.org/ticket/6426 de referencia adicional)

que tenía que añadir: requisitos => {: website_id => expresión regular} para cada ruta anidado que también se va a incluir un nombre de dominio con períodos en el mismo.

Aquí está mi ruta de trabajo:

map.resources :websites, :requirements => { :id => /[a-zA-Z0-9\-\.]+/ } do |websites| 
    websites.with_options :requirements => { :website_id => /[a-zA-Z0-9\-\.]+/ } do |websites_requirements| 
     websites_requirements.resources :dns_records 
    end 
end 

<%= link_to 'New DNS Record', new_website_dns_record_path(@website) %> 

# Produces the URL 
/websites/asd.com/dns_records/new 

La llamada a

websites.with_options 

es simplemente de acuerdo con SECO de manera que: requisitos no tienen que ser especificados para todas las rutas anidadas para los sitios web. Entonces también podría tener

websites_requirements.resources :accounts 
websites_requirements.resources :monthly_bandwidth_records 
etc. 
1

Este es un tema interesante. No creo que pueda deshacerse del '.:format' malo adjunto al final si hace un map.resources básico. Si quiere puntos en los nombres, no está de acuerdo con los estilos habituales de rieles, y creo que una ruta personalizada podría estar en orden si absolutamente NECESITA el '.' en la URL

Sin embargo, tal vez debería considerar cambiar su definición de to_param. ¿Qué pensarías sobre usar lo siguiente?

def to_param 
    domain_name.sub('.','_dot_') 
end 

Creo que, si usted está usando esto para administrar sitios web de los clientes, es una forma bastante elegante para generar buenos (y SEO amigable) URL como

/websites/asd_dot_com/dns_records/new 
/websites/asd_dot_com/ 
Cuestiones relacionadas