github.com/pingcap/badger@v1.5.1-0.20230103063557-828f39b09b6d/cache/policy_test.go (about) 1 package cache 2 3 import ( 4 "testing" 5 "time" 6 ) 7 8 func TestPolicy(t *testing.T) { 9 defer func() { 10 if r := recover(); r != nil { 11 t.Fatal("newPolicy failed") 12 } 13 }() 14 newPolicy(100, 10) 15 } 16 17 func TestPolicyMetrics(t *testing.T) { 18 p := newPolicy(100, 10) 19 p.CollectMetrics(newMetrics()) 20 if p.metrics == nil || p.evict.metrics == nil { 21 t.Fatal("policy metrics initialization error") 22 } 23 } 24 25 func TestPolicyProcessItems(t *testing.T) { 26 p := newPolicy(100, 10) 27 p.itemsCh <- []uint64{1, 2, 2} 28 time.Sleep(wait) 29 p.Lock() 30 if p.admit.Estimate(2) != 2 || p.admit.Estimate(1) != 1 { 31 p.Unlock() 32 t.Fatal("policy processItems not pushing to tinylfu counters") 33 } 34 p.Unlock() 35 p.stop <- struct{}{} 36 p.itemsCh <- []uint64{3, 3, 3} 37 time.Sleep(wait) 38 p.Lock() 39 if p.admit.Estimate(3) != 0 { 40 p.Unlock() 41 t.Fatal("policy processItems not stopping") 42 } 43 p.Unlock() 44 } 45 46 func TestPolicyPush(t *testing.T) { 47 p := newPolicy(100, 10) 48 if !p.Push([]uint64{}) { 49 t.Fatal("push empty slice should be good") 50 } 51 keepCount := 0 52 for i := 0; i < 10; i++ { 53 if p.Push([]uint64{1, 2, 3, 4, 5}) { 54 keepCount++ 55 } 56 } 57 if keepCount == 0 { 58 t.Fatal("push dropped everything") 59 } 60 } 61 62 func TestPolicyAdd(t *testing.T) { 63 p := newPolicy(1000, 100) 64 if victims, added := p.Add(1, 101); victims != nil || added { 65 t.Fatal("can't add an item bigger than entire cache") 66 } 67 p.Lock() 68 p.evict.add(1, 1) 69 p.admit.Increment(1) 70 p.admit.Increment(2) 71 p.admit.Increment(3) 72 p.Unlock() 73 if victims, added := p.Add(1, 1); victims != nil || !added { 74 t.Fatal("item should already exist") 75 } 76 if victims, added := p.Add(2, 20); victims != nil || !added { 77 t.Fatal("item should be added with no eviction") 78 } 79 if victims, added := p.Add(3, 90); victims == nil || !added { 80 t.Fatal("item should be added with eviction") 81 } 82 if victims, added := p.Add(4, 20); victims == nil || added { 83 t.Fatal("item should not be added") 84 } 85 } 86 87 func TestPolicyHas(t *testing.T) { 88 p := newPolicy(100, 10) 89 p.Add(1, 1) 90 if !p.Has(1) { 91 t.Fatal("policy should have key") 92 } 93 if p.Has(2) { 94 t.Fatal("policy shouldn't have key") 95 } 96 } 97 98 func TestPolicyDel(t *testing.T) { 99 p := newPolicy(100, 10) 100 p.Add(1, 1) 101 p.Del(1) 102 p.Del(2) 103 if p.Has(1) { 104 t.Fatal("del didn't delete") 105 } 106 if p.Has(2) { 107 t.Fatal("policy shouldn't have key") 108 } 109 } 110 111 func TestPolicyCap(t *testing.T) { 112 p := newPolicy(100, 10) 113 p.Add(1, 1) 114 if p.Cap() != 9 { 115 t.Fatal("cap returned wrong value") 116 } 117 } 118 119 func TestPolicyUpdate(t *testing.T) { 120 p := newPolicy(100, 10) 121 p.Add(1, 1) 122 p.Update(1, 2) 123 p.Lock() 124 if p.evict.keyCosts[1] != 2 { 125 p.Unlock() 126 t.Fatal("update failed") 127 } 128 p.Unlock() 129 } 130 131 func TestPolicyCost(t *testing.T) { 132 p := newPolicy(100, 10) 133 p.Add(1, 2) 134 if p.Cost(1) != 2 { 135 t.Fatal("cost for existing key returned wrong value") 136 } 137 if p.Cost(2) != -1 { 138 t.Fatal("cost for missing key returned wrong value") 139 } 140 } 141 142 func TestPolicyClear(t *testing.T) { 143 p := newPolicy(100, 10) 144 p.Add(1, 1) 145 p.Add(2, 2) 146 p.Add(3, 3) 147 p.Clear() 148 if p.Cap() != 10 || p.Has(1) || p.Has(2) || p.Has(3) { 149 t.Fatal("clear didn't clear properly") 150 } 151 } 152 153 func TestPolicyClose(t *testing.T) { 154 defer func() { 155 if r := recover(); r == nil { 156 t.Fatal("close didn't close channels") 157 } 158 }() 159 p := newPolicy(100, 10) 160 p.Add(1, 1) 161 p.Close() 162 p.itemsCh <- []uint64{1} 163 } 164 165 func TestSampledLFUAdd(t *testing.T) { 166 e := newSampledLFU(4) 167 e.add(1, 1) 168 e.add(2, 2) 169 e.add(3, 1) 170 if e.used != 4 { 171 t.Fatal("used not being incremented") 172 } 173 if e.keyCosts[2] != 2 { 174 t.Fatal("keyCosts not being updated") 175 } 176 } 177 178 func TestSampledLFUDel(t *testing.T) { 179 e := newSampledLFU(4) 180 e.add(1, 1) 181 e.add(2, 2) 182 e.del(2) 183 if e.used != 1 { 184 t.Fatal("del not updating used field") 185 } 186 if _, ok := e.keyCosts[2]; ok { 187 t.Fatal("del not deleting value from keyCosts") 188 } 189 e.del(4) 190 } 191 192 func TestSampledLFUUpdate(t *testing.T) { 193 e := newSampledLFU(4) 194 e.add(1, 1) 195 if !e.updateIfHas(1, 2) { 196 t.Fatal("update should be possible") 197 } 198 if e.used != 2 { 199 t.Fatal("update not changing used field") 200 } 201 if e.updateIfHas(2, 2) { 202 t.Fatal("update shouldn't be possible") 203 } 204 } 205 206 func TestSampledLFUClear(t *testing.T) { 207 e := newSampledLFU(4) 208 e.add(1, 1) 209 e.add(2, 2) 210 e.add(3, 1) 211 e.clear() 212 if len(e.keyCosts) != 0 || e.used != 0 { 213 t.Fatal("clear not deleting keyCosts or zeroing used field") 214 } 215 } 216 217 func TestSampledLFURoom(t *testing.T) { 218 e := newSampledLFU(16) 219 e.add(1, 1) 220 e.add(2, 2) 221 e.add(3, 3) 222 if e.roomLeft(4) != 6 { 223 t.Fatal("roomLeft returning wrong value") 224 } 225 } 226 227 func TestSampledLFUSample(t *testing.T) { 228 e := newSampledLFU(16) 229 e.add(4, 4) 230 e.add(5, 5) 231 sample := e.fillSample([]*policyPair{ 232 {1, 1}, 233 {2, 2}, 234 {3, 3}, 235 }) 236 k := sample[len(sample)-1].key 237 if len(sample) != 5 || k == 1 || k == 2 || k == 3 { 238 t.Fatal("fillSample not filling properly") 239 } 240 if len(sample) != len(e.fillSample(sample)) { 241 t.Fatal("fillSample mutating full sample") 242 } 243 e.del(5) 244 if sample = e.fillSample(sample[:len(sample)-2]); len(sample) != 4 { 245 t.Fatal("fillSample not returning sample properly") 246 } 247 } 248 249 func TestTinyLFUIncrement(t *testing.T) { 250 a := newTinyLFU(4) 251 a.Increment(1) 252 a.Increment(1) 253 a.Increment(1) 254 if !a.door.Has(1) { 255 t.Fatal("doorkeeper bit not set") 256 } 257 if a.freq.Estimate(1) != 2 { 258 t.Fatal("incorrect counter value") 259 } 260 a.Increment(1) 261 if a.door.Has(1) { 262 t.Fatal("doorkeeper bit set after reset") 263 } 264 if a.freq.Estimate(1) != 1 { 265 t.Fatal("counter value not halved after reset") 266 } 267 } 268 269 func TestTinyLFUEstimate(t *testing.T) { 270 a := newTinyLFU(8) 271 a.Increment(1) 272 a.Increment(1) 273 a.Increment(1) 274 if a.Estimate(1) != 3 { 275 t.Fatal("estimate value incorrect") 276 } 277 if a.Estimate(2) != 0 { 278 t.Fatal("estimate value should be 0") 279 } 280 } 281 282 func TestTinyLFUPush(t *testing.T) { 283 a := newTinyLFU(16) 284 a.Push([]uint64{1, 2, 2, 3, 3, 3}) 285 if a.Estimate(1) != 1 || a.Estimate(2) != 2 || a.Estimate(3) != 3 { 286 t.Fatal("push didn't increment counters properly") 287 } 288 if a.incrs != 6 { 289 t.Fatal("incrs not being incremented") 290 } 291 } 292 293 func TestTinyLFUClear(t *testing.T) { 294 a := newTinyLFU(16) 295 a.Push([]uint64{1, 3, 3, 3}) 296 a.clear() 297 if a.incrs != 0 || a.Estimate(3) != 0 { 298 t.Fatal("clear not clearing") 299 } 300 }