github.com/matrixorigin/matrixone@v0.7.0/pkg/dnservice/replica.go (about) 1 // Copyright 2021 - 2022 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 dnservice 16 17 import ( 18 "context" 19 "sync" 20 21 "github.com/matrixorigin/matrixone/pkg/common/log" 22 "github.com/matrixorigin/matrixone/pkg/common/runtime" 23 "github.com/matrixorigin/matrixone/pkg/pb/metadata" 24 "github.com/matrixorigin/matrixone/pkg/pb/txn" 25 "github.com/matrixorigin/matrixone/pkg/txn/service" 26 "github.com/matrixorigin/matrixone/pkg/txn/util" 27 ) 28 29 // replica dn shard replica. 30 type replica struct { 31 rt runtime.Runtime 32 logger *log.MOLogger 33 shard metadata.DNShard 34 service service.TxnService 35 startedC chan struct{} 36 37 mu struct { 38 sync.RWMutex 39 starting bool 40 } 41 } 42 43 func newReplica(shard metadata.DNShard, rt runtime.Runtime) *replica { 44 return &replica{ 45 rt: rt, 46 shard: shard, 47 logger: rt.Logger().With(util.TxnDNShardField(shard)), 48 startedC: make(chan struct{}), 49 } 50 } 51 52 func (r *replica) start(txnService service.TxnService) error { 53 r.mu.Lock() 54 if r.mu.starting { 55 r.mu.Unlock() 56 return nil 57 } 58 r.mu.starting = true 59 r.mu.Unlock() 60 61 defer close(r.startedC) 62 r.service = txnService 63 return r.service.Start() 64 } 65 66 func (r *replica) close(destroy bool) error { 67 r.mu.RLock() 68 defer r.mu.RUnlock() 69 if !r.mu.starting { 70 return nil 71 } 72 r.waitStarted() 73 return r.service.Close(destroy) 74 } 75 76 func (r *replica) handleLocalRequest(ctx context.Context, request *txn.TxnRequest, response *txn.TxnResponse) error { 77 r.waitStarted() 78 prepareResponse(request, response) 79 80 switch request.Method { 81 case txn.TxnMethod_GetStatus: 82 return r.service.GetStatus(ctx, request, response) 83 case txn.TxnMethod_Prepare: 84 return r.service.Prepare(ctx, request, response) 85 case txn.TxnMethod_CommitDNShard: 86 return r.service.CommitDNShard(ctx, request, response) 87 case txn.TxnMethod_RollbackDNShard: 88 return r.service.RollbackDNShard(ctx, request, response) 89 default: 90 panic("cannot handle local CN request") 91 } 92 } 93 94 func (r *replica) waitStarted() { 95 <-r.startedC 96 }