ruby-on-rails - 如何在我的 rails 模型中访问参数(或使用解决方法)?
问题描述
我正在尝试将我的 rails 控制器中的一些代码重构为我的模型,但我发现我对 rails 工作原理的理解存在差距。我试图让 Raffle 类可以使用这两种方法,但我正在努力理解如何做到这一点。当我点击此代码时,返回错误“#Raffle:0x00007f88c9af8940 的未定义局部变量或方法‘参数’”。
如何解决模型无法使用的参数?抱歉,如果这是一个初学者问题-我绝对是初学者。
#app/models/raffle.rb
class Raffle < ApplicationRecord
has_many :tickets
has_many :users, through: :tickets
def bid_tickets(tier)
params[:raffle][:"tier"].to_i #error returned here
end
def bid_total
(bid_tickets(gold) * 3) + (bid_tickets(silver) * 2) + bid_tickets(bronze)
end
#app/views/edit.html.erb
<%= form_for(@raffle) do |f| %>
<%=f.label :ticket, "Gold" %>: <br>
<%= image_tag "gold.jpg", class: "small_ticket" %><br>
<%=f.number_field :gold%><br>
<%=f.label :ticket, "Silver" %>:<br>
<%= image_tag "silver.jpg", class: "small_ticket" %><br>
<%=f.number_field :silver %><br>
<%=f.label :ticket, "Bronze" %>:<br>
<%= image_tag "bronze.jpg", class: "small_ticket" %><br>
<%=f.number_field :bronze %> <br><br>
<%= f.submit "Use Tickets" %>
<% end %><br>
#app/controllers/raffles_controller.rb
def update
if @raffle.enough_slots? + @raffle.current_bids > @raffle.number_of_ticket_slots
if enough_tickets?
redirect_to edit_raffle_path, notice: "You do not have enough tickets."
else
redirect_to edit_raffle_path, notice: "There aren't enough spots left in this raffle to handle your entry! Please use less tickets."
end
else @raffle.update_tickets(current_user)
if @raffle.slots_filled?
@raffle.select_winner
end
redirect_to edit_raffle_path(@raffle)
end
end
returned parameters:
{"_method"=>"patch",
"authenticity_token"=>"xyz",
"raffle"=>{"gold"=>"1", "silver"=>"", "bronze"=>""},
"commit"=>"Use Tickets",
"id"=>"1"}
编辑:
#app/controllers/raffles_controller.rb (StrongParameters)
class RafflesController < ApplicationController
private
def raffle_params
params.require(:raffle).permit(:product_name, :product_description,
:product_image, :number_of_ticket_slots, :filter)
end
end
解决方案
params
在控制器中(通过 Rails)提供给您,因为它是“网络请求”。最好不要将其更深入地传递到您的系统中,因为它包含外部“不受信任”的输入。这就是为什么它不会自动在模型中可用的原因。
例如:
# controller
def update
safe_value = validate_value(params[:unsafe_value]) # extract and validate
# no "web request things" passed in
result = MyFeature.do_stuff(@current_user, safe_value) # pass it to other parts of system
# then convert the result back into a "web request thing", e.g:
# return render json: as_json(result) # return result as json
# return redirect_to endpoint_for(result) # redirect based on result
# etc
end
在将数据作为参数传递给系统的其他部分(如模型)之前,对参数进行预处理(提取值、验证它们等)是一种很好的做法。
这将使您的系统的其余部分与“Web 请求事物”无关,使它们以目的为中心且井井有条。
一方面,StrongParameters
这是一个有助于解决此问题的内置导轨功能。
推荐阅读
- android - 如何修复 org.threeten.bp.format.DateTimeParseException?
- scala - 如何转换 Scala 集合类型?如 Seq[Any] 到 Seq[(String, String)] 没有警告
- c# - 用于创建和发送营销活动的 SendGrid API 失败,因为缺少取消订阅标签
- python-import - Python 中的合格导入
- ssl - 在 IIS 上全局应用 SSL - 需要建议
- excel - COUNTIF 返回 0
- go - 相当于Java在GoLang中将Object作为方法参数传递
- html - 在弹性盒内使用时,网格没有占据其 div 的全部高度
- ajax - woocommerce 网关上的 WPML 字符串翻译(ajax 问题)
- sql-server - EF Core 计算的主键属性未更新