Ruby on Rails
ActiveRecord-associaties
Zoeken…
hoort bij
Een associatie belongs_to
maakt een een-op-een verbinding met een ander model, dus elke instantie van het declarerende model "behoort" tot de ene instantie van het andere model.
Als uw toepassing bijvoorbeeld gebruikers en berichten bevat en elk bericht kan worden toegewezen aan precies één gebruiker, geeft u het postmodel op deze manier aan:
class Post < ApplicationRecord
belongs_to :user
end
In uw tabelstructuur zou u dan kunnen hebben
create_table "posts", force: :cascade do |t|
t.integer "user_id", limit: 4
end
heeft een
Een has_one
associatie brengt een één-op-één-verbinding tot stand met een ander model, maar met verschillende semantiek. Deze associatie geeft aan dat elke instantie van een model een instantie van een ander model bevat of bezit.
Als elke gebruiker in uw applicatie bijvoorbeeld slechts één account heeft, geeft u het gebruikersmodel als volgt aan:
class User < ApplicationRecord
has_one :account
end
Wanneer u in actieve record een has_one
relatie hebt, zorgt actieve record ervoor dat de enige record bestaat met de externe sleutel.
Hier in ons voorbeeld: in de accounttabel kan er slechts één record zijn met een bepaalde user_id. Als u probeert nog een account voor dezelfde gebruiker te koppelen, wordt de externe sleutel van het vorige item ongeldig gemaakt (waardoor deze wees wordt) en wordt automatisch een nieuwe gemaakt. Hiermee wordt het vorige item ongeldig gemaakt, zelfs als het opslaan mislukt, zodat het nieuwe item consistentie behoudt.
user = User.first
user.build_account(name: "sample")
user.save [Saves it successfully, and creates an entry in accounts table with user_id 1]
user.build_account(name: "sample1") [automatically makes the previous entry's foreign key null]
user.save [creates the new account with name sample 1 and user_id 1]
heeft veel
Een has_many
associatie duidt op een één-op-veel-verbinding met een ander model. Deze associatie bevindt zich over het algemeen aan de andere kant van een associatie.
Deze koppeling geeft aan dat elke instantie van het model nul of meer instanties van een ander model heeft.
In een toepassing met gebruikers en berichten kan het gebruikersmodel bijvoorbeeld als volgt worden verklaard:
class User < ApplicationRecord
has_many :posts
end
De belongs_to
van Post
zou hetzelfde blijven als in het voorbeeld belongs_to
; User
zou daarentegen geen schemawijzigingen nodig hebben.
Als u de lijst met alle gepubliceerde berichten voor de User
, kunt u het volgende toevoegen (dat wil zeggen, u kunt bereiken aan uw associatieobjecten toevoegen):
class User < ApplicationRecord
has_many :published_posts, -> { where("posts.published IS TRUE") }, class_name: "Post"
end
Polymorfe associatie
Met dit type koppeling kan een ActiveRecord-model tot meer dan één soort modelrecord behoren. Gemeenschappelijk voorbeeld:
class Human < ActiveRecord::Base
has_one :address, :as => :addressable
end
class Company < ActiveRecord::Base
has_one :address, :as => :addressable
end
class Address < ActiveRecord::Base
belongs_to :addressable, :polymorphic => true
end
Zonder deze koppeling zou u al deze buitenlandse sleutels in uw adrestabel hebben, maar u zou alleen ooit een waarde voor een van hen hebben, omdat een adres in dit scenario slechts tot één entiteit kan behoren (mens of bedrijf). Dit is hoe het eruit zou zien:
class Address < ActiveRecord::Base
belongs_to :human
belongs_to :company
end
De has_many: door associatie
Een has_many :through
associatie wordt vaak gebruikt om een many-to-many
verbinding met een ander model tot stand te brengen. Deze associatie geeft aan dat het declarerende model kan worden gekoppeld aan nul of meer instanties van een ander model door een derde model te doorlopen.
Overweeg bijvoorbeeld een medische praktijk waarbij patiënten afspraken maken om artsen te bezoeken. De relevante associatieverklaringen kunnen er als volgt uitzien:
class Physician < ApplicationRecord
has_many :appointments
has_many :patients, through: :appointments
end
class Appointment < ApplicationRecord
belongs_to :physician
belongs_to :patient
end
class Patient < ApplicationRecord
has_many :appointments
has_many :physicians, through: :appointments
end
De has_one: door associatie
A has_one :through
associatie brengt een one-to-one
verbinding one-to-one
stand met een ander model. Deze associatie geeft aan dat het declarerende model kan worden vergeleken met een exemplaar van een ander model door een derde model te doorlopen.
Als elke supplier
bijvoorbeeld één account
heeft en elke account aan één accountgeschiedenis is gekoppeld, kan het leveranciersmodel er als volgt uitzien:
class Supplier < ApplicationRecord
has_one :account
has_one :account_history, through: :account
end
class Account < ApplicationRecord
belongs_to :supplier
has_one :account_history
end
class AccountHistory < ApplicationRecord
belongs_to :account
end
De vereniging has_and_belongs_to_many
Een has_and_belongs_to_many
associatie creëert een directe many-to-many
verbinding met een ander model, zonder tussenliggend model.
Als uw toepassing bijvoorbeeld assemblies
en parts
, waarbij elke assemblage veel onderdelen heeft en elk onderdeel in veel assemblages voorkomt, kunt u de modellen op deze manier declareren:
class Assembly < ApplicationRecord
has_and_belongs_to_many :parts
end
class Part < ApplicationRecord
has_and_belongs_to_many :assemblies
end
Zelfreferente vereniging
Zelfreferente associatie wordt gebruikt om een model met zichzelf te associëren. Het meest voorkomende voorbeeld zou zijn om de associatie tussen een vriend en zijn volger te beheren.
ex.
rails g model friendship user_id:references friend_id:integer
nu kun je modellen als;
class User < ActiveRecord::Base
has_many :friendships
has_many :friends, :through => :friendships
has_many :inverse_friendships, :class_name => "Friendship", :foreign_key => "friend_id"
has_many :inverse_friends, :through => :inverse_friendships, :source => :user
end
en het andere model zal eruit zien;
class Friendship < ActiveRecord::Base
belongs_to :user
belongs_to :friend, :class_name => "User"
end