【问题标题】:Updating a record with rails 4使用 rails 4 更新记录
【发布时间】:2015-08-16 22:57:44
【问题描述】:

我正在尝试使用管理员用户更新记录,并使用“验证”按钮将记录的状态从待处理更改为已确认。我已经创建了一个表单,以及这样做的路线,但是控制器给我带来了麻烦,我不确定要为它编写什么代码来更新我点击验证的特定记录。

小时控制器

def index
    @allhours = HourLog.where(status:'Pending')
  end
def update
    @hour = HourLog.where(status:'Pending')
    @hour.update(@hour.id, :status)
  end

小时/index.html.erb

<td><%=form_for(:hour_log, method: :put) do |f|%>
    <%= f.hidden_field :status, :value => 'Confirmed' %>
    <%= f.submit 'Validate'%>
    <%end%>
</td>

任何帮助都会很棒,谢谢!

错误: HoursController 中的 NoMethodError#update #

的未定义方法“id”

我知道更新定义中控制器的 (@hour.id) 部分有问题,但我不知道用什么替换它

编辑:耙路线

         Prefix Verb   URI Pattern                Controller#Action
           root GET    /                          welcome#index
         signup GET    /signup(.:format)          users#new
          users GET    /users(.:format)           users#index
                POST   /users(.:format)           users#create
       new_user GET    /users/new(.:format)       users#new
      edit_user GET    /users/:id/edit(.:format)  users#edit
           user GET    /users/:id(.:format)       users#show
                PATCH  /users/:id(.:format)       users#update
                PUT    /users/:id(.:format)       users#update
                DELETE /users/:id(.:format)       users#destroy
                GET    /users(.:format)           users#index
                PUT    /users(.:format)           users#update
          login GET    /login(.:format)           sessions#new
                POST   /login(.:format)           sessions#create
         logout DELETE /logout(.:format)          sessions#destroy
      dashboard GET    /dashboard(.:format)       hours#new
dashboard_hours GET    /dashboard/hours(.:format) hours#index
          hours PUT    /hours(.:format)           hours#update
                GET    /hours(.:format)           hours#index
                POST   /hours(.:format)           hours#create
       new_hour GET    /hours/new(.:format)       hours#new
      edit_hour GET    /hours/:id/edit(.:format)  hours#edit
           hour GET    /hours/:id(.:format)       hours#show
                PATCH  /hours/:id(.:format)       hours#update
                PUT    /hours/:id(.:format)       hours#update
                DELETE /hours/:id(.:format)       hours#destroy

小时控制器

class HoursController < ApplicationController
  before_action :require_user
  before_action :require_admin, only: [:index]
  def index
    @allhours = HourLog.where(status:'pending')
  end
  def new
    @hour = current_user.hour_logs.new
    @entry = current_user.hour_logs.all
  end
  def edit
    flash[:warning] =  "Hash: #{params}"
  end

  def create
    @hour = HourLog.new(hour_params)
    @hour.user_id = current_user.id if current_user
    @hour.status = 'pending'
    if @hour.save
      redirect_to '/dashboard'
    end
  end
  private
  def hour_params
    params.require(:hour_log).permit(:assignment, :hours, :supervisor, :date)
  end
  def update_hour_params
    params.require(:hour_log).permit(:status)
  end
end

HourLog 方法

class HourLog < ActiveRecord::Base
  belongs_to :user
end

【问题讨论】:

  • “但是控制器给我带来了麻烦。”这甚至意味着什么?您看到的确切问题是什么?
  • 由于我输入的“id”,它没有更新记录。如果我输入 (params[:id], :status),那么它说它找不到没有 id 的记录。现在它说“.id”是一个未定义的方法
  • @DKucher 请在问题正文中发布完整的错误消息

标签: ruby-on-rails ruby-on-rails-4


【解决方案1】:

