github.com/dschalla/mattermost-server@v4.8.1-rc1+incompatible/store/layered_store.go (about) 1 // Copyright (c) 2016-present Mattermost, Inc. All Rights Reserved. 2 // See License.txt for license information. 3 4 package store 5 6 import ( 7 "context" 8 9 l4g "github.com/alecthomas/log4go" 10 "github.com/mattermost/mattermost-server/einterfaces" 11 "github.com/mattermost/mattermost-server/model" 12 ) 13 14 const ( 15 ENABLE_EXPERIMENTAL_REDIS = false 16 ) 17 18 type LayeredStoreDatabaseLayer interface { 19 LayeredStoreSupplier 20 Store 21 } 22 23 type LayeredStore struct { 24 TmpContext context.Context 25 ReactionStore ReactionStore 26 DatabaseLayer LayeredStoreDatabaseLayer 27 LocalCacheLayer *LocalCacheSupplier 28 RedisLayer *RedisSupplier 29 LayerChainHead LayeredStoreSupplier 30 } 31 32 func NewLayeredStore(db LayeredStoreDatabaseLayer, metrics einterfaces.MetricsInterface, cluster einterfaces.ClusterInterface) Store { 33 store := &LayeredStore{ 34 TmpContext: context.TODO(), 35 DatabaseLayer: db, 36 LocalCacheLayer: NewLocalCacheSupplier(metrics, cluster), 37 } 38 39 store.ReactionStore = &LayeredReactionStore{store} 40 41 // Setup the chain 42 if ENABLE_EXPERIMENTAL_REDIS { 43 l4g.Debug("Experimental redis enabled.") 44 store.RedisLayer = NewRedisSupplier() 45 store.RedisLayer.SetChainNext(store.DatabaseLayer) 46 store.LayerChainHead = store.RedisLayer 47 } else { 48 store.LocalCacheLayer.SetChainNext(store.DatabaseLayer) 49 store.LayerChainHead = store.LocalCacheLayer 50 } 51 52 return store 53 } 54 55 type QueryFunction func(LayeredStoreSupplier) *LayeredStoreSupplierResult 56 57 func (s *LayeredStore) RunQuery(queryFunction QueryFunction) StoreChannel { 58 storeChannel := make(StoreChannel) 59 60 go func() { 61 result := queryFunction(s.LayerChainHead) 62 storeChannel <- result.StoreResult 63 }() 64 65 return storeChannel 66 } 67 68 func (s *LayeredStore) Team() TeamStore { 69 return s.DatabaseLayer.Team() 70 } 71 72 func (s *LayeredStore) Channel() ChannelStore { 73 return s.DatabaseLayer.Channel() 74 } 75 76 func (s *LayeredStore) Post() PostStore { 77 return s.DatabaseLayer.Post() 78 } 79 80 func (s *LayeredStore) User() UserStore { 81 return s.DatabaseLayer.User() 82 } 83 84 func (s *LayeredStore) Audit() AuditStore { 85 return s.DatabaseLayer.Audit() 86 } 87 88 func (s *LayeredStore) ClusterDiscovery() ClusterDiscoveryStore { 89 return s.DatabaseLayer.ClusterDiscovery() 90 } 91 92 func (s *LayeredStore) Compliance() ComplianceStore { 93 return s.DatabaseLayer.Compliance() 94 } 95 96 func (s *LayeredStore) Session() SessionStore { 97 return s.DatabaseLayer.Session() 98 } 99 100 func (s *LayeredStore) OAuth() OAuthStore { 101 return s.DatabaseLayer.OAuth() 102 } 103 104 func (s *LayeredStore) System() SystemStore { 105 return s.DatabaseLayer.System() 106 } 107 108 func (s *LayeredStore) Webhook() WebhookStore { 109 return s.DatabaseLayer.Webhook() 110 } 111 112 func (s *LayeredStore) Command() CommandStore { 113 return s.DatabaseLayer.Command() 114 } 115 116 func (s *LayeredStore) CommandWebhook() CommandWebhookStore { 117 return s.DatabaseLayer.CommandWebhook() 118 } 119 120 func (s *LayeredStore) Preference() PreferenceStore { 121 return s.DatabaseLayer.Preference() 122 } 123 124 func (s *LayeredStore) License() LicenseStore { 125 return s.DatabaseLayer.License() 126 } 127 128 func (s *LayeredStore) Token() TokenStore { 129 return s.DatabaseLayer.Token() 130 } 131 132 func (s *LayeredStore) Emoji() EmojiStore { 133 return s.DatabaseLayer.Emoji() 134 } 135 136 func (s *LayeredStore) Status() StatusStore { 137 return s.DatabaseLayer.Status() 138 } 139 140 func (s *LayeredStore) FileInfo() FileInfoStore { 141 return s.DatabaseLayer.FileInfo() 142 } 143 144 func (s *LayeredStore) Reaction() ReactionStore { 145 return s.ReactionStore 146 } 147 148 func (s *LayeredStore) Job() JobStore { 149 return s.DatabaseLayer.Job() 150 } 151 152 func (s *LayeredStore) UserAccessToken() UserAccessTokenStore { 153 return s.DatabaseLayer.UserAccessToken() 154 } 155 156 func (s *LayeredStore) ChannelMemberHistory() ChannelMemberHistoryStore { 157 return s.DatabaseLayer.ChannelMemberHistory() 158 } 159 160 func (s *LayeredStore) Plugin() PluginStore { 161 return s.DatabaseLayer.Plugin() 162 } 163 164 func (s *LayeredStore) MarkSystemRanUnitTests() { 165 s.DatabaseLayer.MarkSystemRanUnitTests() 166 } 167 168 func (s *LayeredStore) Close() { 169 s.DatabaseLayer.Close() 170 } 171 172 func (s *LayeredStore) DropAllTables() { 173 s.DatabaseLayer.DropAllTables() 174 } 175 176 func (s *LayeredStore) TotalMasterDbConnections() int { 177 return s.DatabaseLayer.TotalMasterDbConnections() 178 } 179 180 func (s *LayeredStore) TotalReadDbConnections() int { 181 return s.DatabaseLayer.TotalReadDbConnections() 182 } 183 184 func (s *LayeredStore) TotalSearchDbConnections() int { 185 return s.DatabaseLayer.TotalSearchDbConnections() 186 } 187 188 type LayeredReactionStore struct { 189 *LayeredStore 190 } 191 192 func (s *LayeredReactionStore) Save(reaction *model.Reaction) StoreChannel { 193 return s.RunQuery(func(supplier LayeredStoreSupplier) *LayeredStoreSupplierResult { 194 return supplier.ReactionSave(s.TmpContext, reaction) 195 }) 196 } 197 198 func (s *LayeredReactionStore) Delete(reaction *model.Reaction) StoreChannel { 199 return s.RunQuery(func(supplier LayeredStoreSupplier) *LayeredStoreSupplierResult { 200 return supplier.ReactionDelete(s.TmpContext, reaction) 201 }) 202 } 203 204 func (s *LayeredReactionStore) GetForPost(postId string, allowFromCache bool) StoreChannel { 205 return s.RunQuery(func(supplier LayeredStoreSupplier) *LayeredStoreSupplierResult { 206 return supplier.ReactionGetForPost(s.TmpContext, postId) 207 }) 208 } 209 210 func (s *LayeredReactionStore) DeleteAllWithEmojiName(emojiName string) StoreChannel { 211 return s.RunQuery(func(supplier LayeredStoreSupplier) *LayeredStoreSupplierResult { 212 return supplier.ReactionDeleteAllWithEmojiName(s.TmpContext, emojiName) 213 }) 214 } 215 216 func (s *LayeredReactionStore) PermanentDeleteBatch(endTime int64, limit int64) StoreChannel { 217 return s.RunQuery(func(supplier LayeredStoreSupplier) *LayeredStoreSupplierResult { 218 return supplier.ReactionPermanentDeleteBatch(s.TmpContext, endTime, limit) 219 }) 220 }