github.com/matrixorigin/matrixone@v1.2.0/pkg/sql/colexec/window/window_test.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 window
    16  
    17  import (
    18  	"bytes"
    19  	"github.com/matrixorigin/matrixone/pkg/sql/colexec/aggexec"
    20  	"testing"
    21  
    22  	"github.com/matrixorigin/matrixone/pkg/common/mpool"
    23  	"github.com/matrixorigin/matrixone/pkg/vm"
    24  
    25  	"github.com/matrixorigin/matrixone/pkg/container/types"
    26  	"github.com/matrixorigin/matrixone/pkg/pb/plan"
    27  	"github.com/matrixorigin/matrixone/pkg/testutil"
    28  	"github.com/matrixorigin/matrixone/pkg/vm/process"
    29  )
    30  
    31  // add unit tests for cases
    32  type winTestCase struct {
    33  	arg  *Argument
    34  	flgs []bool // flgs[i] == true: nullable
    35  	proc *process.Process
    36  }
    37  
    38  var (
    39  	tcs []winTestCase
    40  )
    41  
    42  func init() {
    43  	tcs = []winTestCase{
    44  		newTestCase([]bool{false}, []types.Type{types.T_int8.ToType()}, []*plan.Expr{}, []aggexec.AggFuncExecExpression{
    45  			aggexec.MakeAggFunctionExpression(0, false, []*plan.Expr{newExpression(0)}, nil),
    46  		}),
    47  		newTestCase([]bool{false}, []types.Type{types.T_int8.ToType()}, []*plan.Expr{newExpression(0)}, []aggexec.AggFuncExecExpression{
    48  			aggexec.MakeAggFunctionExpression(0, false, []*plan.Expr{newExpression(0)}, nil),
    49  		}),
    50  		newTestCase([]bool{false, true, false, true}, []types.Type{
    51  			types.T_int8.ToType(),
    52  			types.T_int16.ToType(),
    53  		}, []*plan.Expr{newExpression(0), newExpression(1)}, []aggexec.AggFuncExecExpression{
    54  			aggexec.MakeAggFunctionExpression(0, false, []*plan.Expr{newExpression(0)}, nil),
    55  		}),
    56  		newTestCase([]bool{false, true, false, true}, []types.Type{
    57  			types.T_int8.ToType(),
    58  			types.T_int16.ToType(),
    59  			types.T_int32.ToType(),
    60  			types.T_int64.ToType(),
    61  		}, []*plan.Expr{newExpression(0), newExpression(3)}, []aggexec.AggFuncExecExpression{
    62  			aggexec.MakeAggFunctionExpression(0, false, []*plan.Expr{newExpression(0)}, nil),
    63  		}),
    64  		newTestCase([]bool{false, true, false, true}, []types.Type{
    65  			types.T_int64.ToType(),
    66  			types.T_int64.ToType(),
    67  			types.T_int64.ToType(),
    68  			types.T_decimal128.ToType(),
    69  		}, []*plan.Expr{newExpression(1), newExpression(3)}, []aggexec.AggFuncExecExpression{
    70  			aggexec.MakeAggFunctionExpression(0, false, []*plan.Expr{newExpression(0)}, nil),
    71  		}),
    72  		newTestCase([]bool{false, true, false, true}, []types.Type{
    73  			types.T_int64.ToType(),
    74  			types.T_int64.ToType(),
    75  			types.T_int64.ToType(),
    76  			types.T_decimal128.ToType(),
    77  		}, []*plan.Expr{newExpression(1), newExpression(2), newExpression(3)}, []aggexec.AggFuncExecExpression{
    78  			aggexec.MakeAggFunctionExpression(0, false, []*plan.Expr{newExpression(0)}, nil),
    79  		}),
    80  		newTestCase([]bool{false, true, false, true}, []types.Type{
    81  			types.T_int64.ToType(),
    82  			types.T_int64.ToType(),
    83  			types.New(types.T_varchar, 2, 0),
    84  			types.T_decimal128.ToType(),
    85  		}, []*plan.Expr{newExpression(1), newExpression(2), newExpression(3)}, []aggexec.AggFuncExecExpression{
    86  			aggexec.MakeAggFunctionExpression(0, false, []*plan.Expr{newExpression(0)}, nil),
    87  		}),
    88  		newTestCase([]bool{false, true, false, true}, []types.Type{
    89  			types.T_int64.ToType(),
    90  			types.T_int64.ToType(),
    91  			types.T_varchar.ToType(),
    92  			types.T_decimal128.ToType(),
    93  		}, []*plan.Expr{newExpression(1), newExpression(2), newExpression(3)}, []aggexec.AggFuncExecExpression{
    94  			aggexec.MakeAggFunctionExpression(0, false, []*plan.Expr{newExpression(0)}, nil),
    95  		}),
    96  	}
    97  }
    98  
    99  func TestString(t *testing.T) {
   100  	buf := new(bytes.Buffer)
   101  	for _, tc := range tcs {
   102  		tc.arg.String(buf)
   103  	}
   104  }
   105  
   106  func newTestCase(flgs []bool, ts []types.Type, exprs []*plan.Expr, aggs []aggexec.AggFuncExecExpression) winTestCase {
   107  	for _, expr := range exprs {
   108  		if col, ok := expr.Expr.(*plan.Expr_Col); ok {
   109  			idx := col.Col.ColPos
   110  			expr.Typ = plan.Type{
   111  				Id:    int32(ts[idx].Oid),
   112  				Width: ts[idx].Width,
   113  				Scale: ts[idx].Scale,
   114  			}
   115  		}
   116  	}
   117  	return winTestCase{
   118  		flgs: flgs,
   119  		proc: testutil.NewProcessWithMPool(mpool.MustNewZero()),
   120  		arg: &Argument{
   121  			WinSpecList: exprs,
   122  			Types:       ts,
   123  			Aggs:        aggs,
   124  			OperatorBase: vm.OperatorBase{
   125  				OperatorInfo: vm.OperatorInfo{
   126  					Idx:     0,
   127  					IsFirst: false,
   128  					IsLast:  false,
   129  				},
   130  			},
   131  		},
   132  	}
   133  }
   134  
   135  func newExpression(pos int32) *plan.Expr {
   136  	return &plan.Expr{
   137  		Typ: plan.Type{},
   138  		Expr: &plan.Expr_Col{
   139  			Col: &plan.ColRef{
   140  				ColPos: pos,
   141  			},
   142  		},
   143  	}
   144  }
   145  
   146  // create a new block based on the type information, flgs[i] == ture: has null
   147  // func newBatch(ts []types.Type, proc *process.Process, rows int64) *batch.Batch {
   148  // 	return testutil.NewBatch(ts, false, int(rows), proc.Mp())
   149  // }
   150  
   151  // func cleanResult(result *vm.CallResult, proc *process.Process) {
   152  // 	if result.Batch != nil {
   153  // 		result.Batch.Clean(proc.Mp())
   154  // 		result.Batch = nil
   155  // 	}
   156  // }