2012-05-10 8 views
1

と「最初の」または「作成」であるならば、私はこの文を使用しようとしている差別ん:は、どのように私は何かがfirst_or_create

@vote = Vote.where(:resource_id => params[:id], :user_id => current_user.id).first_or_create(:value => 1) 

これはupvoteまたはdownvoteのためです。 DB内に行が存在しない場合は、それを作成する必要があります(投稿に投票したことはありません)。それ以外の場合は-1,0,1で値を変更する必要があります。

2回目にupvoteをクリックすると、投票を取り消して、1行ではなく0行に置く必要があります。同じことがdownvoteで起こりますが、これは現在upvote関数のみです。

レールでもこの​​ステートメントのデバッグに問題があります。基本的には、保存されたレコードと作成されたレコードのどちらを区別する必要がありますか。私が入れた場合:

@vote = Vote.where(:resource_id => 25, :user_id => 1) 
@vote.exists? 

は私がtrue

を取得するが、私はこれを置けば...(とレコードが存在し、それだけで上記働いていた)..私は取得

@vote = Vote.where(:resource_id => 25, :user_id => 1).first_or_create(:value => 1) 
@vote.exists? 

を.. 。 NoMethodError:未定義のメソッド `exists? ' #

2つのオブジェクトのクラスを見ると、1つは「投票」で、1つは「ActiveRecord :: Relation」です。

私の究極の目標は、そう(ゼロに設定し、投票を元に戻す場合は何とかそうこれは1

でそれを置く)、投票値が既に1であれば、それはチェックこの(ほとんどの部分をリファクタリングすることです。私はfirst_or_createとリファクタリングしようとして始めた前に長いと醜いコード

if @vote.exists? 
     # Check if they have already voted 
     if @vote.first.value == 1 
     @vote.first.value = 0 
     else 
     @vote.first.value = 1 
     end 
     flash[:notice] = "previous vote modified" 
     @vote.first.save 
    else 
     # Create a new Vote instance, save it 
     @vote = Vote.new(:resource_id => params[:id], :user_id => current_user.id, :value => 1) 
     if @vote.valid? 
     @vote.save 
     flash[:notice] = "New vote added" 
     else 
     @vote.save 
     flash[:notice] = (@vote.errors.full_messages).to_s 
     end 
    end 

答えて

5

私の代わりにRailsの魔法のメソッドfind_or_create_byメソッドを使用します

ここで「ダイナミック属性ベースのファインダ」をチェックアウト:。。

http://api.rubyonrails.org/classes/ActiveRecord/Base.html

あなたは、動的な発見方法のようにそれを使用しますが、その後、あなたはそれが存在しない場合は投票を作成するために、追加したい余分な変数を渡します。あなたのケースでは

、それはのようなものだろう:あなたはそれをすぐに作成したくない場合は、基本的に保存せずにVote.newを作成find_or_initialize_byを使用することができます

@vote = Vote.find_or_create_by_resource_id_and_user_id(25, 1, :value => 1) 

+1

ありがとうSteph!女性のルビー開発者は私のお尻をキッキン! – Tallboy

+0

ハハ!私はちょうど前に、これらの方法の力に直面しました。 :) –

+1

残念ながら、これらのメソッドはRails 4では廃止されています。したがって、この提案は現在とRailsの次のバージョンでは機能しますが、今後の互換性の問題が発生します。 –

関連する問題