github.com/MetalBlockchain/metalgo@v1.11.9/chains/atomic/gsharedmemory/shared_memory_server.go (about) 1 // Copyright (C) 2019-2024, Ava Labs, Inc. All rights reserved. 2 // See the file LICENSE for licensing terms. 3 4 package gsharedmemory 5 6 import ( 7 "context" 8 9 "github.com/MetalBlockchain/metalgo/chains/atomic" 10 "github.com/MetalBlockchain/metalgo/database" 11 "github.com/MetalBlockchain/metalgo/ids" 12 13 sharedmemorypb "github.com/MetalBlockchain/metalgo/proto/pb/sharedmemory" 14 ) 15 16 var _ sharedmemorypb.SharedMemoryServer = (*Server)(nil) 17 18 // Server is shared memory that is managed over RPC. 19 type Server struct { 20 sharedmemorypb.UnsafeSharedMemoryServer 21 sm atomic.SharedMemory 22 db database.Database 23 } 24 25 // NewServer returns shared memory connected to remote shared memory 26 func NewServer(sm atomic.SharedMemory, db database.Database) *Server { 27 return &Server{ 28 sm: sm, 29 db: db, 30 } 31 } 32 33 func (s *Server) Get( 34 _ context.Context, 35 req *sharedmemorypb.GetRequest, 36 ) (*sharedmemorypb.GetResponse, error) { 37 peerChainID, err := ids.ToID(req.PeerChainId) 38 if err != nil { 39 return nil, err 40 } 41 42 values, err := s.sm.Get(peerChainID, req.Keys) 43 return &sharedmemorypb.GetResponse{ 44 Values: values, 45 }, err 46 } 47 48 func (s *Server) Indexed( 49 _ context.Context, 50 req *sharedmemorypb.IndexedRequest, 51 ) (*sharedmemorypb.IndexedResponse, error) { 52 peerChainID, err := ids.ToID(req.PeerChainId) 53 if err != nil { 54 return nil, err 55 } 56 57 values, lastTrait, lastKey, err := s.sm.Indexed( 58 peerChainID, 59 req.Traits, 60 req.StartTrait, 61 req.StartKey, 62 int(req.Limit), 63 ) 64 return &sharedmemorypb.IndexedResponse{ 65 Values: values, 66 LastTrait: lastTrait, 67 LastKey: lastKey, 68 }, err 69 } 70 71 func (s *Server) Apply( 72 _ context.Context, 73 req *sharedmemorypb.ApplyRequest, 74 ) (*sharedmemorypb.ApplyResponse, error) { 75 requests := make(map[ids.ID]*atomic.Requests, len(req.Requests)) 76 for _, request := range req.Requests { 77 peerChainID, err := ids.ToID(request.PeerChainId) 78 if err != nil { 79 return nil, err 80 } 81 82 r := &atomic.Requests{ 83 RemoveRequests: request.RemoveRequests, 84 PutRequests: make([]*atomic.Element, len(request.PutRequests)), 85 } 86 for i, put := range request.PutRequests { 87 r.PutRequests[i] = &atomic.Element{ 88 Key: put.Key, 89 Value: put.Value, 90 Traits: put.Traits, 91 } 92 } 93 requests[peerChainID] = r 94 } 95 96 batches := make([]database.Batch, len(req.Batches)) 97 for i, reqBatch := range req.Batches { 98 batch := s.db.NewBatch() 99 for _, putReq := range reqBatch.Puts { 100 if err := batch.Put(putReq.Key, putReq.Value); err != nil { 101 return nil, err 102 } 103 } 104 for _, deleteReq := range reqBatch.Deletes { 105 if err := batch.Delete(deleteReq.Key); err != nil { 106 return nil, err 107 } 108 } 109 batches[i] = batch 110 } 111 return &sharedmemorypb.ApplyResponse{}, s.sm.Apply(requests, batches...) 112 }