Las asociaciones polimórficas en Ruby on Rails son una característica que dan libertad de estructurar relaciones entre modelos. Esto significa que podremos tener mayor semántica en nuestras bases de datos.
Cuando definimos una asociación con Active Record usualmente asumimos que un modelo conectara con otro, sin embargo cuando hablamos de una asociaciones polimórfica significa que podremos conectar un modelo a multiples modelos.
Por ejemplo, tenemos los siguientes tres modelos.
- User
- Product
- Picture
Las imágenes son propiedad del usuario y también del producto. Para solucionar este ejemplo podemos crear dos modelos de imagen ejecutando los siguientes comandos.
- rails g model picture_user user_id:integer name:string url:string
- rails g model picture_product product_id:integer name:string url:string
# app/models/picture_user.rb class PictureUser < ApplicationRecord belongs_to :user end # app/models/picture_product.rb class PictureProduct < ApplicationRecord belongs_to :product end
De esta forma podremos usar user.pictures y product.picture para obtener su respectiva imagen, sin embargo ambos modelos de imágenes son iguales excepto por las claves foráneas lo que significa que esta solución no es la adecuada.
Para esto existen las asociaciones polimórficas que consisten en dos (o más) asociaciones que ocurren con la misma clave foránea.
Para usar user.picture y product.picture usando el mismo modelo necesitaremos hacer algunos cambios en el modelo de imágenes para poder identificar si una imagen pertenece al modelo de usuario o producto, para esto ejecutaremos el siguiente comando.
rails g model picture pictureable_id:integer pictureable_type:string name:string url:string
# app/models/picture.rb class Picture < ApplicationRecord belongs_to :pictureable, polymorphic: true end # app/models/user.rb class User < ApplicationRecord has_many :pictures, as: :pictureable end # app/models/product.rb class Product < ApplicationRecord has_many :pictures, as: :pictureable end
Como podrás notar agregamos el termino able
al nombre de nuestros modelos al hacer la asociación, Si estas familiarizado con Rails sabras que este nombramiento se hace por convención y es parte de la magia de Rails.
De esta forma cualquier modelo que tenga una imagen podrá utilizar asociaciones tal como fue el caso de users y products.
Sabemos que hablar de asociaciones polimórficas puede sonar complicado pero en realidad es solo un par de palabras fancies ya que en realidad el único cambio será en nuestra migración y en el modelo al incluir el atributo polymorphic: true
Si consideras que este aporte fue de valor compártelo para juntos crear un ambiente donde todos deseemos colaborar.