1
0
mirror of https://github.com/Mrs4s/MiraiGo.git synced 2025-05-04 19:17:38 +08:00

utils: port ttl cache to generic

This commit is contained in:
wdvxdr 2022-03-01 15:00:33 +08:00
parent 15a746802b
commit 6bc03d6b8c
No known key found for this signature in database
GPG Key ID: 703F8C071DE7A1B6
7 changed files with 25 additions and 22 deletions

View File

@ -83,7 +83,7 @@ func (c *QQClient) commMsgProcessor(pMsg *msg.Message, info *network.IncomingPac
c.Debug("c2c msg %v already exists in cache. skip.", pMsg.Head.GetMsgUid()) c.Debug("c2c msg %v already exists in cache. skip.", pMsg.Head.GetMsgUid())
return return
} }
c.msgSvcCache.Add(strKey, "", time.Hour) c.msgSvcCache.Add(strKey, unit{}, time.Hour)
if c.lastC2CMsgTime > int64(pMsg.Head.GetMsgTime()) && (c.lastC2CMsgTime-int64(pMsg.Head.GetMsgTime())) > 60*10 { if c.lastC2CMsgTime > int64(pMsg.Head.GetMsgTime()) && (c.lastC2CMsgTime-int64(pMsg.Head.GetMsgTime())) > 60*10 {
c.Debug("c2c msg filtered by time. lastMsgTime: %v msgTime: %v", c.lastC2CMsgTime, pMsg.Head.GetMsgTime()) c.Debug("c2c msg filtered by time. lastMsgTime: %v msgTime: %v", c.lastC2CMsgTime, pMsg.Head.GetMsgTime())
return return

View File

@ -77,12 +77,12 @@ type QQClient struct {
// fileStorageInfo *jce.FileStoragePushFSSvcList // fileStorageInfo *jce.FileStoragePushFSSvcList
// message state // message state
msgSvcCache *utils.Cache msgSvcCache *utils.Cache[unit]
lastC2CMsgTime int64 lastC2CMsgTime int64
transCache *utils.Cache transCache *utils.Cache[unit]
groupSysMsgCache *GroupSystemMessages groupSysMsgCache *GroupSystemMessages
msgBuilders sync.Map msgBuilders sync.Map
onlinePushCache *utils.Cache onlinePushCache *utils.Cache[unit]
heartbeatEnabled bool heartbeatEnabled bool
requestPacketRequestID atomic.Int32 requestPacketRequestID atomic.Int32
groupSeq atomic.Int32 groupSeq atomic.Int32
@ -164,9 +164,9 @@ func NewClientMd5(uin int64, passwordMd5 [16]byte) *QQClient {
sig: &auth.SigInfo{ sig: &auth.SigInfo{
OutPacketSessionID: []byte{0x02, 0xB0, 0x5B, 0x8B}, OutPacketSessionID: []byte{0x02, 0xB0, 0x5B, 0x8B},
}, },
msgSvcCache: utils.NewCache(time.Second * 15), msgSvcCache: utils.NewCache[unit](time.Second * 15),
transCache: utils.NewCache(time.Second * 15), transCache: utils.NewCache[unit](time.Second * 15),
onlinePushCache: utils.NewCache(time.Second * 15), onlinePushCache: utils.NewCache[unit](time.Second * 15),
servers: []*net.TCPAddr{}, servers: []*net.TCPAddr{},
alive: true, alive: true,
highwaySession: new(highway.Session), highwaySession: new(highway.Session),

View File

@ -646,7 +646,7 @@ func decodeOnlinePushTransPacket(c *QQClient, _ *network.IncomingPacketInfo, pay
if _, ok := c.transCache.Get(idStr); ok { if _, ok := c.transCache.Get(idStr); ok {
return nil, nil return nil, nil
} }
c.transCache.Add(idStr, "", time.Second*15) c.transCache.Add(idStr, unit{}, time.Second*15)
if info.GetMsgType() == 34 { if info.GetMsgType() == 34 {
data.ReadInt32() data.ReadInt32()
data.ReadByte() data.ReadByte()

View File

@ -296,6 +296,9 @@ type (
SigSession []byte SigSession []byte
SessionKey []byte SessionKey []byte
} }
// unit is an alias for struct{}, like `()` in rust
unit = struct{}
) )
const ( const (

View File

@ -37,7 +37,7 @@ func decodeOnlinePushReqPacket(c *QQClient, info *network.IncomingPacketInfo, pa
if _, ok := c.onlinePushCache.Get(k); ok { if _, ok := c.onlinePushCache.Get(k); ok {
continue continue
} }
c.onlinePushCache.Add(k, "", time.Second*30) c.onlinePushCache.Add(k, unit{}, time.Second*30)
// 0x2dc // 0x2dc
if m.MsgType == 732 { if m.MsgType == 732 {
r := binary.NewReader(m.VMsg) r := binary.NewReader(m.VMsg)

2
go.mod
View File

@ -1,6 +1,6 @@
module github.com/Mrs4s/MiraiGo module github.com/Mrs4s/MiraiGo
go 1.17 go 1.18
require ( require (
github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248 github.com/RomiChan/protobuf v0.0.0-20220227114948-643565fff248

View File

@ -7,26 +7,26 @@ import (
// https://github.com/Konstantin8105/SimpleTTL // https://github.com/Konstantin8105/SimpleTTL
// entry - typical element of cache // entry - typical element of cache
type entry struct { type entry[T any] struct {
expiry time.Time expiry time.Time
value interface{} value T
} }
// Cache - simple implementation of cache // Cache - simple implementation of cache
// More information: https://en.wikipedia.org/wiki/Time_to_live // More information: https://en.wikipedia.org/wiki/Time_to_live
type Cache struct { type Cache[T any] struct {
lock sync.RWMutex lock sync.RWMutex
cache map[string]*entry cache map[string]*entry[T]
} }
// NewCache - initialization of new cache. // NewCache - initialization of new cache.
// For avoid mistake - minimal time to live is 1 minute. // For avoid mistake - minimal time to live is 1 minute.
// For simplification, - key is string and cache haven`t stop method // For simplification, - key is string and cache haven`t stop method
func NewCache(interval time.Duration) *Cache { func NewCache[T any](interval time.Duration) *Cache[T] {
if interval < time.Second { if interval < time.Second {
interval = time.Second interval = time.Second
} }
cache := &Cache{cache: make(map[string]*entry)} cache := &Cache[T]{cache: make(map[string]*entry[T])}
go func() { go func() {
ticker := time.NewTicker(interval) ticker := time.NewTicker(interval)
for { for {
@ -47,7 +47,7 @@ func NewCache(interval time.Duration) *Cache {
} }
// Count - return amount element of TTL map. // Count - return amount element of TTL map.
func (cache *Cache) Count() int { func (cache *Cache[_]) Count() int {
cache.lock.RLock() cache.lock.RLock()
defer cache.lock.RUnlock() defer cache.lock.RUnlock()
@ -55,7 +55,7 @@ func (cache *Cache) Count() int {
} }
// Get - return value from cache // Get - return value from cache
func (cache *Cache) Get(key string) (interface{}, bool) { func (cache *Cache[_]) Get(key string) (interface{}, bool) {
cache.lock.RLock() cache.lock.RLock()
defer cache.lock.RUnlock() defer cache.lock.RUnlock()
@ -67,7 +67,7 @@ func (cache *Cache) Get(key string) (interface{}, bool) {
return nil, false return nil, false
} }
func (cache *Cache) GetAndUpdate(key string, ttl time.Duration) (interface{}, bool) { func (cache *Cache[_]) GetAndUpdate(key string, ttl time.Duration) (interface{}, bool) {
cache.lock.RLock() cache.lock.RLock()
defer cache.lock.RUnlock() defer cache.lock.RUnlock()
@ -79,18 +79,18 @@ func (cache *Cache) GetAndUpdate(key string, ttl time.Duration) (interface{}, bo
} }
// Add - add key/value in cache // Add - add key/value in cache
func (cache *Cache) Add(key string, value interface{}, ttl time.Duration) { func (cache *Cache[T]) Add(key string, value T, ttl time.Duration) {
cache.lock.Lock() cache.lock.Lock()
defer cache.lock.Unlock() defer cache.lock.Unlock()
cache.cache[key] = &entry{ cache.cache[key] = &entry[T]{
value: value, value: value,
expiry: time.Now().Add(ttl), expiry: time.Now().Add(ttl),
} }
} }
// GetKeys - return all keys of cache map // GetKeys - return all keys of cache map
func (cache *Cache) GetKeys() []string { func (cache *Cache[T]) GetKeys() []string {
cache.lock.RLock() cache.lock.RLock()
defer cache.lock.RUnlock() defer cache.lock.RUnlock()