Single Table Inheritance

Muy buenas,

Tengo un pequeño problema con la herencia en Rails.

Tengo gran cantidad de “Categorías”: categorías de posts, categorías
de expedientes, categorías de personas…
Resulta que estas categorías siempre tienen los mismos datos:

t.string :codigo, :size => 3, :null => false
t.string :title, :size => 80, :null => false
t.text :description

Por lo que he visto, una buena solución sería utilizar STI

class Category < AR

end

class Category::PostCategory < Category

end

…etc

Esto lo tengo claro, simplemente metiendo el t.string :type en la
migración de categoría ya conseguiría esto.

Pero no termina de convencerme STI, por el tema de los controladores y
las vistas.

  • Tengo que tener tantos controladores como modelos??? Hacen lo mismo.
  • Si las vistas son iguales (excepto en el título), he de repetirlas??
    Esto lo podría solucionar con partials.

Mi idea sería organizarlo
así:
app
models
category.rb

category
post_category.rb
expediente_category.rb

controllers
categories_controller.rb

views
categories
show.html.erb

post_categories
expedientes_categories\

Sabéis de algún howto, post o libro dónde quede bien explicado STI,
con algún ejemplo que no sea el típico del Manager < Employee <
Person???

Sé que quizá la pregunta no esté hecha del todo bien, pero lo que
quiero a fin de cuentas es poder organizar las diferentes “Categorías”
mejor de lo que lo hago.

Gracias por adelantado!

Un saludo!

Te puedo decir que yo estoy usando algo así con muy buen resultado. Para
los controladores, me limito a hacer un controlador maestro que hace
casi todo, y luego uno por cada tipo que heredan del maestro y hacen las
cosas específicas de cada uno:

class AccionesController < MasterProdController
def new
@producto = Accion.new
nuevo_producto_opinion
render :template => “productos/new”
end

Crea un nuevo producto

def create
# guardo el producto
@producto = Accion.new(params[:producto])
@producto.subtipo_id = Subtipo::ACCIONES
guarda_producto_opinion
end

end

Donde nuevo_producto_opinion y guarda_producto_opinion son funciones del
MasterProdController. Esto y poco más es el código que hay en cada
controlador…

Respecto a las vistas, si se parecen lo suficiente, es más fácil aún:
las metes en la clase genérica, y haces el render especificando el
destino (te lo he puesto en el new); en tu caso, bastaría con tener las
vistas en views/categories, no necesitas las carpetas específicas de
cada clase hija.

s2

Hola de nuevo,

Me falla al intentar hacer un render “categories/new”:

class Category::ArticleCategoriesController < ApplicationController

def new
@category = Category::ArticleCategory.new
render :template => “categories/new”
end

[…]

end

undefined method `category_article_categories_path’ for
#ActionView::Base:0x3874a94

<% form_for(@category) do |f| %> <------------ FALLO!!
<%= f.error_messages %>

<%= f.label :code %>
<%= f.text_field :code %>

[…]

<%= f.submit "Create" %>

<% end %>

Un saludo!

El 17/11/2008, a las 18:35, Fernando C.
escribió:

guardo el producto

Juan José Vidal Agustín wrote:

Hola de nuevo,

Me falla al intentar hacer un render “categories/new”:

class Category::ArticleCategoriesController < ApplicationController

def new
@category = Category::ArticleCategory.new
render :template => “categories/new”
end

[…]

end

undefined method `category_article_categories_path’ for
#ActionView::Base:0x3874a94

<% form_for(@category) do |f| %> <------------ FALLO!!

Estamos pensando en algo diferente… lo que yo te proponía no era lo
que haces
class Category::ArticleCategoriesController < ApplicationController
@category = Category::ArticleCategory.new

sino esto:
class ArticleCategoriesController < CategoryController

def new
@category = ArticleCategory.new
render :template => “categories/new”
end

[…]

end

Eso es lo que yo tengo, y funciona sin problemas…

s2