Skip to content

Commit

Permalink
Merge pull request #4 from thinkoner/develop
Browse files Browse the repository at this point in the history
Added cache
  • Loading branch information
leeqvip authored Jan 28, 2019
2 parents f3e191b + e2619b0 commit 991903d
Show file tree
Hide file tree
Showing 11 changed files with 996 additions and 1 deletion.
19 changes: 18 additions & 1 deletion .travis.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,21 @@
language: go

sudo: false

go:
- "1.x"
- 1.6.x
- 1.7.x
- 1.8.x
- 1.9.x
- 1.10.x
- 1.11.x
- master

services:
- redis-server

before_install:
- go get github.com/mattn/goveralls

script:
- $HOME/gopath/bin/goveralls -service=travis-ci
49 changes: 49 additions & 0 deletions cache/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
# ThinkGo-Cache

`ThinkGo-Cache` is a cache library for Golang,it currently supports redis, memory, and can customize the store adapter.

## Installation

```
go get github.com/thinkoner/thinkgo/cache
```

## Usage

#### Basic Usage

```go
import (
"github.com/thinkoner/thinkgo/cache"
"time"
)


var foo string

// Create a cache with memory store
c, _ := cache.Cache(cache.NewMemoryStore("thinkgo"))

// Set the value
c.Put("foo", "thinkgo", 10 * time.Minute)

// Get the string associated with the key "foo" from the cache
c.Get("foo", &foo)

```

#### Retrieve & Store

Sometimes you may wish to retrieve an item from the cache, but also store a default value if the requested item doesn't exist. For example, you may wish to retrieve all users from the cache or, if they don't exist, retrieve them from the callback and add them to the cache. You may do this using the `Remember` method:

```go
var foo int

cache.Remember("foo", &a, 1*time.Minute, func() interface{} {
return "thinkgo"
})
```

## License

This project is licensed under the `Apache 2.0 license`.
38 changes: 38 additions & 0 deletions cache/cache.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
package cache

import (
"errors"
"fmt"
)

var adapters = make(map[string]Store)

// Register Register a cache adapter available by the adapter name.
func Register(name string, adapter Store) error {
if adapter == nil {
return errors.New("cache: Register adapter is nil")
}
if _, ok := adapters[name]; ok {
return errors.New("cache: Register called twice for adapter " + name)
}
adapters[name] = adapter
return nil
}

// NewCache Create a new cache by adapter name.
func Cache(adapter interface{}) (*Repository, error) {
var store Store
switch adapter.(type) {
case string:
var ok bool
store, ok = adapters[adapter.(string)]
if !ok {
err := fmt.Errorf("cache: unknown adapter name %q (forgot to import?)", adapter.(string))
return nil, err
}
case Store:
store = adapter.(Store)
}

return NewRepository(store), nil
}
123 changes: 123 additions & 0 deletions cache/cache_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,123 @@
package cache

import (
"fmt"
"testing"
"time"

"github.com/gomodule/redigo/redis"
)

func testCache(t *testing.T, cache *Repository) {
var a int
var b string
err := cache.Get("a", &a)
if err == nil {
t.Error("Getting A found value that shouldn't exist:", a)
}

err = cache.Get("b", &b)
if err == nil {
t.Error("Getting B found value that shouldn't exist:", b)
}

cache.Put("a", 1, 10*time.Minute)
cache.Put("b", "thinkgo", 10*time.Minute)

err = cache.Get("a", &a)
if err != nil {
t.Error(err)
}

if a != 1 {
t.Error("Expect: ", 1)
}

err = cache.Get("b", &b)
if err != nil {
t.Error(err)
}

if b != "thinkgo" {
t.Error("Expect: ", "thinkgo")
}

testCacheRemember(t, cache)
}

func testCacheRemember(t *testing.T, cache *Repository) {
cache.Clear()

var a int

err := cache.Remember("a", &a, 1*time.Minute, func() interface{} {
return 1
})

if err != nil {
t.Error(err)
}

if a != 1 {
t.Error(fmt.Sprintf("Expect: %d, Actual: %d ", 1, a))
}

err = cache.Remember("a", &a, 1*time.Minute, func() interface{} {
return 2
})

if err != nil {
t.Error(err)
}

if a != 1 {
t.Error(fmt.Sprintf("Expect: %d, Actual: %d ", 1, a))
}

cache.Clear()
err = cache.Remember("a", &a, 1*time.Minute, func() interface{} {
return 3
})

if err != nil {
t.Error(err)
}

if a != 3 {
t.Error(fmt.Sprintf("Expect: %d, Actual: %d ", 3, a))
}
}

func TestMemoryCache(t *testing.T) {
Register("memory", NewMemoryStore("thinkgo"))

cache, err := Cache("memory")

if err != nil {
t.Error(err)
}
testCache(t, cache)
}

func TestRedisCache(t *testing.T) {
pool := &redis.Pool{
MaxIdle: 5,
MaxActive: 1000,
IdleTimeout: 300 * time.Second,
Wait: true,
// Other pool configuration not shown in this example.
Dial: func() (redis.Conn, error) {
c, err := redis.Dial("tcp", "127.0.0.1:6379")
if err != nil {
return nil, err
}
return c, nil
},
}

cache, err := Cache(NewRedisStore(pool, "thinkgo"))
if err != nil {
t.Error(err)
}
testCache(t, cache)
}
Loading

0 comments on commit 991903d

Please sign in to comment.