我创建了一个按钮,用户可以在其中输入内容,然后按下该按钮以更新数据库(put
请求),可以在show.html.erb
中看到此信息:
<% provide(:title, @user.name) %>
<div class="row">
<aside class="col-md-4">
<section class="user_info">
<h1>
<%= gravatar_for @user %>
<%= @user.name %>
<br>
<%= @user.email %>
<% if @errors %>
<p>THE FORM COULD NOT BE SAVED </p>
<ul id='errors'>
<% @errors.each do |error| %>
<li><%= error %></li>
<% end %>
</ul>
<% end %>
<br>
<% if is_admin? %>
<% if !@user.admin %>
<div class="row">
<div class="col-md-6 col-md-offset-3">
<%= form_for(@user) do |f| %>
<%= f.label :wistia_project_id %>
<%= f.text_field :wistia_project_id, class: 'form-control' %>
<%= f.submit "Save", :action => "set_wistia_project_ID", :method => :patch, :form_class => "form-control" %>
<% end %>
</div>
</div>
<% end %>
<% end %>
</h1>
</section>
</aside>
</div>
该函数位于user_controller.rb
中:
# Sets wistia_project_ID.
def set_wistia_project_ID
@user = User.find(params[:id])
@user.set_project_id
unless @user.valid?
@errors = @user.errors.full_messages
render :show
end
end
该函数调用另一个函数,只是为了更清楚地分离事物。此其他函数位于user.rb
中:
# Sets the wistia_project_ID.
def set_project_id!(val)
self.wistia_project_ID = val # self is necessary here
save # or self.save, but the self is unnecessary here
end
我的routes.rb
:
.
.
.
resources :users do
member do
patch 'set_wistia_project_ID'
end
end
我的问题是,当您按下按钮时,它说:Completed 500 Internal Server Error in 26ms (ActiveRecord: 0.7ms)
和
NoMethodError (undefined method `set_project_id' for #<User:0x000055b1a0914ab8>
2019-06-26T14:46:34.940086+00:00 app[web.1]: Did you mean? wistia_project_id):
答案 0 :(得分:3)
Zavitoski正确了。但是,我建议您所做的许多事情从根本上来说都是错误的。鉴于您尚处于起步阶段,我希望您不要介意我指出几点。
首先,要挑剔,是的,您创建了一个按钮。但是,它不是“用户可以在字段中输入内容然后按此按钮来更新数据库”的按钮。您在 form 上创建了一个按钮。然后您在该表单上创建了一个 field 。用户可以在现场输入内容。然后单击该按钮将提交包含该字段信息的表单。
现在,您在该表格上做了:
<%= form_for(@user) do |f| %>
<%= f.label :wistia_project_id %>
<%= f.text_field :wistia_project_id, class: 'form-control' %>
<%= f.submit "Save", :action => "set_wistia_project_ID", :method => :patch, :form_class => "form-control" %>
<% end %>
有一些问题:
:action => "set_wistia_project_ID"
首先,set_wisteria_project_ID
不是一个非常红宝石的动作名称。 set_wistia_project_id
更像它。另外,您正在使用旧格式的键值格式。并且,您可以使用符号而不是字符串作为操作名称,从而使代码更漂亮。也许是这样的:
<%= f.submit "Save", action: :set_wistia_project_id, method: :patch, form_class: "form-control" %>
但是,这也是一个错误。因为您不需要执行set_wistia_project_id
操作。 (这是action
或method
,而不是function
。)您已经执行了update
操作。如果form_for
是@user
的实例,那么User
足够聪明,可以执行此操作。因此,实际上,您应该这样做:
<%= form_for @user do |f| %>
<%= f.label :wistia_project_id %>
<%= f.text_field :wistia_project_id, class: 'form-control' %>
<%= f.submit "Save", form_class: "form-control" %>
<% end %>
我不确定form_class
是什么,但我相信它是正确的。
现在,在您的UsersController
中,只需执行以下操作:
class UsersController < ApplicationController
def update
@user = User.find(params[:id])
if user.update(user_params)
# do something successful
else
# do something unsuccessful
end
end
private
def user_params
# NOTE: You'll probably want to permit other stuff here, too.
params.require(:user).permit(:wistia_project_id)
end
end
摆脱这个:
class User < ApplicationRecord
# Sets the wistia_project_ID.
def set_project_id!(val)
self.wistia_project_ID = val # self is necessary here
save # or self.save, but the self is unnecessary here
end
end
因为您只是在复制update
方法。并且,您可能希望该属性为wistia_project_id
,而不是wistia_project_ID
。 (同样,您永远不会将_ID
作为rails核心的后缀,并且您可能会很习惯。)而且,如果您确定关联设置正确,ActiveRecord应该确保wistia_project_id
实际上是有效值。
然后像这样写您的routes.rb
:
resources :users
因为您不需要所有set_wistia_project_id
业务。
答案 1 :(得分:2)
似乎您没有使用定义的名称来调用函数,也没有传递所需的参数(project_id)。
def set_wistia_project_ID
@user = User.find(params[:id])
@user.set_project_id!(params[:wistia_project_id])
unless @user.valid?
@errors = @user.errors.full_messages
render :show
end
end
这应该使用您创建的函数并从表单中传递参数。