我看到这个答案已被接受,但我想为任何可能出现并找到这个问题的人提出一个替代解决方案。假设:基本页面是一个包含所有待处理项目的索引,点击是一个简单的状态变化。 (可以轻松地将状态切换添加到此解决方案中。)

(我正在使用问题中的命名。)

使用 link_to 作为消息

可以通过使用 link_to 触发控制器操作以更新此标志来实现标志从“待定”到“已确认”的状态更改。 哈希参数可以通过链接传递,以启用控制器中的简化逻辑。

查看:Index.html.erb

<% @allhours.each do |hour| %>
  <ul>
    <li><%= hour.textdescriptionvar %> is an item pending approval. 
        <%= link_to(" Click to approve", edit_hour_path(hour, :status => "Confirmed"))
    </li>
  </ul>

<% end %>

控制器:HourLogsController

       def edit
            flash[:info] =  "Hash: #{params}"
            @hour = HourLog.find(params[:id])
        end

        def update
            @hour = HourLog.find(params[:id])
            @hour.update_attributes(hours_params)
            if  @hour.save
               redirect_to @hour, :notice => "Successfully changed stat."
            else
                render 'index' # Any action here, index for example
            end
          end
    private

        def hours_params
          params.require(:hour_log).permit(:status)           
        end

我会推荐一个数据:确认消息被添加到link_to,但我想模仿张贴者的情况。

link_to here 的 Rails 规范。

【讨论】:

  • 当然。我只是使用了通用路径。您需要在您的倾斜路线中查找 url 并找到 hour_log 的编辑路径。如果您需要这方面的帮助,请发布您的 $rake 路线的输出
  • 酷。使用您的 URL 更新了答案,即 edit_hour_path(...)。告诉我进展如何。
  • 我使用了 hour_log,因为那是您发布的表单上的模型名称。它应该是您定义 <:base> 的模型的小写名称
  • 我在不同的参数中使用 hour_log,它正在工作。但这似乎不起作用
  • 我们需要找出 params{} 哈希中的变量名是什么。这是该方法中需要的名称。
【解决方案2】:

@hour = HourLog.where(status:'Pending') 将返回一个 ActiveRecord 关系,而不是一条记录。

试试这个:

@hour = HourLog.find_by(status: 'pending')
@hour.update_attribute :status, params[:hour_log][:status]

此方法查找状态为 ="pending" 的第一条记录并更新它而不是特定记录。

【讨论】:

  • 我试过了,得到了这个错误:NoMethodError in HoursController#update undefined method `update_attribute' for nil:NilClass
  • 哦,这意味着没有 statuspending 的 HourLog。
  • 但是我有一个显示 HourLog 条目状态的视图,它仍然显示待处理。我认为“update_attribute”是问题所在。有什么方法可以使用不同的方法吗?
  • 不,如果它显示undefined method 'update_attribute' for nil,那么它告诉你它试图在nil上调用update_attribute,这意味着@hournil,这意味着HourLog.find_by(status: 'pending')正在返回nil,这意味着它找不到任何具有该状态的东西。您可以将其与HourLog.where(status: 'pending').count 进行比较,您会发现它是0
  • 你说得对,“待定”只是大小写问题。现在我收到一个模板错误:缺少模板小时/更新,应用程序/更新 {:locale=>[:en], :formats=>[:html], :variants=>[], :handlers=>[ :erb, :builder, :raw, :ruby, :coffee, :jbuilder]}。在以下位置搜索:*“C:/Users/DK/desktop/project/nhs/app/views”*“C:/RailsInstaller/Ruby2.0.0/lib/ruby/gems/2.0.0/gems/twitter-bootstrap-rails -3.2.0/app/views"
【解决方案3】:

您将需要@hour.update params[:hour_log],因为update_attribute 不运行验证。并将数据库中的数据保留为小写,除非它是由用户编写的。这个链接很有用http://www.davidverhasselt.com/set-attributes-in-activerecord/

【讨论】:

    猜你喜欢
    • 2015-04-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多