Libcache
A Lightweight in-memory key:value cache library for Go.
Introduction
Caches are tremendously useful in a wide variety of use cases.
you should consider using caches when a value is expensive to compute or retrieve,
and you will need its value on a certain input more than once.
libcache is here to help with that.
Libcache are local to a single run of your application.
They do not store data in files, or on outside servers.
Libcache previously an go-guardian package and designed to be a companion with it.
While both can operate completely independently.
Features
- Rich caching API
 - Maximum cache size enforcement
 - Default cache TTL (time-to-live) as well as custom TTLs per cache entry
 - Thread safe as well as non-thread safe
 - Event-Driven callbacks (OnExpired,OnEvicted)
 - Dynamic cache creation
 - Multiple cache replacement policies:
- FIFO (First In, First Out)
 - LIFO (Last In, First Out)
 - LRU (Least Recently Used)
 - MRU (Most Recently Used)
 - LFU (Least Frequently Used)
 - ARC (Adaptive Replacement Cache)
 
 
Quickstart
Installing
Using libcache is easy. First, use go get to install the latest version of the library.
go get github.com/shaj13/libcache
Next, include libcache in your application:
import (
    _ "github.com/shaj13/libcache/<desired-replacement-policy>"
    "github.com/shaj13/libcache"
)
Examples
Note: All examples use the LRU cache replacement policy for simplicity, any other cache replacement policy can be applied to them.
Basic
package main 
import (
    "fmt" 
    "github.com/shaj13/libcache"
    _ "github.com/shaj13/libcache/lru"
)
func main() {
    size := 10
    cache := libcache.LRU.NewUnsafe(size)
    for i:= 0 ; i < 10 ; i++ {
        cache.Store(i, i)
    }
    fmt.Println(cache.Load(0)) // nil, false  
    fmt.Println(cache.Load(1)) // 1, true
}
Thread Safe
package main
import (
	"fmt"
	"github.com/shaj13/libcache"
	_ "github.com/shaj13/libcache/lru"
)
func main() {
	done := make(chan struct{})
	f := func(c libcache.Cache) {
		for !c.Contains(5) {
		}
		fmt.Println(c.Load(5)) // 5, true
		done <- struct{}{}
	}
	size := 10
	cache := libcache.LRU.New(size)
	go f(cache)
	for i := 0; i < 10; i++ {
		cache.Store(i, i)
	}
	<-done
}
Unlimited Size
zero capacity means cache has no limit and replacement policy turned off.
package main 
import (
    "fmt" 
    "github.com/shaj13/libcache"
    _ "github.com/shaj13/libcache/lru"
)
func main() {
	cache := libcache.LRU.New(0)
    for i:= 0 ; i < 100000 ; i++ {
        cache.Store(i, i)
    }
	fmt.Println(cache.Load(55555))
}
TTL
package main 
import (
	"fmt"
	"time"
	"github.com/shaj13/libcache"
	_ "github.com/shaj13/libcache/lru"
)
func main() {
	cache := libcache.LRU.New(10)
	cache.SetTTL(time.Second) // default TTL 
	
	for i:= 0 ; i < 10 ; i++ {
        cache.Store(i, i)
	}
	fmt.Println(cache.Expiry(1))
	cache.StoreWithTTL("mykey", "value", time.Hour) // TTL per cache entry 
	fmt.Println(cache.Expiry("mykey"))
}
Events
Timed expiration by default is performed with lazy maintenance during reads operations,
Evict an expired entry immediately can be done using on expired callback.
You may also specify a eviction listener for your cache to perform some operation when an entry is evicted.
Note: Expiration events relying on golang runtime timers heap to call on expired callback when an entry TTL elapsed.
package main 
import (
	"fmt"
	"time"
	"github.com/shaj13/libcache"
	_ "github.com/shaj13/libcache/lru"
)
func main() {
	cache := libcache.LRU.New(10)
	cache.RegisterOnEvicted(func(key, value interface{}) {
		fmt.Printf("Cache Key %v Evicted\n", key)
	})
	cache.RegisterOnExpired(func(key, value interface{}) {
		fmt.Printf("Cache Key %v Expired, Removing it from cache\n", key)
		// use delete directly when your application 
		// guarantee no other goroutine can store items with the same key.
		// Peek also invoke lazy expiry. 
		// 
		// Note this should done only with safe cache.
		cache.Peek(key) 
	})	
	for i:= 0 ; i < 10 ; i++ {
        cache.StoreWithTTL(i, i, time.Microsecond)
	}
	time.Sleep(time.Second)
	fmt.Println(cache.Len())
}
Contributing
- Fork it
 - Download your fork to your PC (
git clone https://github.com/your_username/libcache && cd libcache) - Create your feature branch (
git checkout -b my-new-feature) - Make changes and add them (
git add .) - Commit your changes (
git commit -m 'Add some feature') - Push to the branch (
git push origin my-new-feature) - Create new pull request
 
License
Libcache is released under the MIT license. See LICENSE