2009-01-23 21 views
24

Tengo dos controladores para dos modelos respectivos, por ejemplo, fotos y categorías. los métodos index y show son muy similares en cada controlador, y las vistas son idénticas. ¿Cuál es el mejor método para compartir la vista de los dos modelos?Dos controladores para una vista compartida en Ruby on Rails

tengo dos opciones: aunque

  • Use un ayudante. En el ayudante colocará el código para la vista, y llamará al ayudante desde cada vista (fotos/vistas y categorías/vistas)

  • Use un parcial en cada vista. Creo que es una solución más limpia, pero veo enormes DRY en mi mente cuando voy a codificar esta solución.

lo tanto, tengo dos controladores de dos modelos, cada uno en y expone un objeto @photo (controlador de fotos con todas las fotos, y las categorías controlador con fotos sólo la de Categoría del alojamiento seleccionado) y necesito una vista a mostrar ambos.

Estoy buscando una solución elegante para esto, quejándose de los principios REST y DRY. ¿Alguna idea?

Gracias de antemano.

Respuesta

38

Tengo una situación similar con uno de mis proyectos. Todas las vistas de eliminación para la mayoría de los controladores se diseñan del mismo modo, muestran los mismos cuadros de confirmación y simplemente representan de forma predecible el objeto que se está eliminando.

La solución fue bastante simple y elegante en mi opinión. En pocas palabras, lo que nosotros (los desarrolladores) hicimos fue crear un nuevo directorio en app/views llamado shared y poner puntos de vista compartidos allí. Estos podrían ser archivos de plantilla completos o solo parciales.

Sugiero usar una plantilla compartida (en categorías ni fotos, ver directorios, sino en el directorio compartido) y renderizarla manualmente desde la vista.

p. Ej. tener un método como tal en los dos controladores y un archivo app/views/shared/photo.html.erb:

def show 
    @photo = Photo.first # ... or whatever here 
    render :template => 'shared/photo' 
end 

Esto debe procesar correctamente la plantilla compartida. Es la ruta DRYest y no tiene la sensación de contaminación que se obtiene al usar una vista más o menos vacía en el directorio de vista de cada controlador solo para incluir un parcial compartido, como entiendo que su pregunta sugiere.

+0

¡Ah brillante! Acabo de pasar 2 horas tratando de SECAR uno de mis parciales que me estaba causando dolor. Gracias, esto es muy simple. – brad

+0

Ahora, ¿qué sucede cuando necesita cargar esa plantilla con AJAX? :) – Noz

+0

Cuando pruebo esto en Rails 4.2.5 obtengo el error "ActionController :: RackDelegation # content_type delegado a @ _response.content_type, pero @_response es nil: #

1

Usaría un ayudante porque se comparten entre las vistas. Para la parte HTML, usaría parciales para que sea una mezcla de ambas maneras.

+0

Sí, creo que es la mejor solución debido a su visibilidad desde cada controlador o vista, pero, ¿es correcto poner código de vista (código html) en un ayudante? – ARemesal

+0

Sería mejor no poner código de vista en los ayudantes a menos que sea menos de unas líneas –

+0

Usaría una combinación de parcial para el código HTML y ayudantes para el código. – Keltia

6

Sobre el first respuesta:

Si el parcial debe hacerse desde un punto de vista:

 
<%= render :partial => "shared/photo" %> 

y la parcial debe estar en app/views/shared/_photo.html.erb

1

Esto parece un buen caso de uso para la gema Cells.

0

@bjeanes Si todas sus vistas de eliminación son las mismas, puede crear views/default/delete.html.erb y todas las acciones de eliminación lo usarán.

Eso es lo que estoy haciendo: La mayoría de mis puntos de vista están en default, y crear otros específicos sólo cuando sea necesario

Actualización: Ok, esta entrada es a partir de 2009, de todos modos, voy a seguir mi comentario aquí en caso de que alguien llegue aquí desde Google como yo lo hice.