package main import ( "encoding/json" "io/ioutil" "time" ) const ( fileName = "/omp.cache" ) type cacheObject struct { Value string `json:"value"` Timestamp int64 `json:"timestamp"` TTL int `json:"ttl"` } type fileCache struct { cache *concurrentMap cachePath string } func (fc *fileCache) init(cachePath string) { fc.cache = newConcurrentMap() fc.cachePath = cachePath content, err := ioutil.ReadFile(fc.cachePath + fileName) if err != nil { return } var list map[string]*cacheObject if err := json.Unmarshal(content, &list); err != nil { return } for key, co := range list { fc.cache.set(key, co) } } func (fc *fileCache) close() { cache := fc.cache.list() if len(cache) == 0 { return } if dump, err := json.MarshalIndent(cache, "", " "); err == nil { _ = ioutil.WriteFile(fc.cachePath+fileName, dump, 0644) } } // returns the value for the given key as long as // the TTL (minutes) is not expired func (fc *fileCache) get(key string) (string, bool) { val, found := fc.cache.get(key) if !found { return "", false } co, ok := val.(*cacheObject) if !ok { return "", false } expired := time.Now().Unix() >= (co.Timestamp + int64(co.TTL)*60) if expired { fc.cache.remove(key) return "", false } return co.Value, true } // sets the value for the given key with a TTL (minutes) func (fc *fileCache) set(key, value string, ttl int) { fc.cache.set(key, &cacheObject{ Value: value, Timestamp: time.Now().Unix(), TTL: ttl, }) }