2012-03-14 3 views
1

레일즈 앱에는 사용자가 있습니다. 사용자는 거주하는 도시 및 지구/지역을 물어 봅니다. 형태에서레일스 : 특정 순서로 속성 생성

class User < ActiveRecord::Base 
    belongs_to :city 
    belongs_to :district 
end 

class City < ActiveRecord::Base 
    has_many :users 
    has_many :districts 
end 

class District < ActiveRecord::Base 
    has_many :users 
    belongs_to :city 
end 

나는 문자열 (경우에는 관련이 아래에 더 많은 정보를) 받아들이는 사용자 모델에 가상 속성을 사용하여 연결을 구축 할 수 있습니다.

콘솔에서는이 모든 것이 훌륭하게 작동하지만 UI에서는 작동하지 않습니다. 문제는 양식을 통해 아무런 문제없이 city_name을 얻을 수 있지만 도시와 지구를 동일한 양식으로 할당하려고하면 항상 실패합니다. 즉, 질량 할당이 작동하지 않습니다.

@user.update_attributes(params[:user]) 

대신 내가 알아낼 수 있었던 유일한 수동으로 같은 양식 제출의 각 키를 설정하는 것입니다 :이 방법은 작동

@user.name = params[:user][:name] if params[:user][:name] 
@user.city_name = params[:user][:city_name] if params[:user][:city_name] 
@user.district_name = params[:user][:district_name] if params[:user][:district_name] 

하지만, 가지 취성 고통이다 , 많은 논리로 컨트롤러를 가동시키기 시작하기 때문에 모든 잘못을 느낀다.

내 질문은 : 컨트롤러에 대한 모든이를 걱정하지 않도록

  1. 작성하는 방법 또는 업데이트가 이상적 모델에, 거기에 특정 순서로 속성인가?

  2. 내가 잘못 했나요? 그렇다면 어떤 접근 방식이 더 좋을까요? 나는 잠재적 답변자 관련이 경우 사용자 모델에 가상 속성을 사용하여 연결을 구축하는 방법을


추가 정보는 여기

는 다음과 같습니다

을 나는 사용자가되고 싶어 "Chicago, IL"과 같이 이름을 입력하면 도시를 선택할 수 있습니다. 이 때문에 같은 사용자 모델에 가상 속성을 사용하여, 잘 작동 :

def city_name 
    city.try :full_name 
end 

def city_name=(string) 
    self.city = City.find_or_create_by_location_string(string) 
end 

그것은 단지 찾거나 그들이 선택한 도시에서 지구를 만들 수있는 사용자에 대한 의미가 있습니다. 이것은 약간 다르게 작동합니다

def district_name 
    district.try :name 
end 

def district_name=(string) 
    if self.city.nil? 
    raise "Cannot assign a district without first assigning a city." 
    else 
    self.district = self.city.districts.find_or_create_by_name(string) 
    end 
end 

이러한 일들이 잘 작동 모델 층에서 예상만큼 오래 CITY_NAME 및 district_name 모두 지구 연결을 설정으로 작동합니다.

답변

1

나는 이것을 정리하기 위해 몇 가지 일을 할 수 있다고 생각합니다. 첫째, 델리게이트를 사용하여 코드를 정리할 수 있습니다. 예 : 당신이

user = User.create 
user.city_name # nil 
city = City.create(:name => 'chicago') 
user.city = city 
user.save 
user.city_name # chicago 

뭔가를 할 수 있으며, 그냥 작동합니다

delegate :name, :to => :city, :prefix => true, :allow_nil => true 

그런 식으로.

다음으로, 모델에서 이름 대 ID 로직을 제거한다고 말하고 싶습니다. 양식 (예 :아약스 검색은 지역 ID/도시 ID를 숨겨진 필드에 넣음) 또는 컨트롤러에서 검색합니다. 그런 다음 평소와 같이 도시/지구를 지정하십시오.

+0

이것은 좋은 생각이었습니다. 모델에 문자열을 전달하는 대신 ID에 숨겨진 필드를 사용한다는 아이디어를 기반으로 설정을 재 작업 할 수 있었고 훨씬 간단 해졌습니다. 제안을 주셔서 감사합니다, 당신은 나를 올바른 길로 인도했습니다. – Andrew

관련 문제