github.com/matrixorigin/matrixone@v0.7.0/pkg/txn/storage/memorystorage/read.go (about)

     1  // Copyright 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 memorystorage
    16  
    17  import (
    18  	"bytes"
    19  	"context"
    20  	"encoding/gob"
    21  	"io"
    22  
    23  	"github.com/matrixorigin/matrixone/pkg/pb/txn"
    24  	"github.com/matrixorigin/matrixone/pkg/txn/storage"
    25  	"github.com/matrixorigin/matrixone/pkg/vm/engine/memoryengine"
    26  )
    27  
    28  func (s *Storage) Read(ctx context.Context, txnMeta txn.TxnMeta, op uint32, payload []byte) (res storage.ReadResult, err error) {
    29  
    30  	switch op {
    31  
    32  	case memoryengine.OpOpenDatabase:
    33  		return handleRead(
    34  			ctx, txnMeta, payload,
    35  			s.handler.HandleOpenDatabase,
    36  		)
    37  
    38  	case memoryengine.OpGetDatabases:
    39  		return handleRead(
    40  			ctx, txnMeta, payload,
    41  			s.handler.HandleGetDatabases,
    42  		)
    43  
    44  	case memoryengine.OpOpenRelation:
    45  		return handleRead(
    46  			ctx, txnMeta, payload,
    47  			s.handler.HandleOpenRelation,
    48  		)
    49  
    50  	case memoryengine.OpGetRelations:
    51  		return handleRead(
    52  			ctx, txnMeta, payload,
    53  			s.handler.HandleGetRelations,
    54  		)
    55  
    56  	case memoryengine.OpGetPrimaryKeys:
    57  		return handleRead(
    58  			ctx, txnMeta, payload,
    59  			s.handler.HandleGetPrimaryKeys,
    60  		)
    61  
    62  	case memoryengine.OpGetTableDefs:
    63  		return handleRead(
    64  			ctx, txnMeta, payload,
    65  			s.handler.HandleGetTableDefs,
    66  		)
    67  
    68  	case memoryengine.OpGetHiddenKeys:
    69  		return handleRead(
    70  			ctx, txnMeta, payload,
    71  			s.handler.HandleGetHiddenKeys,
    72  		)
    73  
    74  	case memoryengine.OpNewTableIter:
    75  		return handleRead(
    76  			ctx, txnMeta, payload,
    77  			s.handler.HandleNewTableIter,
    78  		)
    79  
    80  	case memoryengine.OpRead:
    81  		return handleRead(
    82  			ctx, txnMeta, payload,
    83  			s.handler.HandleRead,
    84  		)
    85  
    86  	case memoryengine.OpCloseTableIter:
    87  		return handleRead(
    88  			ctx, txnMeta, payload,
    89  			s.handler.HandleCloseTableIter,
    90  		)
    91  
    92  	case memoryengine.OpTableStats:
    93  		return handleRead(
    94  			ctx, txnMeta, payload,
    95  			s.handler.HandleTableStats,
    96  		)
    97  
    98  	case memoryengine.OpGetTableColumns:
    99  		return handleRead(
   100  			ctx, txnMeta, payload,
   101  			s.handler.HandleGetTableColumns,
   102  		)
   103  
   104  	}
   105  
   106  	return
   107  }
   108  
   109  func handleRead[Req any, Resp any](
   110  	ctx context.Context,
   111  	txnMeta txn.TxnMeta,
   112  	payload []byte,
   113  	fn func(
   114  		ctx context.Context,
   115  		meta txn.TxnMeta,
   116  		req Req,
   117  		resp *Resp,
   118  	) (
   119  		err error,
   120  	),
   121  ) (
   122  	res storage.ReadResult,
   123  	err error,
   124  ) {
   125  
   126  	var req Req
   127  	if err := gob.NewDecoder(bytes.NewReader(payload)).Decode(&req); err != nil {
   128  		return nil, err
   129  	}
   130  
   131  	var resp Resp
   132  	defer logReq("read", req, txnMeta, &resp, &err)()
   133  	defer func() {
   134  		if closer, ok := (any)(resp).(io.Closer); ok {
   135  			_ = closer.Close()
   136  		}
   137  	}()
   138  
   139  	err = fn(ctx, txnMeta, req, &resp)
   140  	if err != nil {
   141  		return nil, err
   142  	}
   143  
   144  	buf := new(bytes.Buffer)
   145  	if err := gob.NewEncoder(buf).Encode(resp); err != nil {
   146  		return nil, err
   147  	}
   148  	res = &readResult{
   149  		payload: buf.Bytes(),
   150  	}
   151  
   152  	return res, nil
   153  }