Caching based on requests
Usually caches on the web are made so that the cache is filled with requests coming in from the browser. Positive about this is that you cache the most used requests and not the ones which are not used. The downside is that in case of errors or timeouts, you really have to think what to do. And what about expiration and the size of the cache?Caching on the background
If you know what to fetch and you know the requests what to get before hand, you can easily schedule the cache fetching. Although I'm not using a popular cache like LRU here, it's certainly possible.A simple example
This is a simple example for a cache. You can get, add and remove items from the cache.package main import ( "github.com/streamrail/concurrent-map" ) var cache cmap.ConcurrentMap func init() { cache = cmap.New() } func AddItemToCache(key string, value string) { cache.Set(key, value) } func GetItemFromCache(key string) string { if cache.Has(key) { if tmp, ok := cache.Get(key); ok { return tmp.(string) } } return "" } func removeItem(key string) { cache.Remove(key) }
Let’s get weather information on the background.
func fetchWeather() *Weather { var w Weather resp, err := client.Get(weatherURL) if err != nil { fmt.Println(err) return nil } defer resp.Body.Close() buf, err := ioutil.ReadAll(resp.Body) if err != nil { fmt.Println(err) return nil } if err = json.Unmarshal(buf, &w); err != nil { fmt.Println(err) } return &w }
Marshal it to json string
func weatherToCache() { fmt.Println("fetching weather") if w := fetchWeather(); w != nil { j, err := json.Marshal(&w.Query.Results.Channel.Item) if err != nil { fmt.Println(err) } else { AddItemToCache(weatherURL, string(j)) } } }
and schedule fetching it
func weatherSchedule() { for range time.Tick(time.Hour * 1) { weatherToCache() } }
In main function We use iris to get the cached weather information after we put the weather scheduling to run on the background.
func main() { weatherToCache() go weatherSchedule() iris.Get("/weather", func(c *iris.Context) { c.Text(200, GetItemFromCache(weatherURL)) }) iris.Listen(":8080") }
Used or mentioned dependencies
iris-go.com
Concurrent map
LRU cache
See the whole project at https://github.com/jelinden/go-background-cache-example