prepared_cache.go 1.6 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889
  1. package gocql
  2. import (
  3. "bytes"
  4. "github.com/gocql/gocql/internal/lru"
  5. "sync"
  6. )
  7. const defaultMaxPreparedStmts = 1000
  8. // preparedLRU is the prepared statement cache
  9. type preparedLRU struct {
  10. mu sync.Mutex
  11. lru *lru.Cache
  12. }
  13. // Max adjusts the maximum size of the cache and cleans up the oldest records if
  14. // the new max is lower than the previous value. Not concurrency safe.
  15. func (p *preparedLRU) max(max int) {
  16. p.mu.Lock()
  17. defer p.mu.Unlock()
  18. for p.lru.Len() > max {
  19. p.lru.RemoveOldest()
  20. }
  21. p.lru.MaxEntries = max
  22. }
  23. func (p *preparedLRU) clear() {
  24. p.mu.Lock()
  25. defer p.mu.Unlock()
  26. for p.lru.Len() > 0 {
  27. p.lru.RemoveOldest()
  28. }
  29. }
  30. func (p *preparedLRU) add(key string, val *inflightPrepare) {
  31. p.mu.Lock()
  32. defer p.mu.Unlock()
  33. p.lru.Add(key, val)
  34. }
  35. func (p *preparedLRU) remove(key string) bool {
  36. p.mu.Lock()
  37. defer p.mu.Unlock()
  38. return p.lru.Remove(key)
  39. }
  40. func (p *preparedLRU) execIfMissing(key string, fn func(lru *lru.Cache) *inflightPrepare) (*inflightPrepare, bool) {
  41. p.mu.Lock()
  42. defer p.mu.Unlock()
  43. val, ok := p.lru.Get(key)
  44. if ok {
  45. return val.(*inflightPrepare), true
  46. }
  47. return fn(p.lru), false
  48. }
  49. func (p *preparedLRU) keyFor(addr, keyspace, statement string) string {
  50. // TODO: we should just use a struct for the key in the map
  51. return addr + keyspace + statement
  52. }
  53. func (p *preparedLRU) evictPreparedID(key string, id []byte) {
  54. p.mu.Lock()
  55. defer p.mu.Unlock()
  56. val, ok := p.lru.Get(key)
  57. if !ok {
  58. return
  59. }
  60. ifp, ok := val.(*inflightPrepare)
  61. if !ok {
  62. return
  63. }
  64. select {
  65. case <-ifp.done:
  66. if bytes.Equal(id, ifp.preparedStatment.id) {
  67. p.lru.Remove(key)
  68. }
  69. default:
  70. }
  71. }