memos/store/cache.go

83 lines
2.1 KiB
Go
Raw Normal View History

2022-08-07 08:09:43 +08:00
package store
import (
"bytes"
"encoding/binary"
"encoding/gob"
"fmt"
"github.com/VictoriaMetrics/fastcache"
)
var (
// 64 MiB.
2023-02-10 08:43:39 +08:00
cacheSize = 1024 * 1024 * 64
2022-08-07 08:09:43 +08:00
)
// CacheService implements a cache.
type CacheService struct {
cache *fastcache.Cache
}
2023-02-10 08:43:39 +08:00
// CacheNamespace is the type of a cache.
type CacheNamespace string
const (
// UserCache is the cache type of users.
UserCache CacheNamespace = "u"
// MemoCache is the cache type of memos.
MemoCache CacheNamespace = "m"
// ShortcutCache is the cache type of shortcuts.
ShortcutCache CacheNamespace = "s"
)
2022-08-07 08:09:43 +08:00
// NewCacheService creates a cache service.
func NewCacheService() *CacheService {
return &CacheService{
cache: fastcache.New(cacheSize),
}
}
// FindCache finds the value in cache.
2023-02-10 08:43:39 +08:00
func (s *CacheService) FindCache(namespace CacheNamespace, id int, entry interface{}) (bool, error) {
2022-08-07 08:09:43 +08:00
buf1 := []byte{0, 0, 0, 0, 0, 0, 0, 0}
binary.LittleEndian.PutUint64(buf1, uint64(id))
buf2, has := s.cache.HasGet(nil, append([]byte(namespace), buf1...))
if has {
dec := gob.NewDecoder(bytes.NewReader(buf2))
if err := dec.Decode(entry); err != nil {
return false, fmt.Errorf("failed to decode entry for cache namespace: %s, error: %w", namespace, err)
}
return true, nil
}
return false, nil
}
// UpsertCache upserts the value to cache.
2023-02-10 08:43:39 +08:00
func (s *CacheService) UpsertCache(namespace CacheNamespace, id int, entry interface{}) error {
2022-08-07 08:09:43 +08:00
buf1 := []byte{0, 0, 0, 0, 0, 0, 0, 0}
binary.LittleEndian.PutUint64(buf1, uint64(id))
var buf2 bytes.Buffer
enc := gob.NewEncoder(&buf2)
if err := enc.Encode(entry); err != nil {
return fmt.Errorf("failed to encode entry for cache namespace: %s, error: %w", namespace, err)
}
s.cache.Set(append([]byte(namespace), buf1...), buf2.Bytes())
return nil
}
// DeleteCache deletes the cache.
2023-02-10 08:43:39 +08:00
func (s *CacheService) DeleteCache(namespace CacheNamespace, id int) {
2022-08-07 08:09:43 +08:00
buf1 := []byte{0, 0, 0, 0, 0, 0, 0, 0}
binary.LittleEndian.PutUint64(buf1, uint64(id))
_, has := s.cache.HasGet(nil, append([]byte(namespace), buf1...))
if has {
s.cache.Del(append([]byte(namespace), buf1...))
}
}