package cache import ( . "code.hoteas.com/golang/hotime/common" "strings" "sync" "time" ) // CacheMemory 基于 sync.Map 的缓存实现 type CacheMemory struct { TimeOut int64 DbSet bool SessionSet bool *Error cache sync.Map // 替代传统的 Map } func (that *CacheMemory) GetError() *Error { return that.Error } func (that *CacheMemory) SetError(err *Error) { that.Error = err } func (c *CacheMemory) get(key string) (res *Obj) { res = &Obj{ Error: *c.Error, } value, ok := c.cache.Load(key) if !ok { return res // 缓存不存在 } data := value.(cacheData) // 检查是否过期 if data.time < time.Now().Unix() { c.cache.Delete(key) // 删除过期缓存 return res } res.Data = data.data return res } func (c *CacheMemory) set(key string, value interface{}, expireAt int64) { data := cacheData{ data: value, time: expireAt, } c.cache.Store(key, data) } func (c *CacheMemory) delete(key string) { if strings.Contains(key, "*") { // 通配符删除 prefix := strings.TrimSuffix(key, "*") c.cache.Range(func(k, v interface{}) bool { if strings.HasPrefix(k.(string), prefix) { c.cache.Delete(k) } return true }) } else { // 精确删除 c.cache.Delete(key) } } func (c *CacheMemory) refreshMap() { go func() { now := time.Now().Unix() c.cache.Range(func(key, value interface{}) bool { data := value.(cacheData) if data.time <= now { c.cache.Delete(key) // 删除过期缓存 } return true }) }() } func (c *CacheMemory) Cache(key string, data ...interface{}) *Obj { now := time.Now().Unix() // 随机触发刷新 if x := RandX(1, 100000); x > 99950 { c.refreshMap() } if len(data) == 0 { // 读操作 return c.get(key) } if len(data) == 1 && data[0] == nil { // 删除操作 c.delete(key) return nil } // 写操作 expireAt := now + c.TimeOut if len(data) == 2 { if customExpire, ok := data[1].(int64); ok { if customExpire > now { expireAt = customExpire } else { expireAt = now + customExpire } } } c.set(key, data[0], expireAt) return nil }