繁体   English   中英

如何在Rails中实施投票?

[英]How to implement voting in Rails?

我在chapter 10Michael Hartl上的RailsTutorial上,做了一些额外的工作,为每个RailsTutorial添加了回形针图像。 当我向Micropost添加照片时,我称它为Microphoto
现在,我做了以下工作:

  1. 正确迁移数据库

     class CreateMicrophotos < ActiveRecord::Migration def change create_table :microphotos do |t| t.string :content t.integer :user_id t.integer :votes_up t.integer :votes_down t.timestamps end add_index :microphotos, [:user_id, :created_at] end end 
  2. 更改显微照片模型和控制器

  3. 写一些观点

这是我的文件:

用户模型

class User < ActiveRecord::Base
  require "paperclip" 
  attr_accessible :name, :email, :password, :password_confirmation, :avatar,
:avatar_file_name, :avatar_content_type, :avatar_file_size, :avatar_updated_at
  has_secure_password
  has_many :microphotos, dependent: :destroy
  has_attached_file :avatar, :styles => { :large => "120x120>", :medium => "48x48>", :thumb => "26x26>" }
  .
  .
  .
  def feed
    Microphoto
  end
end

显微照片模型

class Microphoto < ActiveRecord::Base
  attr_accessible :content, :votes_down, :votes_up, :photoclip,
  :photoclip_file_name, :photoclip_content_type, :photoclip_file_size, :photoclip_updated_at
  belongs_to :user
  has_attached_file :photoclip, :styles => { :large => "500x400>", :medium => "100x80>" }
  validates :content, presence: true, length: { maximum: 140 }  
  validates :user_id, presence: true
  default_scope order: 'microphotos.created_at DESC'
end

Microphotos控制器

class MicrophotosController < ApplicationController
  before_filter :signed_in_user, only: [:create, :destroy]
  def index
  end
  def create
    @microphoto = current_user.microphotos.build(params[:microphoto])
    if @microphoto.save
      flash[:success] = "Your photo has been uploaded successfully!"
      redirect_to root_url
    else
      render 'static_pages/home'
    end
  end
  def destroy
  end
end

我希望发生一件事:

  • 登录的用户可以从其他用户投票给Microphotos,但不能投票给其他人

    我该怎么办?

我试图更改microphotos控制器更改操作。 我知道这可能不是一个真正的问题,但是由于我是Rails的新手,所以我不能这样做。

[更新1]

我使用anonymousxxx建议的方法,但最终导致出现此路由错误消息:

没有路线匹配{:controller =>“ microphotos”,:action =>“ vote_up”,:id =>#}

使用命令rake routes我有这个:

        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
              PUT    /users/:id(.:format)       users#update
              DELETE /users/:id(.:format)       users#destroy
     sessions POST   /sessions(.:format)        sessions#create
  new_session GET    /sessions/new(.:format)    sessions#new
      session DELETE /sessions/:id(.:format)    sessions#destroy
  microphotos POST   /microphotos(.:format)     microphotos#create
   microphoto DELETE /microphotos/:id(.:format) microphotos#destroy
         root        /                          static_pages#home
       signup        /signup(.:format)          users#new
       signin        /signin(.:format)          sessions#new
      signout DELETE /signout(.:format)         sessions#destroy
         help        /help(.:format)            static_pages#help
        about        /about(.:format)           static_pages#about
        terms        /terms(.:format)           static_pages#terms
      vote_up PUT    /vote_up/:id(.:format)     microphotos#vote_up
    vote_down PUT    /vote_down/:id(.:format)   microphotos#vote_down

[更新2]

经过他的指示,我得到了这个ArgumentError
can't use collection outside resource(s) scope

config/routes.rb:18:in `block (3 levels) in <top (required)>'
config/routes.rb:17:in `block (2 levels) in <top (required)>'
config/routes.rb:16:in `block in <top (required)>'
config/routes.rb:1:in `<top (required)>'

这是routes.rb

16  resources :microphotos do
17    collection do
18      put '/vote_up/:id' => "microphotos#vote_up", :on => collection, :as => :vote_up
19      put '/vote_down/:id' => "microphotos#vote_down", :on => collection, :as => :vote_down
20    end
21  end

您可以使用act_as_votable gem。

安装gem:

gem 'acts_as_votable', '~> 0.5.0'
bundle

安装和运行迁移:

rails generate acts_as_votable:migration
bundle exec rake db:migrate

Microphoto模型中,您应该具有:

acts_as_votable

完成此操作后,您可以使用以下方法来投票/撤消microphotos

@microphoto.liked_by @user1
@microphoto.downvote_from @user2
@microphoto.vote :voter => @user3
@microphoto.vote :voter => @user4, :vote => 'bad'
@microphoto.vote :voter => @user5, :vote => 'like'

考虑一下act_as_rateable gem,它可能比Marek Lipka建议的适合您的特定用例更适合您。

解决方案1(用户可以多次投票)

您可以在显微照片上使用if.. else..语句。

参见清单10.46 将删除链接添加到微博部分。

微型帖子只能由所有者用户删除。

<% if current_user?(micropost.user) %>
    <%= link_to "delete", micropost, method: :delete,
                                     data: { confirm: "You sure?" },
                                     title: micropost.content %>
  <% end %>

示例(未经测试,但希望能对您有所帮助):

  # on view (e.g show.html.erb)

  <% if signed_in? && current_user.id != feed_item.user_id %>
    <%= link_to "vote up", vote_up_microphotos_url(feed_item.id), :method => :put %> 
    <%= link_to "vote down", vote_down_microphotos_url(feed_item.id), :method => :put %>
  <% end %>


  # controller
  before_filter :signed_in_user, only: [:create, :destroy, :vote_up, :vote_down]


  def vote_up
    @microphoto = Microphoto.find(params[:id])
    @microphoto.update_attribute(:votes_up, @microphoto.votes_up + 1)
    redirect_to root_path
  end

  def vote_down
    @microphoto = Microphoto.find(params[:id])
    @microphoto.update_attribute(:votes_down, @microphoto.votes_down + 1)
    redirect_to root_path
  end

  # route
  resources :microphotos do
    collection do
     put '/vote_up/:id' => "microphotos#vote_up", :as => :vote_up
     put '/vote_down/:id' => "microphotos#vote_down", :as => :vote_down
    end
  end

解决方案2(用户不能多次投票)

如果你想用户无法在显微照片多票,你应该有一个单独的模型microphoto model的选举权和vote model具有与关系microphoto model ,关系是这样的:

class User < ActiveRecord::Base
has_many :vote_photos
has_many :microphotos
end

class Microphoto < ActiveRecord::Base
has_many :vote_photos
belongs_to :user
end

class VotePhoto < ActiveRecord::Base
 belongs_to :microphoto
 belongs_to :user
end

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM