4

私はレールに不慣れで、次の問題をまだ解決できていません。「ユーザー」と呼ばれるモデルで認証にdeviseを使用しています。このモデルは、「会社」と呼ばれる別のモデルに関連付けられています。

user.rb

  class User < ActiveRecord::Base

  devise :database_authenticatable, :registerable, :confirmable,
         :recoverable, :rememberable, :trackable, :validatable

  belongs_to :company
  accepts_nested_attributes_for :company

  attr_accessible :company_attributes, :email, :password, 
                  :password_confirmation, :remember_me, :company_id

company.rb

  class Company < ActiveRecord::Base

  has_many :users
  attr_accessible :name
  validates :name, :presence => true, :uniqueness => true

登録時に、ユーザーは会社とユーザーの両方を作成します。

users_controller.rb

def new
    @user = User.new
    @user.build_company

    respond_to do |format|
      format.html # new.html.erb
      format.json { render json: @user }
    end
end

def create
  @user = User.new(params[:user])

  respond_to do |format|
    if @user.save
      format.html { redirect_to @user, notice: 'User was successfully created.' }
      format.json { render json: @user, status: :created, location: @user 
    else
      format.html { render action: 'new' }
      format.json { render json: @user.errors, status: :unprocessable_entity }
    end
  end
end

これまでのところ、登録はうまくいっています。つまり、@user.saveが true の場合、ユーザー モデルと会社モデルにそれぞれ 2 つのレコードが作成され、ユーザー モデルの列に正しい関連付けが作成されますcompany_id

が false の場合@user.save、たとえば、ユーザー属性 email の検証が既に取得されているために失敗した場合、新しいビューがレンダリングされます。予想どおり、@user属性 (この場合は email) は保持され、 の後もそれぞれのフォーム フィールドに残りますrender action: 'new'。ただし、会社属性名のフォーム フィールドは空白で表示されます。これは、登録ページのビューです。

new.html.erb

<%= devise_error_messages! %>
<h2>Sign up</h2>
<%= simple_form_for(resource, :as => resource_name, 
                              :url => registration_path(resource_name),
                              :html => {:class => 'form-horizontal' }) do |f| %>

    <%= f.simple_fields_for :company,  @user.build_company do |builder| %>
        <div><%= builder.label :name, "Company" %><br />
        <%= builder.text_field :name, :autofocus => true, 
                            :placeholder => "Example Company Inc.",
                            :required => true %></div>
    <% end %>

  <div><%= f.label :email %><br />
  <%= f.email_field :email, :placeholder => "example@email.com",  :required => true %></div>

  <div><%= f.label :password %><br />
  <%= f.password_field :password,  :required => true %></div>

  <div><%= f.label :password_confirmation %><br />
  <%= f.password_field :password_confirmation,  :required => true %></div>

  <%= f.submit "Sign up", :class => "btn"%>
<% end %>

<%= render "devise/shared/links" %>

@company次のように、フォーム フィールドの内容を params ハッシュ内に保存できるように、ユーザー作成メソッドでインスタンス変数を作成する必要があるかもしれないと考えました。

@company = @user.build_company(params[:company])

残念ながら、これは機能せず、これまでのところ、stackoverflow に投稿された他の質問で解決策を見つけていません。最初のアプリの構築を進められるよう、皆様のご意見をお待ちしております ;)

よろしくお願いします。

4

1 に答える 1

0

Michal の意見のおかげで、ユーザーが関連付けられた会社を通じて作成され、その逆ではないようにコントローラーを再配置しました。それぞれの会社のコントローラーは次のようになります。

company_controller.rb

# GET company/new
def new
    @company = Company.new
    @company.users.build
end

# POST company/
def create
    @company = Company.new(params[:company])

    respond_to do |format|
      if @company.save
        format.html { redirect_to root_path, notice: 'Welcome! Your account has been created successfully. A confirmation link has been sent to your email address.' }
        format.json { render json:  root_path, status: :created, location: @company }
      else
        format.html { render action: "new" }
        format.json { render json: @company.errors, status: :unprocessable_entity }
      end
    end
end

GET リクエストのフォームは、次のように Devise User モデル フィールドをネストします。

new.html.erb

<h2>Create an account</h2>
<%= simple_form_for( @company, :html => {:class => 'form-horizontal' }) do |f| %>
<%= render 'shared/error_messages', :object => @company %>
    <%= f.input     :name, 
                    :label =>'Company name',
                    :placeholder => "Example Company Inc.",
                    :autofocus => true %>
    <%= f.simple_fields_for :users do |builder| %>
        <%= builder.input   :email, 
                            :placeholder => "example@email.com" %>
        <%= builder.input :password %>
        <%= builder.input :password_confirmation %>
    <% end %>
    <%= f.button    :submit, 'Create account',
                    :class => 'btn'%>
<% end %>
<%= link_to "Sign in", new_session_path(:user) %>

これで、検証が失敗した場合、すべてのインスタンス属性値がそれぞれのフォーム フィールドに残ります。

于 2013-06-15T19:39:10.340 に答える