tags: fix post counts for nonexistent tags.
Fix a bug where the post count regenerator didn't fix counts for tags that had a non-zero count but weren't present on any posts.
This commit is contained in:
@@ -106,23 +106,43 @@ class Tag < ApplicationRecord
|
|||||||
Tag.where(name: tag_names).update_all("post_count = post_count - 1")
|
Tag.where(name: tag_names).update_all("post_count = post_count - 1")
|
||||||
end
|
end
|
||||||
|
|
||||||
def regenerate_post_counts!
|
# fix tags where the post count is non-zero but the tag isn't present on any posts.
|
||||||
sql = <<~SQL
|
def regenerate_nonexistent_post_counts!
|
||||||
|
Tag.find_by_sql(<<~SQL)
|
||||||
UPDATE tags
|
UPDATE tags
|
||||||
SET post_count = COALESCE(true_count, 0)
|
SET post_count = 0
|
||||||
|
WHERE
|
||||||
|
post_count != 0
|
||||||
|
AND name NOT IN (
|
||||||
|
SELECT DISTINCT tag
|
||||||
|
FROM posts, unnest(string_to_array(tag_string, ' ')) AS tag
|
||||||
|
GROUP BY tag
|
||||||
|
)
|
||||||
|
RETURNING tags.*
|
||||||
|
SQL
|
||||||
|
end
|
||||||
|
|
||||||
|
# fix tags where the stored post count doesn't match the true post count.
|
||||||
|
def regenerate_incorrect_post_counts!
|
||||||
|
Tag.find_by_sql(<<~SQL)
|
||||||
|
UPDATE tags
|
||||||
|
SET post_count = true_count
|
||||||
FROM (
|
FROM (
|
||||||
SELECT tag, COUNT(*) AS true_count
|
SELECT tag, COUNT(*) AS true_count
|
||||||
FROM posts, unnest(string_to_array(tag_string, ' ')) AS tag
|
FROM posts, unnest(string_to_array(tag_string, ' ')) AS tag
|
||||||
GROUP BY tag
|
GROUP BY tag
|
||||||
) true_counts
|
) true_counts
|
||||||
WHERE
|
WHERE
|
||||||
(tags.name = tag AND tags.post_count != true_count)
|
tags.name = tag AND tags.post_count != true_count
|
||||||
OR tags.post_count < 0
|
|
||||||
RETURNING tags.*
|
RETURNING tags.*
|
||||||
SQL
|
SQL
|
||||||
|
end
|
||||||
|
|
||||||
updated_tags = Tag.find_by_sql(sql)
|
def regenerate_post_counts!
|
||||||
updated_tags
|
tags = []
|
||||||
|
tags += regenerate_incorrect_post_counts!
|
||||||
|
tags += regenerate_nonexistent_post_counts!
|
||||||
|
tags
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -278,11 +278,14 @@ class TagTest < ActiveSupport::TestCase
|
|||||||
should "be fixed" do
|
should "be fixed" do
|
||||||
tag1 = FactoryBot.create(:tag, name: "touhou", post_count: -10)
|
tag1 = FactoryBot.create(:tag, name: "touhou", post_count: -10)
|
||||||
tag2 = FactoryBot.create(:tag, name: "bkub", post_count: 10)
|
tag2 = FactoryBot.create(:tag, name: "bkub", post_count: 10)
|
||||||
|
tag3 = FactoryBot.create(:tag, name: "chen", post_count: 10)
|
||||||
post = FactoryBot.create(:post, tag_string: "touhou bkub")
|
post = FactoryBot.create(:post, tag_string: "touhou bkub")
|
||||||
|
|
||||||
Tag.regenerate_post_counts!
|
tags = Tag.regenerate_post_counts!
|
||||||
|
assert_equal(3, tags.size)
|
||||||
assert_equal(1, tag1.reload.post_count)
|
assert_equal(1, tag1.reload.post_count)
|
||||||
assert_equal(1, tag2.reload.post_count)
|
assert_equal(1, tag2.reload.post_count)
|
||||||
|
assert_equal(0, tag3.reload.post_count)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|||||||
Reference in New Issue
Block a user