MM-59933: Increment/Decrement the member count directly (#28196)
While using Redis, there is no need to invalidate and then update the new count from the DB when we know the exact number it is going to be incremented or decremented by. In that case, we can directly use Redis primitives to update the cache and prevent yet another DB query. To achieve this, we modify the LRU cache get/set paths slightly to not marshal into byte slices for *int64 values. This is needed for Redis to operate the INCR/DECR commands. https://mattermost.atlassian.net/browse/MM-59933 ```release-note NONE ``` Co-authored-by: Mattermost Build <build@mattermost.com>
Этот коммит содержится в:
коммит произвёл
GitHub
родитель
da24e0c4da
Коммит
7be7a47fd3
@@ -441,8 +441,13 @@ func (s LocalCacheChannelStore) SaveMember(rctx request.CTX, member *model.Chann
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// For redis, directly increment member count.
|
||||
s.InvalidateMemberCount(member.ChannelId)
|
||||
if externalCache, ok := s.rootStore.channelMemberCountsCache.(cache.ExternalCache); ok {
|
||||
s.rootStore.doIncrementCache(externalCache, member.ChannelId, 1)
|
||||
} else {
|
||||
s.InvalidateMemberCount(member.ChannelId)
|
||||
}
|
||||
return member, nil
|
||||
}
|
||||
|
||||
@@ -452,7 +457,15 @@ func (s LocalCacheChannelStore) SaveMultipleMembers(members []*model.ChannelMemb
|
||||
return nil, err
|
||||
}
|
||||
for _, member := range members {
|
||||
s.InvalidateMemberCount(member.ChannelId)
|
||||
// For redis, directly increment member count.
|
||||
// It should be possible to group the members from the slice
|
||||
// by channelID and increment it once per channel. But it depends
|
||||
// on whether all members are part of the same channel or not.
|
||||
if externalCache, ok := s.rootStore.channelMemberCountsCache.(cache.ExternalCache); ok {
|
||||
s.rootStore.doIncrementCache(externalCache, member.ChannelId, 1)
|
||||
} else {
|
||||
s.InvalidateMemberCount(member.ChannelId)
|
||||
}
|
||||
}
|
||||
return members, nil
|
||||
}
|
||||
@@ -522,8 +535,13 @@ func (s LocalCacheChannelStore) RemoveMember(rctx request.CTX, channelId, userId
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
// For redis, directly decrement member count
|
||||
s.InvalidateMemberCount(channelId)
|
||||
|
||||
// For redis, directly decrement member count.
|
||||
if externalCache, ok := s.rootStore.channelMemberCountsCache.(cache.ExternalCache); ok {
|
||||
s.rootStore.doDecrementCache(externalCache, channelId, 1)
|
||||
} else {
|
||||
s.InvalidateMemberCount(channelId)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
@@ -532,7 +550,11 @@ func (s LocalCacheChannelStore) RemoveMembers(rctx request.CTX, channelId string
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
// For redis, directly decrement member count
|
||||
s.InvalidateMemberCount(channelId)
|
||||
// For redis, directly decrement member count.
|
||||
if externalCache, ok := s.rootStore.channelMemberCountsCache.(cache.ExternalCache); ok {
|
||||
s.rootStore.doDecrementCache(externalCache, channelId, len(userIds))
|
||||
} else {
|
||||
s.InvalidateMemberCount(channelId)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
@@ -526,6 +526,20 @@ func (s *LocalCacheStore) doMultiReadCache(cache cache.Cache, keys []string, val
|
||||
return errs
|
||||
}
|
||||
|
||||
func (s *LocalCacheStore) doIncrementCache(cache cache.ExternalCache, key string, val int) {
|
||||
err := cache.Increment(key, val)
|
||||
if err != nil {
|
||||
s.logger.Warn("Error while incrementing cache entry", mlog.Err(err), mlog.String("cache_name", cache.Name()))
|
||||
}
|
||||
}
|
||||
|
||||
func (s *LocalCacheStore) doDecrementCache(cache cache.ExternalCache, key string, val int) {
|
||||
err := cache.Decrement(key, val)
|
||||
if err != nil {
|
||||
s.logger.Warn("Error while decrementing cache entry", mlog.Err(err), mlog.String("cache_name", cache.Name()))
|
||||
}
|
||||
}
|
||||
|
||||
func (s *LocalCacheStore) doClearCacheCluster(cache cache.Cache) {
|
||||
err := cache.Purge()
|
||||
if err != nil {
|
||||
|
||||
Ссылка в новой задаче
Block a user