1
0
mirror of https://github.com/owncloud/ocis.git synced 2025-04-18 23:44:07 +03:00

Bump github.com/jellydator/ttlcache/v3 from 3.2.0 to 3.3.0

Bumps [github.com/jellydator/ttlcache/v3](https://github.com/jellydator/ttlcache) from 3.2.0 to 3.3.0.
- [Release notes](https://github.com/jellydator/ttlcache/releases)
- [Commits](https://github.com/jellydator/ttlcache/compare/v3.2.0...v3.3.0)

---
updated-dependencies:
- dependency-name: github.com/jellydator/ttlcache/v3
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
This commit is contained in:
dependabot[bot] 2024-08-28 06:21:50 +00:00 committed by Ralf Haferkamp
parent eff0ab1609
commit 90f66d707d
5 changed files with 93 additions and 25 deletions

2
go.mod
View File

@ -51,7 +51,7 @@ require (
github.com/grpc-ecosystem/grpc-gateway/v2 v2.22.0
github.com/invopop/validation v0.8.0
github.com/jellydator/ttlcache/v2 v2.11.1
github.com/jellydator/ttlcache/v3 v3.2.0
github.com/jellydator/ttlcache/v3 v3.3.0
github.com/jinzhu/now v1.1.5
github.com/justinas/alice v1.2.0
github.com/kovidgoyal/imaging v1.6.3

4
go.sum
View File

@ -705,8 +705,8 @@ github.com/jcmturner/rpc/v2 v2.0.3 h1:7FXXj8Ti1IaVFpSAziCZWNzbNuZmnvw/i6CqLNdWfZ
github.com/jcmturner/rpc/v2 v2.0.3/go.mod h1:VUJYCIDm3PVOEHw8sgt091/20OJjskO/YJki3ELg/Hc=
github.com/jellydator/ttlcache/v2 v2.11.1 h1:AZGME43Eh2Vv3giG6GeqeLeFXxwxn1/qHItqWZl6U64=
github.com/jellydator/ttlcache/v2 v2.11.1/go.mod h1:RtE5Snf0/57e+2cLWFYWCCsLas2Hy3c5Z4n14XmSvTI=
github.com/jellydator/ttlcache/v3 v3.2.0 h1:6lqVJ8X3ZaUwvzENqPAobDsXNExfUJd61u++uW8a3LE=
github.com/jellydator/ttlcache/v3 v3.2.0/go.mod h1:hi7MGFdMAwZna5n2tuvh63DvFLzVKySzCVW6+0gA2n4=
github.com/jellydator/ttlcache/v3 v3.3.0 h1:BdoC9cE81qXfrxeb9eoJi9dWrdhSuwXMAnHTbnBm4Wc=
github.com/jellydator/ttlcache/v3 v3.3.0/go.mod h1:bj2/e0l4jRnQdrnSTaGTsh4GSXvMjQcy41i7th0GVGw=
github.com/jessevdk/go-flags v1.4.0/go.mod h1:4FA24M0QyGHXBuZZK/XkWh8h0e1EYbRYJSGM75WSRxI=
github.com/jhump/protoreflect v1.15.1 h1:HUMERORf3I3ZdX05WaQ6MIpd/NJ434hTp5YiKgfCL6c=
github.com/jhump/protoreflect v1.15.1/go.mod h1:jD/2GMKKE6OqX8qTjhADU1e6DShO+gavG9e0Q693nKo=

View File

@ -10,7 +10,8 @@
- Type parameters
- Item expiration and automatic deletion
- Automatic expiration time extension on each `Get` call
- `Loader` interface that may be used to load/lazily initialize missing cache
- `Loader` interface that may be used to load/lazily initialize missing cache
- Thread Safe
items
- Event handlers (insertion and eviction)
- Metrics

View File

@ -133,7 +133,7 @@ func (c *Cache[K, V]) set(key K, value V, ttl time.Duration) *Item[K, V] {
ttl = c.options.ttl
}
elem := c.get(key, false)
elem := c.get(key, false, true)
if elem != nil {
// update/overwrite an existing item
item := elem.Value.(*Item[K, V])
@ -176,14 +176,14 @@ func (c *Cache[K, V]) set(key K, value V, ttl time.Duration) *Item[K, V] {
// It returns nil if the item is not found or is expired.
// Not safe for concurrent use by multiple goroutines without additional
// locking.
func (c *Cache[K, V]) get(key K, touch bool) *list.Element {
func (c *Cache[K, V]) get(key K, touch bool, includeExpired bool) *list.Element {
elem := c.items.values[key]
if elem == nil {
return nil
}
item := elem.Value.(*Item[K, V])
if item.isExpiredUnsafe() {
if !includeExpired && item.isExpiredUnsafe() {
return nil
}
@ -218,7 +218,7 @@ func (c *Cache[K, V]) getWithOpts(key K, lockAndLoad bool, opts ...Option[K, V])
c.items.mu.Lock()
}
elem := c.get(key, !getOpts.disableTouchOnHit)
elem := c.get(key, !getOpts.disableTouchOnHit, false)
if lockAndLoad {
c.items.mu.Unlock()
@ -339,8 +339,8 @@ func (c *Cache[K, V]) Has(key K) bool {
c.items.mu.RLock()
defer c.items.mu.RUnlock()
_, ok := c.items.values[key]
return ok
elem, ok := c.items.values[key]
return ok && !elem.Value.(*Item[K, V]).isExpiredUnsafe()
}
// GetOrSet retrieves an item from the cache by the provided key.
@ -436,26 +436,66 @@ func (c *Cache[K, V]) DeleteExpired() {
// If the item is not found, the method is no-op.
func (c *Cache[K, V]) Touch(key K) {
c.items.mu.Lock()
c.get(key, true)
c.get(key, true, false)
c.items.mu.Unlock()
}
// Len returns the total number of items in the cache.
// Len returns the number of unexpired items in the cache.
func (c *Cache[K, V]) Len() int {
c.items.mu.RLock()
defer c.items.mu.RUnlock()
return len(c.items.values)
total := c.items.expQueue.Len()
if total == 0 {
return 0
}
// search the heap-based expQueue by BFS
countExpired := func() int {
var (
q []int
res int
)
item := c.items.expQueue[0].Value.(*Item[K, V])
if !item.isExpiredUnsafe() {
return res
}
q = append(q, 0)
for len(q) > 0 {
pop := q[0]
q = q[1:]
res++
for i := 1; i <= 2; i++ {
idx := 2*pop + i
if idx >= total {
break
}
item = c.items.expQueue[idx].Value.(*Item[K, V])
if item.isExpiredUnsafe() {
q = append(q, idx)
}
}
}
return res
}
return total - countExpired()
}
// Keys returns all keys currently present in the cache.
// Keys returns all unexpired keys in the cache.
func (c *Cache[K, V]) Keys() []K {
c.items.mu.RLock()
defer c.items.mu.RUnlock()
res := make([]K, 0, len(c.items.values))
for k := range c.items.values {
res = append(res, k)
res := make([]K, 0)
for k, elem := range c.items.values {
if !elem.Value.(*Item[K, V]).isExpiredUnsafe() {
res = append(res, k)
}
}
return res
@ -467,18 +507,18 @@ func (c *Cache[K, V]) Items() map[K]*Item[K, V] {
c.items.mu.RLock()
defer c.items.mu.RUnlock()
items := make(map[K]*Item[K, V], len(c.items.values))
for k := range c.items.values {
item := c.get(k, false)
if item != nil {
items[k] = item.Value.(*Item[K, V])
items := make(map[K]*Item[K, V])
for k, elem := range c.items.values {
item := elem.Value.(*Item[K, V])
if item != nil && !item.isExpiredUnsafe() {
items[k] = item
}
}
return items
}
// Range calls fn for each item present in the cache. If fn returns false,
// Range calls fn for each unexpired item in the cache. If fn returns false,
// Range stops the iteration.
func (c *Cache[K, V]) Range(fn func(item *Item[K, V]) bool) {
c.items.mu.RLock()
@ -491,9 +531,10 @@ func (c *Cache[K, V]) Range(fn func(item *Item[K, V]) bool) {
for item := c.items.lru.Front(); item != c.items.lru.Back().Next(); item = item.Next() {
i := item.Value.(*Item[K, V])
expired := i.isExpiredUnsafe()
c.items.mu.RUnlock()
if !fn(i) {
if !expired && !fn(i) {
return
}
@ -503,6 +544,32 @@ func (c *Cache[K, V]) Range(fn func(item *Item[K, V]) bool) {
}
}
// RangeBackwards calls fn for each unexpired item in the cache in reverse order.
// If fn returns false, RangeBackwards stops the iteration.
func (c *Cache[K, V]) RangeBackwards(fn func(item *Item[K, V]) bool) {
c.items.mu.RLock()
// Check if cache is empty
if c.items.lru.Len() == 0 {
c.items.mu.RUnlock()
return
}
for item := c.items.lru.Back(); item != c.items.lru.Front().Prev(); item = item.Prev() {
i := item.Value.(*Item[K, V])
expired := i.isExpiredUnsafe()
c.items.mu.RUnlock()
if !expired && !fn(i) {
return
}
if item.Prev() != nil {
c.items.mu.RLock()
}
}
}
// Metrics returns the metrics of the cache.
func (c *Cache[K, V]) Metrics() Metrics {
c.metricsMu.RLock()

2
vendor/modules.txt vendored
View File

@ -1231,7 +1231,7 @@ github.com/jbenet/go-context/io
# github.com/jellydator/ttlcache/v2 v2.11.1
## explicit; go 1.15
github.com/jellydator/ttlcache/v2
# github.com/jellydator/ttlcache/v3 v3.2.0
# github.com/jellydator/ttlcache/v3 v3.3.0
## explicit; go 1.18
github.com/jellydator/ttlcache/v3
# github.com/jinzhu/now v1.1.5