質問するログイン新規登録

Q&A

解決済

2回答

1708閲覧

【Rails】form_withでのデータ新規登録処理時、NoMethodErrorが出て処理が失敗する

otdsh9432

総合スコア55

Ruby

Rubyはプログラミング言語のひとつで、オープンソース、オブジェクト指向のプログラミング開発に対応しています。

Ruby on Rails

Ruby on Railsは、オープンソースのWebアプリケーションフレームワークです。「同じことを繰り返さない」というRailsの基本理念のもと、他のフレームワークより少ないコードで簡単に開発できるよう設計されています。

0グッド

0クリップ

投稿2020/07/04 09:34

編集2020/07/04 09:36

0

0

実現したいこと

form_withを用いて新規投稿を行う画面処理を実装したいです。

事象・困っていること

画面でformの各項目を入力し、更新ボタンを押下したところ、
「NoMethodError in Posts#create undefined method `where' for nil:NilClass」
という表示が出て、処理が失敗してしまいます。
エラー画面キャプチャ

エラーメッセージに含まれる「where」は、collection_selectで、formにてプルダウンリストを表示させるため、
コードマスタからwhereで条件に合うコードリストを取ってきている箇所で使用しています。
(<%= f.collection_select :area, code.where(code_id: "1"), :code, :name %>)

画面表示時は、この部分でエラーはなくプルダウンリストも表示されます。
しかし、更新ボタンを押下後のみエラーが出るのがなぜなのかわからない状態です。

form_withの仕組みをより詳しく知る必要があるかと思い調査中ですが、
なかなか原因がわからず、かなり時間がかかっているため、ご質問した次第です。

エラーが起きた背景

下記のように、ルーティングをネストしており、
communityというモデルの配下に、postというモデルを配置しています。
(今回のフォームは、postに対するデータ登録です)

Ruby

1 resources :communities do 2 resources :posts do 3 end

→もともとは、postモデルのみ存在していました(ネストしていませんでした)。
その際はform_withからの登録処理は正常に動作していました。
しかし、最近、communityモデルを新設し、postをネストしました。
それに伴い、form_withも下記の通りネストに対応させた形に修正しました。
(model:とurl:を分けて、urlを明記した形)

Ruby

1<%= form_with(model: post, url: [community,post] ,local:true) do |f| %>

新規投稿フォーム(new.html.erb、_form.html.erb)

<new.html.erb>

Ruby

1<h3>お店を登録する</h3> 2 <div class="post-form"> 3 <%= render partial:'form', locals:{post: @post, code: @code, community: @community} %> 4 </div>

<_form.html.erb>※関連部分のみ抜粋

Ruby

1<%= form_with(model: post, url: [community,post] ,local:true) do |f| %> 2 <div class="form-group"> 3 <%= f.label "店名" %> 4 <%= f.text_field :title, class:'form-control', id: 'title_name' %> 5 </div> 6 <div class="form-group"> 7 <%= f.label "都道府県" %><br> 8 <%= f.collection_select :prefecture_code, JpPrefecture::Prefecture.all, :code, :name, {include_blank: '都道府県を選択してください'}, {class: "form-control"} %> 9 </div> 10 <div class="form-group"> 11 <%= f.label "エリア" %><br> 12 <%= f.collection_select :area, code.where(code_id: "1"), :code, :name, {include_blank: 'エリアを選択してください'}, {class: "form-control"} %> 13 </div> 14 <div class="form-group"> 15 <%= f.label "料理ジャンル" %><br> 16 <%= f.collection_select :rest_type, code.where(code_id: "2"), :code, :name, {include_blank: '料理ジャンルを選択してください'}, {class: "form-control"} %> 17 </div> 18 <%= f.hidden_field :community_id, value: community.id %> 19 <%= f.submit "更新する", class:'btn btn-primary' %> 20 <%= link_to '戻る', community_posts_path(community), class:'btn' %> 21<% end %>

コントローラ(posts_controller.rb)※関連部分のみ抜粋

Ruby

1class PostsController < ApplicationController 2 3 def new 4 @community = Community.find_by(params[:community_id]) 5 @post = Post.new 6 @code = Code.all 7 end 8 9 def create 10 @post = current_user.posts.build(post_params) 11 12 if @post.save 13 redirect_to communities_url, notice:"お店「#{@post.title}」を登録しました。" 14 else 15 render :new 16 end 17 end 18 19 private 20 21 def post_params 22 params.permit(:title, :area, :prefecture_code, :rest_type, :community_id) 23 end 24 25end

ルーティング(routes.rb)※関連部分のみ抜粋

Ruby

1Rails.application.routes.draw do 2 3 resources :communities do 4 resources :posts do 5 end 6 7end

コードマスタ(schema.rb)※抜粋

Ruby

1 create_table "codes", options: "ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci", force: :cascade do |t| 2 t.string "code_id", null: false 3 t.string "sub_id", null: false 4 t.string "code", null: false 5 t.string "name" 6 t.datetime "created_at", null: false 7 t.datetime "updated_at", null: false 8 t.index ["code_id", "sub_id", "code"], name: "index_codes_on_code_id_and_sub_id_and_code", unique: true 9 end

不足情報等ございましたら、お手数をお掛けし恐れ入りますが、
ご指摘いただけますと幸いです。
何卒よろしくお願い申し上げます。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

guest

回答の取得に失敗しました

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.25%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問