1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147
|
require "helper"
class TestCssCacheAccess < Nokogiri::TestCase
def setup
super
@css = "a1 > b2 > c3"
@parse_result = Nokogiri::CSS.parse(@css)
@to_xpath_result = @parse_result.map(&:to_xpath)
Nokogiri::CSS::Parser.clear_cache
Nokogiri::CSS::Parser.class_eval do
class << @cache
alias :old_bracket :[]
def access_count
@access_count ||= 0
end
def [](key)
@access_count ||= 0
@access_count += 1
old_bracket(key)
end
end
end
assert Nokogiri::CSS::Parser.cache_on?
end
def teardown
Nokogiri::CSS::Parser.clear_cache(true)
Nokogiri::CSS::Parser.set_cache true
super
end
[false, true].each do |cache_setting|
define_method "test_css_cache_#{cache_setting ? "true" : "false"}" do
Nokogiri::CSS::Parser.set_cache cache_setting
Nokogiri::CSS.xpath_for(@css)
Nokogiri::CSS.xpath_for(@css)
Nokogiri::CSS::Parser.new.xpath_for(@css)
Nokogiri::CSS::Parser.new.xpath_for(@css)
if cache_setting
assert_equal(1, Nokogiri::CSS::Parser.class_eval { @cache.count })
assert_equal(4, Nokogiri::CSS::Parser.class_eval { @cache.access_count })
else
assert_equal(0, Nokogiri::CSS::Parser.class_eval { @cache.count })
assert_equal(0, Nokogiri::CSS::Parser.class_eval { @cache.access_count })
end
end
end
end
class TestCssCache < Nokogiri::TestCase
def teardown
Nokogiri::CSS::Parser.set_cache true
super
end
def test_enabled_cache_is_used
Nokogiri::CSS::Parser.clear_cache
Nokogiri::CSS::Parser.set_cache true
css = ".foo .bar .baz"
cache = Nokogiri::CSS::Parser.instance_variable_get("@cache")
assert_nil cache[css]
Nokogiri::CSS.xpath_for(css)
assert cache[css]
cache[css] = "this is an injected value"
assert_equal "this is an injected value", Nokogiri::CSS.xpath_for(css)
end
def test_disabled_cache_is_not_used
Nokogiri::CSS::Parser.clear_cache
Nokogiri::CSS::Parser.set_cache false
css = ".foo .bar .baz"
cache = Nokogiri::CSS::Parser.instance_variable_get("@cache")
assert_nil cache[css]
Nokogiri::CSS.xpath_for(css)
assert_nil cache[css]
end
def test_without_cache_avoids_cache
Nokogiri::CSS::Parser.clear_cache
Nokogiri::CSS::Parser.set_cache true
css = ".foo .bar .baz"
cache = Nokogiri::CSS::Parser.instance_variable_get("@cache")
assert_nil cache[css]
Nokogiri::CSS::Parser.without_cache do
Nokogiri::CSS.xpath_for(css)
end
assert_nil cache[css]
end
def test_without_cache_resets_cache_value
Nokogiri::CSS::Parser.set_cache true
Nokogiri::CSS::Parser.without_cache do
assert !Nokogiri::CSS::Parser.cache_on?
end
assert Nokogiri::CSS::Parser.cache_on?
end
def test_without_cache_resets_cache_value_even_after_exception
Nokogiri::CSS::Parser.set_cache true
assert_raises(RuntimeError) do
Nokogiri::CSS::Parser.without_cache do
raise RuntimeError
end
end
assert Nokogiri::CSS::Parser.cache_on?
end
def test_race_condition
# https://github.com/sparklemotion/nokogiri/issues/1935
threads = []
Nokogiri::CSS::Parser.set_cache true
threads << Thread.new do
Nokogiri::CSS::Parser.without_cache do
sleep 0.02
end
end
threads << Thread.new do
sleep 0.01
Nokogiri::CSS::Parser.without_cache do
sleep 0.02
end
end
threads.each(&:join)
assert Nokogiri::CSS::Parser.cache_on?
end
end
|