0

我有一个项目控制器和模型以及一个投标控制器和模型。当用户创建更高价格的新出价时,我想提高该项目的当前出价。

当用户创建一个项目时,他们可以设置起始价格,即项目表中的“价格”列。

我的架构如下:

 create_table "bids", force: true do |t|
    t.datetime "created_at"
    t.datetime "updated_at"
    t.integer  "item_id"
    t.integer  "user_id"
    t.integer  "amount"
  end

  create_table "items", force: true do |t|
    t.datetime "created_at"
    t.datetime "updated_at"
    t.integer  "user_id"
    t.string   "title"
    t.integer  "price"
  end

物品控制器:

class ItemsController < ApplicationController
  before_action :set_item, only: [:show, :edit, :update, :destroy]
  before_filter :user_signed_in?

  def index
    @item = Item.all
  end

  def show
    @item = Item.find(params[:id])

  end

  def edit
  end

  def new
    @item = Item.new
    @item.bids.build
  end

  def create
    @item = Item.new(item_params)
    if @item.save
      redirect_to @item, notice: 'Item successfully created.'
    else
      format.html { render action: 'new'}
    end
  end

  def update
    respond_to do |format|
      if @item.update(item_params)
        format.html { redirect_to @item, notice: 'Your item has been updated.'}
      else
        format.html { render action: 'edit'}
      end
    end
  end

  def destroy
    @item.destroy
    respond_to do |format|
      format.html { redirect_to items_url }
    end
  end


  private

  def set_item
    @item = Item.find(params[:id])
  end

  def item_params
    params[:item][:user_id] = current_user.id
    params[:item].permit(:price, :user_id, :title, :bids_attributes => [:amount, :user_id, :item_id])
  end



end

投标控制器:

class BidsController < ApplicationController
  before_action :set_bid, only: [:show, :edit, :update, :destroy]

  def show
    @bid = Bid.find(params[:id])
  end

  def new
    @item = Item.find(params[:item_id])
    @bid = @item.bids.build
  end

  def create
    @item = Item.find(params[:item_id])
    @bid = @item.bids.new(bid_params)

    respond_to do |format|
      if @bid.save
        format.html { redirect_to item_url(params[:track_id]), notice: "Bid successfully placed."}
      else
        format.html { render action: 'new' }
      end
    end
  end

    private
    def set_bid
      @bid = Bid.find(params[:id])
    end

    def bid_params
      params[:bid][:user_id] = current_user.id

      params[:bid].permit(:amount, :user_id, :item_id)
    end
end

实现这一目标的最佳方法是什么?我还需要创建一个验证,以确保输入的数字高于当前价格。

4

1 回答 1

0

您可以在控制器或模型中执行此操作。为了方便,我喜欢在模型中做这种事情。您必须担心的另一件事是如果取消出价会发生什么?您还需要更新父级。

此代码完全未经测试

class Item < ActiveRecord::Base    

  def check_highest_bid
    highest_bid = self.bids.order("amount DESC").first.amount rescue 0
    self.price = highest_bid
    save
  end

end

class Bid < ActiveRecord::Base   

  validate :check_if_highest_bid

  after_save :update_item
  after_destroy :update_item

  def update_item
    self.item.check_highest_bid
  end     

  def check_if_highest_bid
     errors.add(:amount, "must be higher than current bid") unless self.item.price < self.amount
  end
end

文档: http ://edgeguides.rubyonrails.org/active_record_validations.html#custom-methods

于 2013-09-22T07:24:52.337 回答