質問編集履歴

4

回答を参考に行ったことを記述しました

2020/08/24 14:52

投稿

fresh_fish
fresh_fish

スコア20

test CHANGED
File without changes
test CHANGED
@@ -55,3 +55,125 @@
55
55
  end
56
56
 
57
57
  ```
58
+
59
+
60
+
61
+ ### 回答を参考にして
62
+
63
+ サーバーログで確認したパラメータ
64
+
65
+ "band"=>{"name"=>"Beatles", "relationships_attributes"=>{"0"=>{"user_id"=>"2", "part"=>"Gt1", "_destroy"=>"false"}, "1598231822108"=>{"user_id"=>"0", "part"=>"Vo1", "_destroy"=>"false"}}}
66
+
67
+
68
+
69
+ と実際のパラメータ
70
+
71
+ <ActionController::Parameters {"name"=>"Beatles", "relationships_attributes"=><ActionController::Parameters {"0"=><ActionController::Parameters {"part"=>"Gt1", "user_id"=>"2", "_destroy"=>"false"} permitted: true>, "1598279704474"=><ActionController::Parameters {"part"=>"Vo1", "user_id"=>"0", "_destroy"=>"false"} permitted: true>} permitted: true>} permitted: true>
72
+
73
+
74
+
75
+ が違ったためrelations.any?{|k,v| v["user_id"].to_i == current_user.id}では
76
+
77
+ エラー undefined method `any?' for #<ActionController::Parameters:0x00007fb8b09e55c8>
78
+
79
+ が起きてしまいました。
80
+
81
+ そこでセキュリティ的に問題はありますがto_unsafe_hを付けてみました
82
+
83
+
84
+
85
+
86
+
87
+ ```ここに言語を入力
88
+
89
+ bands_controller.rb
90
+
91
+ .
92
+
93
+ .
94
+
95
+ .
96
+
97
+
98
+
99
+ def create
100
+
101
+ @band = Band.new(band_params)
102
+
103
+ if validate_on_create(band_params)
104
+
105
+ if @band.save
106
+
107
+ redirect_to @band
108
+
109
+ flash[:notice] = 'バンドの登録に成功しました'
110
+
111
+ else
112
+
113
+ flash[:alert] = 'バンドの登録に失敗しました(save)'
114
+
115
+ redirect_to new_band_path
116
+
117
+ end
118
+
119
+ else
120
+
121
+ flash[:alert] = 'バンドの登録に失敗しました(validate)'
122
+
123
+ redirect_to new_band_path
124
+
125
+ end
126
+
127
+ end
128
+
129
+ .
130
+
131
+ .
132
+
133
+ private
134
+
135
+
136
+
137
+ def validate_on_create(relations)
138
+
139
+ relations.to_unsafe_h.any?{|k,v| v["user_id"].to_i == current_user.id}
140
+
141
+ end
142
+
143
+ ```
144
+
145
+ このように記述したところなんとか動いたのですが、本来通るはずであるuser_id == current_userでも'バンドの登録に失敗しました(validate)'と表示され通りません(ページの描写は出来ている)
146
+
147
+ そこで validate_on_craeteメソッドから意図的に to_unsafe_h を外してエラーを起こしbetter_errorでデバッグしてみました
148
+
149
+ ```ここに言語を入力
150
+
151
+ コンソール
152
+
153
+
154
+
155
+ >> relations
156
+
157
+ => <ActionController::Parameters {"name"=>"Beatles", "relationships_attributes"=><ActionController::Parameters {"0"=><ActionController::Parameters {"part"=>"Gt1", "user_id"=>"2", "_destroy"=>"false"} permitted: true>, "1598279704474"=><ActionController::Parameters {"part"=>"Vo1", "user_id"=>"0", "_destroy"=>"false"} permitted: true>} permitted: true>} permitted: true>
158
+
159
+ >> relations.any?
160
+
161
+ !! #<NoMethodError: undefined method `any?' for #<ActionController::Parameters:0x00007fb8b09e55c8>>
162
+
163
+ >> relations.to_unsafe_h
164
+
165
+ => {"name"=>"Beatles", "relationships_attributes"=>{"0"=>{"part"=>"Gt1", "user_id"=>"2", "_destroy"=>"false"}, "1598279704474"=>{"part"=>"Vo1", "user_id"=>"0", "_destroy"=>"false"}}}
166
+
167
+ >> relations.to_unsafe_h.any?
168
+
169
+ => true
170
+
171
+ >> relations.to_unsafe_h.any?{|k,v| v["user_id"].to_i == 2}
172
+
173
+ => false ##コンソールではcurrent_user.idが使えないため代わりに同じ値の2を使用しています
174
+
175
+
176
+
177
+ ```
178
+
179
+ 一体なぜここがFalseになるのでしょうか?

3

2020/08/24 14:52

投稿

fresh_fish
fresh_fish

スコア20

test CHANGED
@@ -1 +1 @@
1
- Railsにて複雑にネスト化されたパラメータのカスタムバリデーション
1
+ Railsにてネスト化されたパラメータのカスタムバリデーション
test CHANGED
File without changes

2

タイトルの変更

2020/08/24 10:28

投稿

fresh_fish
fresh_fish

スコア20

test CHANGED
@@ -1 +1 @@
1
- 複雑にネスト化されたパラメータのカスタムバリデーション
1
+ Railsにて複雑にネスト化されたパラメータのカスタムバリデーション
test CHANGED
File without changes

1

試したことを記述しました

2020/08/24 01:57

投稿

fresh_fish
fresh_fish

スコア20

test CHANGED
File without changes
test CHANGED
@@ -37,3 +37,21 @@
37
37
  )
38
38
 
39
39
  ```
40
+
41
+ ### 試したこと
42
+
43
+ 最初の構想ではこういうバリデーションを作ろうとしていました
44
+
45
+ ```ここに言語を入力
46
+
47
+ class BandCreateValidator < ActiveModel::Validator
48
+
49
+ def validate(record)
50
+
51
+ record.each do |r|
52
+
53
+ end
54
+
55
+ end
56
+
57
+ ```