Commit 51e3a6930d27d7f06c32244b197895dff4151b0e
1 parent
d0820545
Exists in
master
and in
1 other branch
Handle updating counter cache values when invalid flag is used
Showing
3 changed files
with
108 additions
and
8 deletions
Show diff stats
app/models/vote.rb
| ... | ... | @@ -23,6 +23,7 @@ class Vote < ActiveRecord::Base |
| 23 | 23 | serialize :tracking |
| 24 | 24 | |
| 25 | 25 | after_create :update_winner_choice, :update_loser_choice |
| 26 | + after_save :update_counter_caches_based_on_flags | |
| 26 | 27 | |
| 27 | 28 | def update_winner_choice |
| 28 | 29 | choice.reload # make sure we're using updated counter values |
| ... | ... | @@ -33,4 +34,22 @@ class Vote < ActiveRecord::Base |
| 33 | 34 | loser_choice.reload |
| 34 | 35 | loser_choice.compute_score! |
| 35 | 36 | end |
| 37 | + | |
| 38 | + # this is necessary to handle counter cache, at least until the following patch is accepted: | |
| 39 | + # https://rails.lighthouseapp.com/projects/8994/tickets/3521-patch-add-conditional-counter-cache | |
| 40 | + def update_counter_caches_based_on_flags | |
| 41 | + if valid_record_changed? | |
| 42 | + if valid_record | |
| 43 | + Question.increment_counter(:votes_count, self.question_id) | |
| 44 | + Prompt.increment_counter(:votes_count, self.prompt_id) | |
| 45 | + Choice.increment_counter(:wins, self.choice_id) | |
| 46 | + Choice.increment_counter(:losses, self.loser_choice_id) | |
| 47 | + else | |
| 48 | + Question.decrement_counter(:votes_count, self.question_id) | |
| 49 | + Prompt.decrement_counter(:votes_count, self.prompt_id) | |
| 50 | + Choice.decrement_counter(:wins, self.choice_id) | |
| 51 | + Choice.decrement_counter(:losses, self.loser_choice_id) | |
| 52 | + end | |
| 53 | + end | |
| 54 | + end | |
| 36 | 55 | end | ... | ... |
spec/models/visitor_spec.rb
| ... | ... | @@ -126,6 +126,7 @@ describe Visitor do |
| 126 | 126 | |
| 127 | 127 | valid_skip = @visitor.skip!(allparams) |
| 128 | 128 | @visitor.skips.count.should == 1 |
| 129 | + @visitor.skips.size.should == 1 | |
| 129 | 130 | @appearance.reload.answerable.should == valid_skip |
| 130 | 131 | |
| 131 | 132 | # we need to reset because vote_for deletes keys from the params |
| ... | ... | @@ -137,6 +138,7 @@ describe Visitor do |
| 137 | 138 | invalid_skip.validity_information.should == "Appearance #{@appearance.id} already answered" |
| 138 | 139 | @appearance.reload.answerable.should == valid_skip |
| 139 | 140 | @visitor.reload.skips.count.should == 1 |
| 141 | + @visitor.reload.skips.size.should == 1 | |
| 140 | 142 | end |
| 141 | 143 | |
| 142 | 144 | it "should mark a vote as invalid if submitted with an already answered appearance" do |
| ... | ... | @@ -146,6 +148,7 @@ describe Visitor do |
| 146 | 148 | |
| 147 | 149 | valid_vote = @visitor.vote_for!(allparams) |
| 148 | 150 | @visitor.votes.count.should == 1 |
| 151 | + @question.reload.votes.size.should == 1 | |
| 149 | 152 | @appearance.reload.answerable.should == valid_vote |
| 150 | 153 | |
| 151 | 154 | # we need to reset because vote_for deletes keys from the params |
| ... | ... | @@ -157,6 +160,7 @@ describe Visitor do |
| 157 | 160 | invalid_vote.validity_information.should == "Appearance #{@appearance.id} already answered" |
| 158 | 161 | @appearance.reload.answerable.should == valid_vote |
| 159 | 162 | @visitor.reload.votes.count.should == 1 |
| 163 | + @question.reload.votes.size.should == 1 #test counter cache works as well | |
| 160 | 164 | end |
| 161 | 165 | |
| 162 | 166 | it "should accurately update score counts after vote" do | ... | ... |
spec/models/vote_spec.rb
| ... | ... | @@ -11,6 +11,10 @@ describe Vote do |
| 11 | 11 | before(:each) do |
| 12 | 12 | @question = Factory.create(:aoi_question) |
| 13 | 13 | @prompt = @question.prompts.first |
| 14 | + @required_params = {:question => @question, :prompt => @prompt, | |
| 15 | + :choice => @prompt.left_choice, | |
| 16 | + :voter=> @question.site.default_visitor, | |
| 17 | + :loser_choice => @prompt.right_choice} | |
| 14 | 18 | end |
| 15 | 19 | |
| 16 | 20 | it "should create a new instance with factory girl" do |
| ... | ... | @@ -95,16 +99,89 @@ describe Vote do |
| 95 | 99 | end |
| 96 | 100 | |
| 97 | 101 | it "should allow default valid_record behavior to be overriden by default" do |
| 98 | - required_params = {:question => @question, :prompt => @prompt, | |
| 99 | - :choice => @prompt.left_choice, | |
| 100 | - :voter=> @question.site.default_visitor, | |
| 101 | - :loser_choice => @prompt.right_choice} | |
| 102 | - | |
| 103 | - vote = Vote.create!(required_params) | |
| 102 | + vote = Vote.create!(@required_params) | |
| 104 | 103 | vote.valid_record.should be_true |
| 105 | 104 | |
| 106 | - | |
| 107 | - vote = Vote.create!(required_params.merge!(:valid_record => false)) | |
| 105 | + vote = Vote.create!(@required_params.merge!(:valid_record => false)) | |
| 108 | 106 | vote.valid_record.should be_false |
| 109 | 107 | end |
| 108 | + | |
| 109 | + it "should update counter cache on question when vote is flagged as invalid" do | |
| 110 | + vote = Factory.create(:vote, :question => @question) | |
| 111 | + @question.reload | |
| 112 | + @question.votes.size.should == 1 | |
| 113 | + @question.votes_count.should == 1 | |
| 114 | + | |
| 115 | + vote.valid_record = false; | |
| 116 | + vote.save | |
| 117 | + | |
| 118 | + @question.reload | |
| 119 | + @question.votes.size.should == 0 | |
| 120 | + @question.votes_count.should == 0 | |
| 121 | + | |
| 122 | + the_vote = Factory.create(:vote, :question => @question) | |
| 123 | + the_vote.validity_information = "blah blah blah" | |
| 124 | + the_vote.save | |
| 125 | + | |
| 126 | + @question.reload.votes.size.should == 1 | |
| 127 | + | |
| 128 | + end | |
| 129 | + it "should update counter cache on question when vote is created with invalid flag" do | |
| 130 | + vote = Vote.create!(@required_params) | |
| 131 | + @question.reload.votes.size.should == 1 | |
| 132 | + | |
| 133 | + vote = Vote.create!(@required_params.merge!(:valid_record => false)) | |
| 134 | + @question.reload.votes.size.should == 1 | |
| 135 | + end | |
| 136 | + | |
| 137 | + it "should update counter cache on choice after changing valid status" do | |
| 138 | + vote = Factory.create(:vote, :question => @question, :prompt => @prompt, | |
| 139 | + :choice => @prompt.left_choice) | |
| 140 | + | |
| 141 | + @prompt.left_choice.reload | |
| 142 | + @prompt.left_choice.votes.size.should == 1 | |
| 143 | + @prompt.left_choice.wins.should == 1 | |
| 144 | + | |
| 145 | + vote.valid_record = false | |
| 146 | + vote.save | |
| 147 | + @prompt.left_choice.reload | |
| 148 | + @prompt.left_choice.votes.size.should == 0 | |
| 149 | + @prompt.left_choice.wins.should == 0 | |
| 150 | + | |
| 151 | + end | |
| 152 | + it "should update counter cache on prompt after changing valid status" do | |
| 153 | + vote = Factory.create(:vote, :question => @question, :prompt => @prompt) | |
| 154 | + | |
| 155 | + @prompt.reload | |
| 156 | + @prompt.votes.size.should == 1 | |
| 157 | + @prompt.votes_count.should == 1 | |
| 158 | + | |
| 159 | + vote.valid_record = false | |
| 160 | + vote.save | |
| 161 | + @prompt.reload | |
| 162 | + @prompt.votes.size.should == 0 | |
| 163 | + @prompt.votes_count.should == 0 | |
| 164 | + | |
| 165 | + end | |
| 166 | + | |
| 167 | + it "should update counter cache on loser_choice after invalid is changed" do | |
| 168 | + vote = Factory.create(:vote, :question => @question, :prompt => @prompt, | |
| 169 | + :choice => @prompt.left_choice, | |
| 170 | + :loser_choice => @prompt.right_choice) | |
| 171 | + | |
| 172 | + @prompt.right_choice.reload | |
| 173 | + @prompt.right_choice.votes.size.should == 0 | |
| 174 | + @prompt.right_choice.wins.should == 0 | |
| 175 | + @prompt.right_choice.losses.should == 1 | |
| 176 | + | |
| 177 | + vote.valid_record = false | |
| 178 | + vote.save | |
| 179 | + | |
| 180 | + @prompt.right_choice.reload | |
| 181 | + @prompt.right_choice.votes.size.should == 0 | |
| 182 | + @prompt.right_choice.wins.should == 0 | |
| 183 | + @prompt.right_choice.losses.should == 0 | |
| 184 | + | |
| 185 | + end | |
| 186 | + | |
| 110 | 187 | end | ... | ... |