234 lines
8.1 KiB
Ruby
234 lines
8.1 KiB
Ruby
# typed: false
|
|
require "rails_helper"
|
|
|
|
RSpec.describe "Domain::User counter caches", type: :model do
|
|
let(:user) { create(:domain_user_fa_user) }
|
|
let(:post) { create(:domain_post_fa_post) }
|
|
|
|
describe "user_post_creations_count" do
|
|
it "increments when a post creation is added" do
|
|
expect {
|
|
Domain::UserPostCreation.create!(user: user, post: post)
|
|
}.to change { user.reload.user_post_creations.size }.from(0).to(1)
|
|
end
|
|
|
|
it "decrements when a post creation is removed" do
|
|
creation = Domain::UserPostCreation.create!(user: user, post: post)
|
|
expect { creation.destroy }.to change {
|
|
user.reload.user_post_creations.size
|
|
}.from(1).to(0)
|
|
end
|
|
|
|
it "provides direct access to the counts" do
|
|
posts = create_list(:domain_post_fa_post, 3)
|
|
posts.each { |p| Domain::UserPostCreation.create!(user: user, post: p) }
|
|
|
|
# Counter in database should be updated automatically
|
|
expect(user.reload.user_post_creations.size).to eq(3)
|
|
|
|
# Calling the method should use the cached value
|
|
expect(user.user_post_creations.size).to eq(3)
|
|
end
|
|
|
|
it "resets to the correct count" do
|
|
posts = create_list(:domain_post_fa_post, 3)
|
|
posts.each { |p| Domain::UserPostCreation.create!(user: user, post: p) }
|
|
|
|
# Manually set to wrong value
|
|
user.update_column(:user_post_creations_count, 0)
|
|
expect(user.read_attribute(:user_post_creations_count)).to eq(0)
|
|
|
|
# Reset counter
|
|
Domain::User.reset_counters(user.id, :user_post_creations)
|
|
expect(user.reload.user_post_creations_count).to eq(3)
|
|
end
|
|
end
|
|
|
|
describe "user_post_favs_count" do
|
|
it "increments when a post fav is added" do
|
|
expect { Domain::UserPostFav.create!(user: user, post: post) }.to change {
|
|
user.reload.user_post_favs.size
|
|
}.from(0).to(1)
|
|
end
|
|
|
|
it "decrements when a post fav is removed" do
|
|
fav = Domain::UserPostFav.create!(user: user, post: post)
|
|
expect { fav.destroy }.to change { user.reload.user_post_favs.size }.from(
|
|
1,
|
|
).to(0)
|
|
end
|
|
|
|
it "provides direct access to the counts" do
|
|
posts = create_list(:domain_post_fa_post, 3)
|
|
posts.each { |p| Domain::UserPostFav.create!(user: user, post: p) }
|
|
|
|
# Counter in database should be updated automatically
|
|
expect(user.reload.user_post_favs.size).to eq(3)
|
|
|
|
# Calling the method should use the cached value
|
|
expect(user.user_post_favs.size).to eq(3)
|
|
end
|
|
end
|
|
|
|
describe "user_user_follows_from_count" do
|
|
let(:other_user) { create(:domain_user_fa_user) }
|
|
|
|
it "increments when a follow is added" do
|
|
expect {
|
|
Domain::UserUserFollow.create!(from: user, to: other_user)
|
|
}.to change { user.reload.user_user_follows_from.size }.from(0).to(1)
|
|
end
|
|
|
|
it "decrements when a follow is removed" do
|
|
follow = Domain::UserUserFollow.create!(from: user, to: other_user)
|
|
expect { follow.destroy }.to change {
|
|
user.reload.user_user_follows_from.size
|
|
}.from(1).to(0)
|
|
end
|
|
|
|
it "provides direct access to the counts" do
|
|
users = create_list(:domain_user_fa_user, 3)
|
|
users.each { |u| Domain::UserUserFollow.create!(from: user, to: u) }
|
|
|
|
# Counter in database should be updated automatically
|
|
expect(user.reload.user_user_follows_from.size).to eq(3)
|
|
|
|
# Calling the method should use the cached value
|
|
expect(user.user_user_follows_from.size).to eq(3)
|
|
end
|
|
end
|
|
|
|
describe "user_user_follows_to_count" do
|
|
let(:other_user) { create(:domain_user_fa_user) }
|
|
|
|
it "increments when a follow is added" do
|
|
expect {
|
|
Domain::UserUserFollow.create!(from: other_user, to: user)
|
|
}.to change { user.reload.user_user_follows_to.size }.from(0).to(1)
|
|
end
|
|
|
|
it "decrements when a follow is removed" do
|
|
follow = Domain::UserUserFollow.create!(from: other_user, to: user)
|
|
expect { follow.destroy }.to change {
|
|
user.reload.user_user_follows_to.size
|
|
}.from(1).to(0)
|
|
end
|
|
|
|
it "provides direct access to the counts" do
|
|
users = create_list(:domain_user_fa_user, 3)
|
|
users.each { |u| Domain::UserUserFollow.create!(from: u, to: user) }
|
|
|
|
# Counter in database should be updated automatically
|
|
expect(user.reload.user_user_follows_to.size).to eq(3)
|
|
|
|
# Calling the method should use the cached value
|
|
expect(user.user_user_follows_to.size).to eq(3)
|
|
end
|
|
end
|
|
|
|
describe "counter cache consistency" do
|
|
it "maintains separate counts for creations and favs" do
|
|
# Create 2 posts and fav 3 posts
|
|
created_posts = create_list(:domain_post_fa_post, 2)
|
|
faved_posts = create_list(:domain_post_fa_post, 3)
|
|
|
|
created_posts.each do |p|
|
|
Domain::UserPostCreation.create!(user: user, post: p)
|
|
end
|
|
faved_posts.each { |p| Domain::UserPostFav.create!(user: user, post: p) }
|
|
|
|
user.reload
|
|
expect(user.user_post_creations_count).to eq(2)
|
|
expect(user.user_post_favs_count).to eq(3)
|
|
end
|
|
end
|
|
|
|
it "falls back to sql COUNT when the counter cache is not set" do
|
|
user = create(:domain_user_fa_user)
|
|
post = create(:domain_post_fa_post, creator: user)
|
|
|
|
# creation of a post should update the counter cache
|
|
user.reload
|
|
expect(user.user_post_creations_count).to eq(1)
|
|
expect(user.user_post_favs_count).to be_nil
|
|
|
|
# insert a fav without updating the counter cache, so the counter cache is nil
|
|
Domain::UserPostFav::FaUserPostFav.insert_all!(
|
|
[{ user_id: user.id, post_id: post.id }],
|
|
)
|
|
|
|
user.reload
|
|
expect(user.user_post_favs_count).to be_nil
|
|
expect(user.user_post_favs.size).to eq(1)
|
|
expect(user.user_post_favs.count).to eq(1)
|
|
|
|
# recompute the value of the counter cache
|
|
Domain::User.reset_counters(user.id, :user_post_favs)
|
|
|
|
user.reload
|
|
expect(user.user_post_favs_count).to eq(1)
|
|
expect(user.user_post_favs.size).to eq(1)
|
|
expect(user.user_post_favs.count).to eq(1)
|
|
end
|
|
|
|
it "sets the right value when there was already an existing model" do
|
|
user = create(:domain_user_fa_user)
|
|
|
|
# create a post as if it was there prior to the counter cache existing
|
|
create(:domain_post_fa_post, creator: user)
|
|
user.update_column(:user_post_creations_count, nil)
|
|
|
|
user.reload
|
|
user = Domain::User.find(user.id)
|
|
expect(user.user_post_creations_count).to eq(nil)
|
|
expect(user.user_post_creations.length).to eq(1)
|
|
expect(user.user_post_creations.count).to eq(1)
|
|
|
|
# create a second post
|
|
create(:domain_post_fa_post, creator: user)
|
|
user.reload
|
|
expect(user.user_post_creations_count).to eq(2)
|
|
expect(user.user_post_creations.size).to eq(2)
|
|
expect(user.user_post_creations.length).to eq(2)
|
|
expect(user.user_post_creations.count).to eq(2)
|
|
|
|
# and a third to test incrementing
|
|
create(:domain_post_fa_post, creator: user)
|
|
user.reload
|
|
expect(user.user_post_creations.count).to eq(3)
|
|
expect(user.user_post_creations_count).to eq(3)
|
|
expect(user.user_post_creations.length).to eq(3)
|
|
expect(user.user_post_creations.size).to eq(3)
|
|
end
|
|
|
|
it "works with user_user_follows" do
|
|
user = create(:domain_user_fa_user)
|
|
other_user_1 = create(:domain_user_fa_user)
|
|
other_user_2 = create(:domain_user_fa_user)
|
|
|
|
[user, other_user_1, other_user_2].each do |u|
|
|
expect(u.user_user_follows_from_count).to be_nil
|
|
expect(u.user_user_follows_from.size).to eq(0)
|
|
expect(u.user_user_follows_to_count).to be_nil
|
|
expect(u.user_user_follows_to.size).to eq(0)
|
|
end
|
|
|
|
Domain::UserUserFollow.create!(from: user, to: other_user_1)
|
|
user.reload
|
|
expect(user.user_user_follows_from_count).to eq(1)
|
|
expect(user.user_user_follows_from.size).to eq(1)
|
|
expect(other_user_1.user_user_follows_to_count).to eq(1)
|
|
expect(other_user_1.user_user_follows_to.size).to eq(1)
|
|
|
|
Domain::UserUserFollow.create!(from: user, to: other_user_2)
|
|
user.reload
|
|
expect(user.user_user_follows_from_count).to eq(2)
|
|
expect(user.user_user_follows_from.size).to eq(2)
|
|
|
|
Domain::UserUserFollow.create!(from: other_user_1, to: user)
|
|
user.reload
|
|
expect(user.user_user_follows_to_count).to eq(1)
|
|
expect(user.user_user_follows_to.size).to eq(1)
|
|
end
|
|
end
|