Skip to content

Commit

Permalink
Cleanly shutdown cleanup go-routine (#337)
Browse files Browse the repository at this point in the history
* Shutdown cleanup go routine with context cancellation

Cleanly shutdown go routine. Big cache was made when go did not have ctx support

Fixes #336

* Review fixes

#337 (comment)
#337 (comment)
  • Loading branch information
alok87 authored Oct 12, 2022
1 parent fe96353 commit 8b4452b
Show file tree
Hide file tree
Showing 8 changed files with 87 additions and 66 deletions.
10 changes: 7 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,13 @@ Requires Go 1.12 or newer.
### Simple initialization

```go
import "github.com/allegro/bigcache/v3"
import (
"fmt"
"context"
"github.com/allegro/bigcache/v3"
)

cache, _ := bigcache.NewBigCache(bigcache.DefaultConfig(10 * time.Minute))
cache, _ := bigcache.New(context.Background(), bigcache.DefaultConfig(10 * time.Minute))

cache.Set("my-unique-key", []byte("value"))

Expand Down Expand Up @@ -71,7 +75,7 @@ config := bigcache.Config {
OnRemoveWithReason: nil,
}

cache, initErr := bigcache.NewBigCache(config)
cache, initErr := bigcache.New(context.Background(), config)
if initErr != nil {
log.Fatal(initErr)
}
Expand Down
17 changes: 15 additions & 2 deletions bigcache.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package bigcache

import (
"context"
"fmt"
"time"
)
Expand Down Expand Up @@ -40,12 +41,21 @@ const (
Deleted = RemoveReason(3)
)

// New initialize new instance of BigCache
func New(ctx context.Context, config Config) (*BigCache, error) {
return newBigCache(ctx, config, &systemClock{})
}

// NewBigCache initialize new instance of BigCache
//
// Deprecated: NewBigCache is deprecated, please use New(ctx, config) instead,
// New takes in context and can gracefully
// shutdown with context cancellations
func NewBigCache(config Config) (*BigCache, error) {
return newBigCache(config, &systemClock{})
return newBigCache(context.Background(), config, &systemClock{})
}

func newBigCache(config Config, clock clock) (*BigCache, error) {
func newBigCache(ctx context.Context, config Config, clock clock) (*BigCache, error) {
if !isPowerOfTwo(config.Shards) {
return nil, fmt.Errorf("Shards number must be power of two")
}
Expand Down Expand Up @@ -94,6 +104,9 @@ func newBigCache(config Config, clock clock) (*BigCache, error) {
defer ticker.Stop()
for {
select {
case <-ctx.Done():
fmt.Println("ctx done, shutting down bigcache cleanup routine")
return
case t := <-ticker.C:
cache.cleanUp(uint64(t.Unix()))
case <-cache.close:
Expand Down
15 changes: 8 additions & 7 deletions bigcache_bench_test.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package bigcache

import (
"context"
"fmt"
"math/rand"
"strconv"
Expand All @@ -16,7 +17,7 @@ func BenchmarkWriteToCacheWith1Shard(b *testing.B) {

func BenchmarkWriteToLimitedCacheWithSmallInitSizeAnd1Shard(b *testing.B) {
m := blob('a', 1024)
cache, _ := NewBigCache(Config{
cache, _ := New(context.Background(), Config{
Shards: 1,
LifeWindow: 100 * time.Second,
MaxEntriesInWindow: 100,
Expand All @@ -32,7 +33,7 @@ func BenchmarkWriteToLimitedCacheWithSmallInitSizeAnd1Shard(b *testing.B) {

func BenchmarkWriteToUnlimitedCacheWithSmallInitSizeAnd1Shard(b *testing.B) {
m := blob('a', 1024)
cache, _ := NewBigCache(Config{
cache, _ := New(context.Background(), Config{
Shards: 1,
LifeWindow: 100 * time.Second,
MaxEntriesInWindow: 100,
Expand Down Expand Up @@ -81,7 +82,7 @@ func BenchmarkIterateOverCache(b *testing.B) {

for _, shards := range []int{512, 1024, 8192} {
b.Run(fmt.Sprintf("%d-shards", shards), func(b *testing.B) {
cache, _ := NewBigCache(Config{
cache, _ := New(context.Background(), Config{
Shards: shards,
LifeWindow: 1000 * time.Second,
MaxEntriesInWindow: max(b.N, 100),
Expand Down Expand Up @@ -121,7 +122,7 @@ func BenchmarkReadFromCacheNonExistentKeys(b *testing.B) {
}

func writeToCache(b *testing.B, shards int, lifeWindow time.Duration, requestsInLifeWindow int) {
cache, _ := NewBigCache(Config{
cache, _ := New(context.Background(), Config{
Shards: shards,
LifeWindow: lifeWindow,
MaxEntriesInWindow: max(requestsInLifeWindow, 100),
Expand All @@ -142,7 +143,7 @@ func writeToCache(b *testing.B, shards int, lifeWindow time.Duration, requestsIn
}

func appendToCache(b *testing.B, shards int, lifeWindow time.Duration, requestsInLifeWindow int) {
cache, _ := NewBigCache(Config{
cache, _ := New(context.Background(), Config{
Shards: shards,
LifeWindow: lifeWindow,
MaxEntriesInWindow: max(requestsInLifeWindow, 100),
Expand All @@ -166,7 +167,7 @@ func appendToCache(b *testing.B, shards int, lifeWindow time.Duration, requestsI
}

func readFromCache(b *testing.B, shards int, info bool) {
cache, _ := NewBigCache(Config{
cache, _ := New(context.Background(), Config{
Shards: shards,
LifeWindow: 1000 * time.Second,
MaxEntriesInWindow: max(b.N, 100),
Expand All @@ -191,7 +192,7 @@ func readFromCache(b *testing.B, shards int, info bool) {
}

func readFromCacheNonExistentKeys(b *testing.B, shards int) {
cache, _ := NewBigCache(Config{
cache, _ := New(context.Background(), Config{
Shards: shards,
LifeWindow: 1000 * time.Second,
MaxEntriesInWindow: max(b.N, 100),
Expand Down
Loading

0 comments on commit 8b4452b

Please sign in to comment.