Re: tabla intermedia N:M

Mmmmm, lo que me has puesto me has confundido, yo había seguido los pasos
del Agile usando el has_and_belongs_to_many, había hecho:

Mis modelos:
class Proyecto < ActiveRecord::Base
has_and_belongs_to_many :temas
end

class Tema < ActiveRecord::Base
has_and_belongs_to_many :proyectos
end

Las migraciones:
class CreateProyectos < ActiveRecord::Migration
def self.up
create_table :proyectos do |t|
t.column :hidden, :integer, :null=>false, :default=>0
t.column :deleted, :integer, :null=>false, :default=>0
t.column :created_on, :date
t.column :updated_on, :date
t.column :nombre, :string, :null=>false
t.column :foto_grande, :string, :null=>true, :default=>“”
t.column :foto_peq, :string, :null=>true, :default=>“”
t.column :texto, :text, :null=>false
t.column :destacado, :integer,:null=>false, :default=>0
t.column :texto_dest, :text, :null=>true, :default=>“”
t.column :categoria_id, :integer
t.column :cliente_id, :integer
end
end

def self.down
drop_table :proyectos
end
end

class ProyectoTema < ActiveRecord::Migration
def self.up
create_table :proyectos_temas, :id=>false do |t|
t.column :proyecto_id, :integer
t.column :tema_id, :integer
end
end

def self.down
drop_table :proyectos_temas
end
end

class AddIndexProyectoTema < ActiveRecord::Migration
def self.up
add_index :proyectos_temas, :proyecto_id
add_index :proyectos_temas, :tema_id
end

def self.down
remove_index :proyectos_temas, :proyecto_id
remove_index :proyectos_temas, :tema_id
end
end

En la migración cree mi tabla proyectos, mi tabla temas y cree mi tabla
intermedia proyectos_temas con sus respectivos índices.
Por éso, ahora tenía la duda en mi controlador de cómo insertar las filas en la
tabla intermedia puesto que no tengo un modelo para esta tabla y me
perdí. En mi controlador creo el item del proyecto
(@proyecto=Proyecto.new) pero también necesito insertar todos los temas
que pertenecen al proyecto y no se cómo puedo insertar en la tabla
proyectos_temas.
Y lo que me has puesto ya me ha liado, no sabía que se podía hacer así también,
si no te importa aconsejarme como lo estaba haciendo, usando el
has_and_belongs_to_many para ir aprendiendo, sigo con la duda de
cómo insertar los registros en la tabla “proyectos_temas” puesto que no
tengo modelo. Tenía pensado recorrer con un for los valores y cada vez que
entre hacer la inserción en la tabla, pero no se.

----- Mensaje original ----
De: Jaime Mora R. [email protected]
Para: [email protected]
Enviado: jueves, 30 de agosto, 2007 16:37:41
Asunto: Re: [Ror-es] tabla intermedia N:M

Miguel Angel Calleja Lázaro wrote:

Aha, muchas gracias, ahora me ha surgido la duda de cómo puedo insertar
los valores en esta tabla, con una consulta de sql a pelo? o a través de
un modelo? En este caso tendría que hacer un modelo que me buscara mi
tabla “proyectos_categorias”, no? Gracias por vuestra ayuda

class CreateUsuarios < ActiveRecord::Migration
def self.up
create_table “grupos”, :force => true do |t|
t.column “nombre”, :string, :limit => 80
end

Grupo.create :nombre => “admin”
Grupo.create :nombre => “demo”
Grupo.create :nombre => “report”
Grupo.create :nombre => “sales”
Grupo.create :nombre => “user”

create_table “usuarios”, :force => true do |t|
t.column “login”, :string, :limit => 80
end

Usuario.create :login => “erik”
Usuario.create :login => “george”
Usuario.create :login => “jack”
Usuario.create :login => “lori”
Usuario.create :login => “sara”

create_table “permisos”, :id => false, :force => true do |t|
t.column “grupo_id”, :integer, :default => 0, :null => false
t.column “usuario_id”, :integer, :default => 0, :null => false
end
end

def self.down
drop_table :grupos
drop_table :usuarios
drop_table :permisos
end

end

Basado en la migración anterior debes tener los siguientes modelos:

app/models/usuario.rb

class Usuario < ActiveRecord::Base
has_many :permisos, :dependent => true
has_many :grupos, :through => :permisos
end

app/models/grupo.rb

class Grupo < ActiveRecord::Base
has_many :permisos, :dependent => true
has_many :usuarios, :through => :permisos
end

app/models/permiso.rb

class Permiso < ActiveRecord::Base
belongs_to :grupo
belongs_to :usuario
end

Espero te sirva.
Saludos

Posted via http://www.ruby-forum.com/.


Ror-es mailing list
[email protected]


Sé un Mejor Amante del Cine
¿Quieres saber cómo? ¡Deja que otras personas te ayuden!
http://advision.webevents.yahoo.com/reto/entretenimiento.html

Miguel Angel Calleja Lÿffffe1zaro wrote:

Y lo que me has puesto ya me ha liado, no sabí¡ que se podí¡ hacer así ´ambi鮬
si no te importa aconsejarme como lo estaba haciendo, usando el
has_and_belongs_to_many para ir aprendiendo, sigo con la duda de
có­¯ insertar los registros en la tabla “proyectos_temas” puesto que no
tengo modelo. Tení¡ pensado recorrer con un for los valores y cada vez que
entre hacer la inserció® ¥n la tabla, pero no se.

El has_many :through es más flexible. Te conviene utilizarlo si
almacenarás información extra en el join, además tendrás la posibilidad
de tratar el join cómo un modelo :

Permiso.create(:usuario_id => usuario.id, :grupo_id => grupo.id)

Que supongo es lo que andas buscando.

Saludos.

Jaime Mora R. escribió:

Saludos.

Vale, lo he hecho como me has dicho,
class Proyecto < ActiveRecord::Base
has_many :ptemas, :dependent => true
has_many :temas, :through => :ptemas
end
class Tema < ActiveRecord::Base
has_many :ptemas, :dependent=>true
has_many :proyectos, :through=>:ptemas
end
class Ptema < ActiveRecord::Base
belongs_to :proyecto
belongs_to :tema
end

Ahora tengo un problemilla, si borro un proyecto, me debería borrar el
proyecto y de la tabla ptemas aquellas filas con el proyecto_id, pero me
sale este error:
Unknown column ‘id’ in ‘where clause’: DELETE FROM ptemas
WHERE id = NULL

No está cogiendo bien el ‘id’, debería ser ‘proyecto_id’, por qué lo
hace?

Miguel Angel Calleja Lázaro wrote:

Prueba definiendo los modelos de la siguiente manera :

class Proyecto < ActiveRecord::Base
has_many :ptemas, :dependent => :delete_all
has_many :temas, :through => :ptemas
end

class Tema < ActiveRecord::Base
has_many :ptemas, :dependent => :delete_all
has_many :proyectos, :through=>:ptemas
end

class Ptema < ActiveRecord::Base
belongs_to :proyecto
belongs_to :tema
end

Nota al margen, :dependent => true ha sido desaprobada (deprecated) en
la versión 1.2 de Rails [1] :

“:dependent => true is deprecated and has been replaced with :dependent
=> :destroy”

No obstante es necesario utilizar “:dependent => :delete_all” para
forzar a que los objetos asociados sean eliminados pero sin llamar a su
método destroy, y evitar que Rails utilize la convención de utilizar el
campo “id”.

[1]
http://api.rubyonrails.com/classes/ActiveRecord/Associations/ClassMethods.html#M000642

Espero te sirva.