From b3a9cd6c06da47db704b215119a73028c11d78d9 Mon Sep 17 00:00:00 2001 From: evazion Date: Mon, 20 Nov 2017 20:19:29 -0600 Subject: [PATCH] Fix `Post.fast_count("pool:1537") == 0` (fixup 134958d1). Fixup for a bug in 134958d1. `Post.fast_count("pool:1537")` still returned zero because `Tag.is_simple_tag?` incorrectly parsed "pool:1537" as a simple tag, so Post.fast_count still looked for it in the tags table and found the empty "pool:1537" tag. --- app/models/tag.rb | 23 +++++++++++++++++++++-- test/unit/post_test.rb | 7 +++++++ test/unit/tag_test.rb | 22 ++++++++++++++++++++++ 3 files changed, 50 insertions(+), 2 deletions(-) diff --git a/app/models/tag.rb b/app/models/tag.rb index 94fcbb2f1..5f3a3fdc2 100644 --- a/app/models/tag.rb +++ b/app/models/tag.rb @@ -417,8 +417,27 @@ class Tag < ApplicationRecord # true if query is a single "simple" tag (not a metatag, negated tag, or wildcard tag). def is_simple_tag?(query) - q = parse_query(query) - (scan_query(query).size == 1) && (q[:tags][:related].size == 1) + is_single_tag?(query) && !is_metatag?(query) && !is_negated_tag?(query) && !is_optional_tag?(query) && !is_wildcard_tag?(query) + end + + def is_single_tag?(query) + scan_query(query).size == 1 + end + + def is_metatag?(tag) + !!(tag =~ /\A(#{METATAGS}):(.+)\Z/i) + end + + def is_negated_tag?(tag) + tag.starts_with?("-") + end + + def is_optional_tag?(tag) + tag.starts_with?("~") + end + + def is_wildcard_tag?(tag) + tag.include?("*") end def parse_query(query, options = {}) diff --git a/test/unit/post_test.rb b/test/unit/post_test.rb index 336fed3b7..5bbd09f71 100644 --- a/test/unit/post_test.rb +++ b/test/unit/post_test.rb @@ -2405,6 +2405,13 @@ class PostTest < ActiveSupport::TestCase assert_equal(100, Post.fast_count("score:42")) end + + should "return the correct cached count for a pool: search" do + FactoryGirl.build(:tag, name: "pool:1234", post_count: -100).save(validate: false) + Post.set_count_in_cache("pool:1234", 100) + + assert_equal(100, Post.fast_count("pool:1234")) + end end context "a multi-tag search" do diff --git a/test/unit/tag_test.rb b/test/unit/tag_test.rb index bcc47ff3f..21e798b2a 100644 --- a/test/unit/tag_test.rb +++ b/test/unit/tag_test.rb @@ -158,6 +158,28 @@ class TagTest < ActiveSupport::TestCase Tag.expects(:normalize_tags_in_query).returns(nil) assert_equal(["acb"], Tag.parse_query("a*b")[:tags][:include]) end + + should "parse single tags correctly" do + assert_equal(true, Tag.is_single_tag?("foo")) + assert_equal(true, Tag.is_single_tag?("-foo")) + assert_equal(true, Tag.is_single_tag?("~foo")) + assert_equal(true, Tag.is_single_tag?("foo*")) + assert_equal(true, Tag.is_single_tag?("fav:1234")) + assert_equal(true, Tag.is_single_tag?("pool:1234")) + assert_equal(true, Tag.is_single_tag?('source:"foo bar baz"')) + assert_equal(false, Tag.is_single_tag?("foo bar")) + end + + should "parse simple tags correctly" do + assert_equal(true, Tag.is_simple_tag?("foo")) + assert_equal(false, Tag.is_simple_tag?("-foo")) + assert_equal(false, Tag.is_simple_tag?("~foo")) + assert_equal(false, Tag.is_simple_tag?("foo*")) + assert_equal(false, Tag.is_simple_tag?("fav:1234")) + assert_equal(false, Tag.is_simple_tag?("pool:1234")) + assert_equal(false, Tag.is_simple_tag?('source:"foo bar baz"')) + assert_equal(false, Tag.is_simple_tag?("foo bar")) + end end context "A tag" do