github.com/xzl8028/xenia-server@v0.0.0-20190809101854-18450a97da63/store/layered_store.go (about)

     1  // Copyright (c) 2016-present Xenia, Inc. All Rights Reserved.
     2  // See License.txt for license information.
     3  
     4  package store
     5  
     6  import (
     7  	"context"
     8  
     9  	"github.com/xzl8028/xenia-server/einterfaces"
    10  	"github.com/xzl8028/xenia-server/mlog"
    11  	"github.com/xzl8028/xenia-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  	RoleStore       RoleStore
    27  	SchemeStore     SchemeStore
    28  	DatabaseLayer   LayeredStoreDatabaseLayer
    29  	LocalCacheLayer *LocalCacheSupplier
    30  	RedisLayer      *RedisSupplier
    31  	LayerChainHead  LayeredStoreSupplier
    32  }
    33  
    34  func NewLayeredStore(db LayeredStoreDatabaseLayer, metrics einterfaces.MetricsInterface, cluster einterfaces.ClusterInterface) Store {
    35  	store := &LayeredStore{
    36  		TmpContext:      context.TODO(),
    37  		DatabaseLayer:   db,
    38  		LocalCacheLayer: NewLocalCacheSupplier(metrics, cluster),
    39  	}
    40  
    41  	store.ReactionStore = &LayeredReactionStore{store}
    42  	store.RoleStore = &LayeredRoleStore{store}
    43  	store.SchemeStore = &LayeredSchemeStore{store}
    44  
    45  	// Setup the chain
    46  	if ENABLE_EXPERIMENTAL_REDIS {
    47  		mlog.Debug("Experimental redis enabled.")
    48  		store.RedisLayer = NewRedisSupplier()
    49  		store.RedisLayer.SetChainNext(store.DatabaseLayer)
    50  		store.LayerChainHead = store.RedisLayer
    51  	} else {
    52  		store.LocalCacheLayer.SetChainNext(store.DatabaseLayer)
    53  		store.LayerChainHead = store.LocalCacheLayer
    54  	}
    55  
    56  	return store
    57  }
    58  
    59  type QueryFunction func(LayeredStoreSupplier) *LayeredStoreSupplierResult
    60  
    61  func (s *LayeredStore) RunQuery(queryFunction QueryFunction) StoreChannel {
    62  	storeChannel := make(StoreChannel)
    63  
    64  	go func() {
    65  		result := queryFunction(s.LayerChainHead)
    66  		storeChannel <- result.StoreResult
    67  	}()
    68  
    69  	return storeChannel
    70  }
    71  
    72  func (s *LayeredStore) Team() TeamStore {
    73  	return s.DatabaseLayer.Team()
    74  }
    75  
    76  func (s *LayeredStore) Channel() ChannelStore {
    77  	return s.DatabaseLayer.Channel()
    78  }
    79  
    80  func (s *LayeredStore) Post() PostStore {
    81  	return s.DatabaseLayer.Post()
    82  }
    83  
    84  func (s *LayeredStore) User() UserStore {
    85  	return s.DatabaseLayer.User()
    86  }
    87  
    88  func (s *LayeredStore) Bot() BotStore {
    89  	return s.DatabaseLayer.Bot()
    90  }
    91  
    92  func (s *LayeredStore) Task() TaskStore {
    93  	return s.DatabaseLayer.Task()
    94  }
    95  
    96  func (s *LayeredStore) Audit() AuditStore {
    97  	return s.DatabaseLayer.Audit()
    98  }
    99  
   100  func (s *LayeredStore) ClusterDiscovery() ClusterDiscoveryStore {
   101  	return s.DatabaseLayer.ClusterDiscovery()
   102  }
   103  
   104  func (s *LayeredStore) Compliance() ComplianceStore {
   105  	return s.DatabaseLayer.Compliance()
   106  }
   107  
   108  func (s *LayeredStore) Session() SessionStore {
   109  	return s.DatabaseLayer.Session()
   110  }
   111  
   112  func (s *LayeredStore) OAuth() OAuthStore {
   113  	return s.DatabaseLayer.OAuth()
   114  }
   115  
   116  func (s *LayeredStore) System() SystemStore {
   117  	return s.DatabaseLayer.System()
   118  }
   119  
   120  func (s *LayeredStore) Webhook() WebhookStore {
   121  	return s.DatabaseLayer.Webhook()
   122  }
   123  
   124  func (s *LayeredStore) Command() CommandStore {
   125  	return s.DatabaseLayer.Command()
   126  }
   127  
   128  func (s *LayeredStore) CommandWebhook() CommandWebhookStore {
   129  	return s.DatabaseLayer.CommandWebhook()
   130  }
   131  
   132  func (s *LayeredStore) Preference() PreferenceStore {
   133  	return s.DatabaseLayer.Preference()
   134  }
   135  
   136  func (s *LayeredStore) License() LicenseStore {
   137  	return s.DatabaseLayer.License()
   138  }
   139  
   140  func (s *LayeredStore) Token() TokenStore {
   141  	return s.DatabaseLayer.Token()
   142  }
   143  
   144  func (s *LayeredStore) Emoji() EmojiStore {
   145  	return s.DatabaseLayer.Emoji()
   146  }
   147  
   148  func (s *LayeredStore) Status() StatusStore {
   149  	return s.DatabaseLayer.Status()
   150  }
   151  
   152  func (s *LayeredStore) FileInfo() FileInfoStore {
   153  	return s.DatabaseLayer.FileInfo()
   154  }
   155  
   156  func (s *LayeredStore) Reaction() ReactionStore {
   157  	return s.ReactionStore
   158  }
   159  
   160  func (s *LayeredStore) Job() JobStore {
   161  	return s.DatabaseLayer.Job()
   162  }
   163  
   164  func (s *LayeredStore) UserAccessToken() UserAccessTokenStore {
   165  	return s.DatabaseLayer.UserAccessToken()
   166  }
   167  
   168  func (s *LayeredStore) ChannelMemberHistory() ChannelMemberHistoryStore {
   169  	return s.DatabaseLayer.ChannelMemberHistory()
   170  }
   171  
   172  func (s *LayeredStore) Plugin() PluginStore {
   173  	return s.DatabaseLayer.Plugin()
   174  }
   175  
   176  func (s *LayeredStore) Role() RoleStore {
   177  	return s.RoleStore
   178  }
   179  
   180  func (s *LayeredStore) TermsOfService() TermsOfServiceStore {
   181  	return s.DatabaseLayer.TermsOfService()
   182  }
   183  
   184  func (s *LayeredStore) UserTermsOfService() UserTermsOfServiceStore {
   185  	return s.DatabaseLayer.UserTermsOfService()
   186  }
   187  
   188  func (s *LayeredStore) Scheme() SchemeStore {
   189  	return s.SchemeStore
   190  }
   191  
   192  func (s *LayeredStore) Group() GroupStore {
   193  	return s.DatabaseLayer.Group()
   194  }
   195  
   196  func (s *LayeredStore) LinkMetadata() LinkMetadataStore {
   197  	return s.DatabaseLayer.LinkMetadata()
   198  }
   199  
   200  func (s *LayeredStore) MarkSystemRanUnitTests() {
   201  	s.DatabaseLayer.MarkSystemRanUnitTests()
   202  }
   203  
   204  func (s *LayeredStore) Close() {
   205  	s.DatabaseLayer.Close()
   206  }
   207  
   208  func (s *LayeredStore) LockToMaster() {
   209  	s.DatabaseLayer.LockToMaster()
   210  }
   211  
   212  func (s *LayeredStore) UnlockFromMaster() {
   213  	s.DatabaseLayer.UnlockFromMaster()
   214  }
   215  
   216  func (s *LayeredStore) DropAllTables() {
   217  	defer s.LocalCacheLayer.Invalidate()
   218  	s.DatabaseLayer.DropAllTables()
   219  }
   220  
   221  func (s *LayeredStore) TotalMasterDbConnections() int {
   222  	return s.DatabaseLayer.TotalMasterDbConnections()
   223  }
   224  
   225  func (s *LayeredStore) TotalReadDbConnections() int {
   226  	return s.DatabaseLayer.TotalReadDbConnections()
   227  }
   228  
   229  func (s *LayeredStore) TotalSearchDbConnections() int {
   230  	return s.DatabaseLayer.TotalSearchDbConnections()
   231  }
   232  
   233  type LayeredReactionStore struct {
   234  	*LayeredStore
   235  }
   236  
   237  func (s *LayeredReactionStore) Save(reaction *model.Reaction) (*model.Reaction, *model.AppError) {
   238  	return s.LayerChainHead.ReactionSave(s.TmpContext, reaction)
   239  }
   240  
   241  func (s *LayeredReactionStore) Delete(reaction *model.Reaction) (*model.Reaction, *model.AppError) {
   242  	return s.LayerChainHead.ReactionDelete(s.TmpContext, reaction)
   243  }
   244  
   245  func (s *LayeredReactionStore) GetForPost(postId string, allowFromCache bool) ([]*model.Reaction, *model.AppError) {
   246  	return s.LayerChainHead.ReactionGetForPost(s.TmpContext, postId)
   247  }
   248  
   249  func (s *LayeredReactionStore) BulkGetForPosts(postIds []string) ([]*model.Reaction, *model.AppError) {
   250  	return s.LayerChainHead.ReactionsBulkGetForPosts(s.TmpContext, postIds)
   251  }
   252  
   253  func (s *LayeredReactionStore) DeleteAllWithEmojiName(emojiName string) *model.AppError {
   254  	return s.LayerChainHead.ReactionDeleteAllWithEmojiName(s.TmpContext, emojiName)
   255  }
   256  
   257  func (s *LayeredReactionStore) PermanentDeleteBatch(endTime int64, limit int64) (int64, *model.AppError) {
   258  	return s.LayerChainHead.ReactionPermanentDeleteBatch(s.TmpContext, endTime, limit)
   259  }
   260  
   261  type LayeredRoleStore struct {
   262  	*LayeredStore
   263  }
   264  
   265  func (s *LayeredRoleStore) Save(role *model.Role) (*model.Role, *model.AppError) {
   266  	return s.LayerChainHead.RoleSave(s.TmpContext, role)
   267  }
   268  
   269  func (s *LayeredRoleStore) Get(roleId string) (*model.Role, *model.AppError) {
   270  	return s.LayerChainHead.RoleGet(s.TmpContext, roleId)
   271  }
   272  
   273  func (s *LayeredRoleStore) GetAll() ([]*model.Role, *model.AppError) {
   274  	return s.LayerChainHead.RoleGetAll(s.TmpContext)
   275  }
   276  
   277  func (s *LayeredRoleStore) GetByName(name string) (*model.Role, *model.AppError) {
   278  	return s.LayerChainHead.RoleGetByName(s.TmpContext, name)
   279  }
   280  
   281  func (s *LayeredRoleStore) GetByNames(names []string) ([]*model.Role, *model.AppError) {
   282  	return s.LayerChainHead.RoleGetByNames(s.TmpContext, names)
   283  }
   284  
   285  func (s *LayeredRoleStore) Delete(roldId string) (*model.Role, *model.AppError) {
   286  	return s.LayerChainHead.RoleDelete(s.TmpContext, roldId)
   287  }
   288  
   289  func (s *LayeredRoleStore) PermanentDeleteAll() *model.AppError {
   290  	return s.LayerChainHead.RolePermanentDeleteAll(s.TmpContext)
   291  }
   292  
   293  type LayeredSchemeStore struct {
   294  	*LayeredStore
   295  }
   296  
   297  func (s *LayeredSchemeStore) Save(scheme *model.Scheme) StoreChannel {
   298  	return s.RunQuery(func(supplier LayeredStoreSupplier) *LayeredStoreSupplierResult {
   299  		return supplier.SchemeSave(s.TmpContext, scheme)
   300  	})
   301  }
   302  
   303  func (s *LayeredSchemeStore) Get(schemeId string) StoreChannel {
   304  	return s.RunQuery(func(supplier LayeredStoreSupplier) *LayeredStoreSupplierResult {
   305  		return supplier.SchemeGet(s.TmpContext, schemeId)
   306  	})
   307  }
   308  
   309  func (s *LayeredSchemeStore) GetByName(schemeName string) StoreChannel {
   310  	return s.RunQuery(func(supplier LayeredStoreSupplier) *LayeredStoreSupplierResult {
   311  		return supplier.SchemeGetByName(s.TmpContext, schemeName)
   312  	})
   313  }
   314  
   315  func (s *LayeredSchemeStore) Delete(schemeId string) StoreChannel {
   316  	return s.RunQuery(func(supplier LayeredStoreSupplier) *LayeredStoreSupplierResult {
   317  		return supplier.SchemeDelete(s.TmpContext, schemeId)
   318  	})
   319  }
   320  
   321  func (s *LayeredSchemeStore) GetAllPage(scope string, offset int, limit int) StoreChannel {
   322  	return s.RunQuery(func(supplier LayeredStoreSupplier) *LayeredStoreSupplierResult {
   323  		return supplier.SchemeGetAllPage(s.TmpContext, scope, offset, limit)
   324  	})
   325  }
   326  
   327  func (s *LayeredSchemeStore) PermanentDeleteAll() StoreChannel {
   328  	return s.RunQuery(func(supplier LayeredStoreSupplier) *LayeredStoreSupplierResult {
   329  		return supplier.SchemePermanentDeleteAll(s.TmpContext)
   330  	})
   331  }