github.com/matrixorigin/matrixone@v0.7.0/pkg/vm/engine/tae/wal/driver.go (about)

     1  // Copyright 2021 Matrix Origin
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //      http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  package wal
    16  
    17  import (
    18  	"context"
    19  	"sync"
    20  	"time"
    21  
    22  	"github.com/matrixorigin/matrixone/pkg/vm/engine/tae/logstore/driver/batchstoredriver"
    23  	"github.com/matrixorigin/matrixone/pkg/vm/engine/tae/logstore/driver/logservicedriver"
    24  	"github.com/matrixorigin/matrixone/pkg/vm/engine/tae/logstore/entry"
    25  	"github.com/matrixorigin/matrixone/pkg/vm/engine/tae/logstore/sm"
    26  	"github.com/matrixorigin/matrixone/pkg/vm/engine/tae/logstore/store"
    27  )
    28  
    29  type entryWithInfo struct {
    30  	e    LogEntry
    31  	info any
    32  }
    33  
    34  type DriverConfig struct {
    35  	BatchStoreConfig   *batchstoredriver.StoreCfg
    36  	CheckpointDuration time.Duration
    37  }
    38  
    39  type walDriver struct {
    40  	*walInfo
    41  	sync.RWMutex
    42  	impl store.Store
    43  	own  bool
    44  
    45  	logInfoQueue sm.Queue
    46  
    47  	ckpDuration   time.Duration
    48  	cancelfn      context.CancelFunc
    49  	cancelContext context.Context
    50  	wg            sync.WaitGroup
    51  }
    52  
    53  func NewDriverWithLogservice(factory logservicedriver.LogServiceClientFactory) Driver {
    54  	ckpDuration := time.Second * 5
    55  	impl := store.NewStoreWithLogserviceDriver(factory)
    56  	driver := NewDriverWithStore(impl, true, ckpDuration)
    57  	return driver
    58  }
    59  
    60  func NewDriverWithBatchStore(dir, name string, cfg *DriverConfig) Driver {
    61  	var batchStoreCfg *batchstoredriver.StoreCfg
    62  	ckpDuration := time.Second * 5
    63  	if cfg != nil {
    64  		batchStoreCfg = cfg.BatchStoreConfig
    65  		ckpDuration = cfg.CheckpointDuration
    66  	}
    67  	impl := store.NewStoreWithBatchStoreDriver(dir, name, batchStoreCfg)
    68  	driver := NewDriverWithStore(impl, true, ckpDuration)
    69  	return driver
    70  }
    71  
    72  func NewDriverWithStore(impl store.Store, own bool, ckpDuration time.Duration) Driver {
    73  	if ckpDuration == 0 {
    74  		ckpDuration = time.Second
    75  	}
    76  	driver := &walDriver{
    77  		walInfo:     newWalInfo(),
    78  		impl:        impl,
    79  		own:         own,
    80  		wg:          sync.WaitGroup{},
    81  		ckpDuration: ckpDuration,
    82  	}
    83  	driver.logInfoQueue = sm.NewSafeQueue(1000, 1000, driver.onLogInfo)
    84  	driver.cancelContext, driver.cancelfn = context.WithCancel(context.Background())
    85  	driver.logInfoQueue.Start()
    86  	driver.wg.Add(1)
    87  	return driver
    88  }
    89  func (driver *walDriver) Start() {
    90  	go driver.checkpointTicker()
    91  }
    92  func (driver *walDriver) GetCheckpointed() uint64 {
    93  	return driver.impl.GetCheckpointed(GroupPrepare)
    94  }
    95  func (driver *walDriver) replayhandle(handle store.ApplyHandle) store.ApplyHandle {
    96  	return func(group uint32, commitId uint64, payload []byte, typ uint16, info any) {
    97  		driver.logEntry(info.(*entry.Info))
    98  		handle(group, commitId, payload, typ, nil)
    99  	}
   100  }
   101  func (driver *walDriver) Replay(handle store.ApplyHandle) error {
   102  	return driver.impl.Replay(driver.replayhandle(handle))
   103  }
   104  
   105  func (driver *walDriver) GetPenddingCnt() uint64 {
   106  	return driver.impl.GetPendding(GroupPrepare)
   107  }
   108  
   109  func (driver *walDriver) GetCurrSeqNum() uint64 {
   110  	return driver.impl.GetCurrSeqNum(GroupPrepare)
   111  }
   112  
   113  func (driver *walDriver) LoadEntry(groupID uint32, lsn uint64) (LogEntry, error) {
   114  	return driver.impl.Load(groupID, lsn)
   115  }
   116  
   117  func (driver *walDriver) AppendEntry(group uint32, e LogEntry) (uint64, error) {
   118  	id, err := driver.impl.Append(group, e)
   119  	ent := &entryWithInfo{
   120  		e:    e,
   121  		info: e.GetInfo(),
   122  	}
   123  	_, err2 := driver.logInfoQueue.Enqueue(ent)
   124  	if err2 != nil {
   125  		panic(err)
   126  	}
   127  	return id, err
   128  }
   129  
   130  func (driver *walDriver) Close() error {
   131  	driver.cancelfn()
   132  	driver.logInfoQueue.Stop()
   133  	if driver.own {
   134  		return driver.impl.Close()
   135  	}
   136  	driver.wg.Wait()
   137  	return nil
   138  }