Usando Rails 7
Estou usando uma Herança de Tabela Única (STI) para armazenar algumas associações muito simples. O objeto de origem usa associações has_many com os modelos STI. Seguindo alguns conselhos em questão https://stackoverflow.com/a/45681641/1014251 Estou usando um relacionamento polimórfico no modelo de junção. Isso funciona muito bem com um incômodo:
Ao criar modelos de junção, o tipo de origem é obtido da classe STI raiz e não da origem real.
Os modelos:
class Guidance < ApplicationRecord
has_many :guidance_details
has_many :themes, through: :guidance_details, source: :detailable, source_type: "Theme"
end
class Detail < ApplicationRecord
has_many :guidance_details, as: :detailable
has_many :guidances, through: :guidance_details
end
class GuidanceDetail < ApplicationRecord
belongs_to :detailable, polymorphic: true
belongs_to :guidance
end
class Theme < Detail
end
O problema
Se eu criar um novo GuidanceDetail e não especificá-lo, detailable_source
o sistema insere "Detalhe" em vez de "Tema".:
guidance_detail = GuidanceDetail.create(guidance: Guidance.first, detailable: Theme.first)
guidance_detail.detailable_type => "Detail"
O tipo detalhável deve ser "Tema".
Para corrigir isso, atualmente estou tendo que especificar o detailable_type toda vez que crio um novo GuidanceDetail.
Uma correção que não funciona
Tentei especificar a associação has_many do objeto filho diretamente, mas obtive o mesmo resultado:
class Theme < Detail
has_many :guidance_details, as: :detailable
end
O método de criação alternativo não funciona
theme = Theme.first
guidance = Guidance.first
guidance.themes << theme
Saídas:
GuidanceDetail Create (1.3ms) INSERT INTO "guidance_details" ("detailable_id", "guidance_id", "position", "created_at", "updated_at", "detailable_type") VALUES ($1, $2, $3, $4, $5, $6) RETURNING "id" [["detailable_id", 11], ["guidance_id", 1], ["position", nil], ["created_at", "2024-11-14 10:24:19.785623"], ["updated_at", "2024-11-14 10:24:19.785623"], ["detailable_type", "Detail"]]
Como você pode ver: "detailable_type" é "Detail".