質問をすることでしか得られない、回答やアドバイスがある。

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

新規登録して質問してみよう
ただいま回答率
85.48%
Ruby on Rails

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

Q&A

解決済

1回答

3405閲覧

strongparameterで値をハッシュに変換できない

ketyan

総合スコア22

Ruby on Rails

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

0グッド

0クリップ

投稿2020/01/20 08:37

###現状とエラー
現在railsを使ってアプリを製作中です。
updateアクションを実行したいのですが、unable to convert unpermitted parameters to hashのエラーで失敗してしまいます。

###コード
エラーコード
ストロングパラメータの行でエラーが起きています

ActionController::UnfilteredParameters - unable to convert unpermitted parameters to hash: app/controllers/incomes_controller.rb:41:in `block in incomes_params' app/controllers/incomes_controller.rb:40:in `incomes_params' app/controllers/incomes_controller.rb:11:in `create

モデル
Incomeモデル:category,price,date,memoの4つのカラムを持っています

IncomeModel

1class Income < ApplicationRecord 2 default_scope -> { order(date: :desc) } 3 validates :category, presence:true 4 validates :price, presence:true 5 validates :date, presence:true 6 validates :memo, presence:true, length: { maximum: 40 } 7end

Income_collectionモデル:Incomeをまとめて作成、変更するためのモデルです

IncomeCollectionModel

1class IncomeCollection < ApplicationRecord 2end 3class IncomeCollection 4 include ActiveModel::Conversion 5 extend ActiveModel::Naming 6 extend ActiveModel::Translation 7 include ActiveModel::AttributeMethods 8 include ActiveModel::Validations 9 INCOME_NUM = 5 10 attr_accessor :collection # ここに作成したモデルが格納される 11 12 13 def initialize(attributes = []) 14 if attributes.present? 15 self.collection = attributes.map do |value| 16 Income.new( 17 category: value['category'], 18 price: value['price'], 19 date: value['date'], 20 memo: value['memo'] 21 ) 22 end 23 else 24 self.collection = INCOME_NUM.times.map{ Income.new } 25 end 26 end 27 28 # レコードが存在するか確認するメソッド 29 def persisted? 30 false 31 end 32 33 34 # コレクションをDBに保存するメソッド 35 def save 36 is_success = true 37 ActiveRecord::Base.transaction do 38 collection.each do |result| 39 # バリデーションを全てかけたいからsave!ではなくsaveを使用 40 is_success = false unless result.save 41 end 42 # バリデーションエラーがあった時は例外を発生させてロールバックさせる 43 raise ActiveRecord::RecordInvalid unless is_success 44 end 45 rescue 46 p 'エラー' 47 ensure 48 return is_success 49 end 50 51 end

コントローラー
Incomesコントローラー

IncomesController

1class IncomesController < ApplicationController 2 def edit 3 @incomes = Income.all 4 end 5 6 def update 7 @incomes = incomes_params.to_unsafe_h.map do |id, income_param| 8 income = Income.find(id) 9 income.update_attributes(income_param) 10 income 11 end 12 redirect_to incomes_path 13 14 end 15 16 private 17 18 def incomes_params 19 params.require(:incomes).map do |p| 20 ActionController::Parameters.new(p.to_hash).permit(:category, :price, :date, :memo) 21 end 22 end 23 24end

ビュー
editページ

Edit

1<%= form_tag income_path, method: :put do %> 2 <% @incomes.each do |income| %> 3 <%= fields_for "incomes[]", income do |fi| %> 4 <section class = "row incomes_row"> 5 <div class="incomes_item col-sm-3"> 6 <%= fi.label :カテゴリ %> 7 <%= fi.text_field :category, class:"form" %> 8 </div> 9 10 <div class="incomes_item col-sm-3"> 11 <%= fi.label :金額 %> 12 <%= fi.text_field :price %> 13 </div> 14 15 <div class="incomes_item col-sm-3"> 16 <%= fi.label :日付 %> 17 <%= fi.text_field :date %> 18 </div> 19 20 <div class="incomes_item col-sm-3"> 21 <%= fi.label :メモ %> 22 <%= fi.text_field :memo %> 23 </div> 24 </br> 25 </section> 26 <br /> 27 <% end %> 28 <% end %> 29 <%= submit_tag %> 30<% end %>

###原因予想
income_collectionモデルからインスタンスを作っている事が原因で
上手くパラメータを渡せていないかなと思っています。

  • githubの同じような事例を試したのですがダメでした。
  • ストロングパラメータのpermitをpermit!にしても変化がありませんでした。

原因がお分かりの方がいらっしゃいましたらご指摘をお願いいたします。

###開発環境
Rails 5.2.4.1

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

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

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

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

とりあえずパラメータ全体を.permit!すれば.to_hashできます。
が、params.require(:incomes)の中身がよくわからないのでセキュリティー面は保証できません

rb

1params.require(:incomes).permit!.map do |p| # 質問とは関係ないけど p 変数を作るのは p メソッドがある関係上よくない。 2 ActionController::Parameters.new(p.to_hash).permit(:category, :price, :date, :memo) 3end

投稿2020/01/20 09:04

Mugheart

総合スコア2344

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

ketyan

2020/01/20 11:06

Mugheartさん、ご返信有り難うございます。 いろいろと試してみたところ、mapメソッドを取り除いたところpermit! を使わずにアプリが動きました。 動いた理由を調べてみようと思います。 ご回答頂きありがとうございました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

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

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

質問する

関連した質問