Respostas:
Eles essencialmente fazem a mesma coisa, a única diferença é de que lado do relacionamento você está. Se a User
tiver um Profile
, na User
classe que você teria has_one :profile
e na Profile
classe que você teria belongs_to :user
. Para determinar quem "possui" o outro objeto, observe onde está a chave estrangeira. Podemos dizer que um User
"tem" a Profile
porque a profiles
tabela possui uma user_id
coluna. Se houvesse uma coluna chamada profile_id
na users
tabela, no entanto, diríamos que a Profile
possui a User
, e os locais belongs_to / has_one seriam trocados.
Aqui está uma explicação mais detalhada.
Product belongs_to Shop
meios products
tabela tem shop_id
coluna
É sobre onde fica a chave estrangeira.
class Foo < AR:Base
end
belongs_to :bar
, a tabela foos tem uma bar_id
colunahas_one :bar
, a tabela de barras tem uma foo_id
colunaNo nível conceitual, se você class A
tem um has_one
relacionamento com ele, class B
então class A
é o pai de, class B
portanto, class B
ele terá um belongs_to
relacionamento com class A
ele, pois é filho de class A
.
Ambos expressam um relacionamento 1-1. A diferença é principalmente onde colocar a chave estrangeira, que fica na mesa da classe que declara o belongs_to
relacionamento.
class User < ActiveRecord::Base
# I reference an account.
belongs_to :account
end
class Account < ActiveRecord::Base
# One user references me.
has_one :user
end
As tabelas para essas classes podem se parecer com:
CREATE TABLE users (
id int(11) NOT NULL auto_increment,
account_id int(11) default NULL,
name varchar default NULL,
PRIMARY KEY (id)
)
CREATE TABLE accounts (
id int(11) NOT NULL auto_increment,
name varchar default NULL,
PRIMARY KEY (id)
)
Account
e User
neste exemplo é lamentável, pois geralmente é o caso em que uma conta pode ter muitos usuários.
has_one
e belongs_to
geralmente são iguais no sentido em que apontam para o outro modelo relacionado. belongs_to
certifique-se de que este modelo tenha o foreign_key
definido.
has_one
garante que a outra has_foreign
chave de modelo seja definida.
Para ser mais específico, existem dois lados de relationship
, um é o Owner
e outro é Belongings
. Se only has_one
for definido, podemos obtê-lo, Belongings
mas não podemos obtê-lo a Owner
partir do belongings
. Para rastrear o Owner
, precisamos definir o belongs_to
também no modelo pertencente.
Outra coisa que quero acrescentar é: suponha que tenhamos a seguinte associação de modelos
class Author < ApplicationRecord
has_many :books
end
se escrevermos apenas a associação acima, poderemos obter todos os livros de um autor em particular,
@books = @author.books
Mas para um livro em particular, não podemos obter o autor correspondente por,
@author = @book.author
para que o código acima funcione, precisamos adicionar associação ao modelo Book também, como este
class Book < ApplicationRecord
belongs_to :author
end
Isso adicionará o método 'author' ao modelo do livro.
Para detalhes do modo, consulte os guias
Do ponto de vista da simplicidade, belongs_to
é melhor do que has_one
porque has_one
, você teria que adicionar as seguintes restrições ao modelo e tabela que possui a chave estrangeira para reforçar o has_one
relacionamento:
validates :foreign_key, presence: true, uniqueness: true