2017-12-08 10 views
0

내 Phoenix 앱에는 연락처 테이블과 주소 테이블이 있습니다. 접촉 스키마는 다음과 같습니다외 국인 외래 키

schema "contacts" do 
    field :name, :string 
    field :number, :string 
    has_one :address, App.Address, on_delete: :nothing 

    timestamps() 
end 

주소 스키마는

schema "addresses" do 
    field :name, :string 
    field :lat, :decimal 
    field :lng, :decimal 

    timestamps() 
end 

난 그냥 데이터베이스에서 작성 주소의 드롭 다운을 통해 선택할 수 연락처에 address_id있다 할 것입니다. 그러나 피닉스는

`App.Address.contact_id` in `where` does not exist in the schema in query: 

from a in App.Address, 
    where: a.contact_id == ^9435, 
    select: {a.contact_id, a} 

을 반환 그래서하지만 내가 주소를 연락처 또는 여러 연락처에 포함시킬 주소에 contact_id 필드를 찾기 위해 노력하고있다,하지만 난 주소 테이블의 contact_id 필드를 원하지 않는다 . 외계인 협회와 함께 이것을 어떻게 달성 할 수 있습니까?

각 contact_id 및 address_id에 대한 항목이있는 중간 테이블을 사용하여이 작업을 수행 할 수 있다는 것을 알고 있지만 불필요한 복잡성과 추상화 수준을 추가한다고 생각하기 때문에 피하는 것이 좋습니다.

편집 : 답변 해 주셔서 감사합니다. 게시물을 게시 한 후 몇 분 뒤 역순으로 생각해야한다는 것을 깨달았습니다. 주소를 생각할 때 주소가 많고 연락처에 주소가 하나 있으면 관계가 의미가 있습니다. 나는 그 주소가 반드시 그 사실 일 필요가 없을 때 그 연락처가 속한 것이라고 생각하는 막혔다. Contact는 하나의 Address 수와 Address 여러 Contact들에있을 수 있고 address_id 필드는 contacts 테이블에 있다면

+0

"주소 테이블에 contact_id 필드가 필요하지 않습니다."그러면 레코드가 데이터베이스에 어떻게 연관됩니까? – Dogbert

+0

많은 연락처가 하나의 주소를 공유 할 수 있습니다. 그러나 각 연락처에는 하나의 주소 만 있습니다. – albydarned

답변

1

, 당신은 Contact에서 belongs_to 관계 Contacthas_many이 필요합니다. 보통의 one-to-many 연관을의

contact = Repo.get(Contact, 1234) |> Repo.preload([:address]) 
IO.inspect contact.address.name 
0

:

schema "contacts" do 
    belongs_to :address, App.Address 
    ... 
end 

schema "addresses" do 
    has_many :contact, App.Contact 
    ... 
end 

이제 이런 Contact의 주소를 얻을 수 있습니다. has_one 대신 belongs_to을 사용해야합니다. 그것이 외래 키가 정의 된 곳입니다. 그런 다음 스키마는 관계가 있어야 그들 사이의 차이 here

연관 라인이 있어야합니다 귀하의 연락처 마이그레이션, 같은

add :address_id, references(:addresses, on_delete: :nothing)

로에 대한 자세한 내용을보실 수 있습니다

schema "contacts" do 
    belongs_to :address, App.Address 
end 

schema "addresses" do 
    has_many :contact, App.Contact 
end 

당신이 만약 이러한 조정을 한 후에도 오류가 계속 발생하면 컨트롤러/쿼리의 다른 오류가 발생할 수 있으며 더 많은 코드 예제가 필요합니다.