1

Я новичок в Rails, поэтому у меня есть вопрос новичков.Подтвердить значение от другой модели

У нас есть форма, которая позволяет администраторам установить новый пользователь, который выглядит следующим образом:

<%= form_for :user, :url => url_for(:action => 'create_user', :account_id => @account.id, :hide_form => 1), :html => {:name => 'new_user_form', :id => 'new_user_form', :remote => true} do |f| %> 
    First Name: 
    <% f.text_field 'first_name' %><br/> 
    Last Name: 
    <%= f.text_field 'last_name' %><br/> 
    Username: 
    <%= f.text_field 'login' %><br/> 
    Email: 
    <%= f.text_field 'email' %><br/> 
    Agency Code: 
    <%= text_field_tag 'agency_code', @default_agency_code %><br/> 

    <div class="button-bar"> 
    <%= f.submit :id => "submit_button" %> 
    </div> 
<% end %> 

До сих пор, так хорошо. Действие, которое вызывается, когда форма передается пихает все значения формы в User объект и сохраняет его в базе данных:

def remote_create_user 
    @user = User.new(params[:user]) 
    @user.agency = Agency.find{|agency| agency.product_code == params[:agency_code]} 
    if @user.valid? and @user.save 
    # Move some stuff around for the new user 
    else 
    @error = "Failure to Save:" 
    @user.errors.full_messages.each {|msg| @error += " - #{msg}"} 
    end 
end 

Мое понимание, что линия в окне, которое начинается <%= form_for :user позволяет вид ERB знать, чтобы проверить все поля формы, которые соответствуют классу User, используя логику проверки, указанную в модели User.

Однако последнее поле в форме (Agency Code: <%= text_field_tag 'agency_code', @default_agency_code %><br/>) не соответствует атрибуту в модели User. Вместо этого он соответствует Agency.product_code. Модель Agency определяет валидацию для этого атрибута. Как я могу сказать Rails использовать логику проверки в модели Agency для этого поля? Если нет прямого способа сделать это, как я могу добавить подтверждение непосредственно в текстовое поле кода агентства?

ответ

1

Вы можете просто использовать

@user.agency = Agency.find_by_id{|agency| agency.product_code == params[:agency_code]} 

и в модели пользователя,

validates :agency_id, :presence => true 

find_by_id будет работать лучше в этом случае, чем просто find, потому что она возвращает nil если модель не найдена.

+0

Спасибо, что ответили так быстро! Думаю, меня немного смущает: как изменение в модели «Пользователь» позволило Rails узнать, как проверить правильность в модели «Агентство»? – Kevin

+1

Если я получил это хорошо, глядя на ваш код, кажется, что вы выбираете существующее агентство и не обновляете его при создании пользователя. В этом случае агентство всегда будет действительным, если оно будет найдено, поэтому на самом деле вы хотите проверить атрибут пользователя - у него должно быть агентство. Нет никакой проверки на модель агентства, она есть у пользователя - у нее должно быть агентство (при этом агент_ид не может быть нулевым). Если вы модифицировали агентство после добавления пользователя, вам нужно будет использовать [вложенную форму] (http://stackoverflow.com/q/5073698/413494) – fotanus