github.com/matrixorigin/matrixone@v0.7.0/pkg/frontend/export_test.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 frontend 16 17 import ( 18 "bufio" 19 "context" 20 "os" 21 "testing" 22 23 "github.com/matrixorigin/matrixone/pkg/common/moerr" 24 "github.com/matrixorigin/matrixone/pkg/container/types" 25 "github.com/matrixorigin/matrixone/pkg/defines" 26 "github.com/matrixorigin/matrixone/pkg/sql/parsers/tree" 27 "github.com/prashantv/gostub" 28 "github.com/smartystreets/goconvey/convey" 29 ) 30 31 var colName1, colName2 = "DATABASE()", "VARIABLE_VALUE" 32 33 func Test_initExportFileParam(t *testing.T) { 34 var oq = &outputQueue{ 35 mrs: &MysqlResultSet{}, 36 ep: &ExportParam{ 37 ExportParam: &tree.ExportParam{ 38 Lines: &tree.Lines{}, 39 Fields: &tree.Fields{}, 40 }, 41 }, 42 } 43 initExportFileParam(oq.ep, oq.mrs) 44 45 col1 := new(MysqlColumn) 46 col1.SetName(colName1) 47 col2 := new(MysqlColumn) 48 col2.SetName(colName2) 49 oq.mrs.AddColumn(col1) 50 oq.mrs.AddColumn(col2) 51 52 oq.ep.ForceQuote = append(oq.ep.ForceQuote, colName1) 53 oq.mrs.Name2Index[colName1] = 0 54 initExportFileParam(oq.ep, oq.mrs) 55 } 56 57 func Test_openNewFile(t *testing.T) { 58 convey.Convey("openNewFile failed", t, func() { 59 var oq = &outputQueue{ 60 mrs: &MysqlResultSet{}, 61 ep: &ExportParam{ 62 ExportParam: &tree.ExportParam{ 63 Lines: &tree.Lines{}, 64 Fields: &tree.Fields{}, 65 Header: true, 66 FilePath: "test/export.csv", 67 }, 68 }, 69 } 70 stubs := gostub.StubFunc(&OpenFile, nil, moerr.NewInternalError(context.TODO(), "can not open file")) 71 defer stubs.Reset() 72 convey.So(openNewFile(context.TODO(), oq.ep, oq.mrs), convey.ShouldNotBeNil) 73 }) 74 75 convey.Convey("openNewFile succ", t, func() { 76 var oq = &outputQueue{ 77 mrs: &MysqlResultSet{}, 78 ep: &ExportParam{ 79 ExportParam: &tree.ExportParam{ 80 Lines: &tree.Lines{}, 81 Fields: &tree.Fields{}, 82 Header: true, 83 FilePath: "test/export.csv", 84 }, 85 LineSize: 1, 86 }, 87 } 88 col1 := new(MysqlColumn) 89 col1.SetName(colName1) 90 col2 := new(MysqlColumn) 91 col2.SetName(colName2) 92 oq.mrs.AddColumn(col1) 93 oq.mrs.AddColumn(col2) 94 95 var file = &os.File{} 96 stubs := gostub.StubFunc(&OpenFile, file, nil) 97 defer stubs.Reset() 98 99 stubs = gostub.StubFunc(&writeDataToCSVFile, nil) 100 defer stubs.Reset() 101 102 convey.So(openNewFile(context.TODO(), oq.ep, oq.mrs), convey.ShouldBeNil) 103 }) 104 } 105 106 func Test_formatOutputString(t *testing.T) { 107 convey.Convey("openNewFile failed", t, func() { 108 var oq = &outputQueue{ 109 mrs: &MysqlResultSet{}, 110 ep: &ExportParam{ 111 ExportParam: &tree.ExportParam{ 112 Lines: &tree.Lines{}, 113 Fields: &tree.Fields{}, 114 Header: true, 115 FilePath: "test/export.csv", 116 }, 117 LineSize: 1, 118 }, 119 } 120 stubs := gostub.StubFunc(&writeDataToCSVFile, moerr.NewInternalError(context.TODO(), "write err")) 121 defer stubs.Reset() 122 convey.So(formatOutputString(oq, nil, nil, '\n', true), convey.ShouldNotBeNil) 123 124 stubs = gostub.StubFunc(&writeDataToCSVFile, nil) 125 defer stubs.Reset() 126 convey.So(formatOutputString(oq, nil, nil, '\n', true), convey.ShouldBeNil) 127 }) 128 } 129 130 func Test_writeToCSVFile(t *testing.T) { 131 convey.Convey("writeToCSVFile case", t, func() { 132 var oq = &outputQueue{ 133 mrs: &MysqlResultSet{}, 134 ep: &ExportParam{ 135 ExportParam: &tree.ExportParam{ 136 Lines: &tree.Lines{}, 137 Fields: &tree.Fields{}, 138 Header: true, 139 FilePath: "test/export.csv", 140 }, 141 LineSize: 1, 142 Writer: &bufio.Writer{}, 143 }, 144 } 145 var output = []byte{'1', '2'} 146 oq.ep.MaxFileSize = 1 147 148 convey.So(writeToCSVFile(oq, output), convey.ShouldNotBeNil) 149 150 oq.ep.Rows = 1 151 stubs := gostub.StubFunc(&Flush, moerr.NewInternalError(context.TODO(), "Flush error")) 152 defer stubs.Reset() 153 154 convey.So(writeToCSVFile(oq, output), convey.ShouldNotBeNil) 155 156 stubs = gostub.StubFunc(&Flush, nil) 157 defer stubs.Reset() 158 159 stubs = gostub.StubFunc(&Seek, int64(0), moerr.NewInternalError(context.TODO(), "Seek error")) 160 defer stubs.Reset() 161 convey.So(writeToCSVFile(oq, output), convey.ShouldNotBeNil) 162 163 stubs = gostub.StubFunc(&Seek, int64(0), nil) 164 defer stubs.Reset() 165 stubs = gostub.StubFunc(&Read, 0, moerr.NewInternalError(context.TODO(), "Read error")) 166 defer stubs.Reset() 167 convey.So(writeToCSVFile(oq, output), convey.ShouldNotBeNil) 168 169 stubs = gostub.StubFunc(&Read, 1, nil) 170 defer stubs.Reset() 171 172 stubs = gostub.StubFunc(&Truncate, moerr.NewInternalError(context.TODO(), "Truncate error")) 173 defer stubs.Reset() 174 convey.So(writeToCSVFile(oq, output), convey.ShouldNotBeNil) 175 176 stubs = gostub.StubFunc(&Truncate, nil) 177 defer stubs.Reset() 178 stubs = gostub.StubFunc(&Close, moerr.NewInternalError(context.TODO(), "Close error")) 179 defer stubs.Reset() 180 convey.So(writeToCSVFile(oq, output), convey.ShouldNotBeNil) 181 182 stubs = gostub.StubFunc(&Close, nil) 183 defer stubs.Reset() 184 stubs = gostub.StubFunc(&openNewFile, moerr.NewInternalError(context.TODO(), "openNewFile error")) 185 defer stubs.Reset() 186 convey.So(writeToCSVFile(oq, output), convey.ShouldNotBeNil) 187 188 stubs = gostub.StubFunc(&openNewFile, nil) 189 defer stubs.Reset() 190 stubs = gostub.StubFunc(&writeDataToCSVFile, moerr.NewInternalError(context.TODO(), "writeDataToCSVFile error")) 191 defer stubs.Reset() 192 convey.So(writeToCSVFile(oq, output), convey.ShouldNotBeNil) 193 194 stubs = gostub.StubFunc(&writeDataToCSVFile, nil) 195 defer stubs.Reset() 196 convey.So(writeToCSVFile(oq, output), convey.ShouldBeNil) 197 }) 198 } 199 200 func Test_writeDataToCSVFile(t *testing.T) { 201 convey.Convey("writeDataToCSVFile case", t, func() { 202 var oq = &outputQueue{ 203 mrs: &MysqlResultSet{}, 204 ep: &ExportParam{ 205 ExportParam: &tree.ExportParam{ 206 Lines: &tree.Lines{}, 207 Fields: &tree.Fields{}, 208 Header: true, 209 FilePath: "test/export.csv", 210 }, 211 LineSize: 1, 212 Writer: &bufio.Writer{}, 213 }, 214 } 215 var output = []byte{'1', '2'} 216 stubs := gostub.StubFunc(&Write, 0, moerr.NewInternalError(context.TODO(), "writeDataToCSVFile error")) 217 defer stubs.Reset() 218 219 convey.So(writeDataToCSVFile(oq.ep, output), convey.ShouldNotBeNil) 220 221 stubs = gostub.StubFunc(&Write, len(output), nil) 222 defer stubs.Reset() 223 convey.So(writeDataToCSVFile(oq.ep, output), convey.ShouldBeNil) 224 225 }) 226 } 227 228 func Test_exportDataToCSVFile(t *testing.T) { 229 convey.Convey("exportDataToCSVFile succ", t, func() { 230 var oq = &outputQueue{ 231 mrs: &MysqlResultSet{}, 232 ep: &ExportParam{ 233 ExportParam: &tree.ExportParam{ 234 Lines: &tree.Lines{}, 235 Fields: &tree.Fields{}, 236 Header: true, 237 FilePath: "test/export.csv", 238 }, 239 LineSize: 1, 240 Writer: &bufio.Writer{}, 241 }, 242 } 243 244 var col = make([]MysqlColumn, 13) 245 col[5].flag = 0 246 col[6].flag = 1 << 5 247 var colType = []defines.MysqlType{defines.MYSQL_TYPE_YEAR, defines.MYSQL_TYPE_YEAR, defines.MYSQL_TYPE_YEAR, defines.MYSQL_TYPE_SHORT, defines.MYSQL_TYPE_DOUBLE, 248 defines.MYSQL_TYPE_LONGLONG, defines.MYSQL_TYPE_LONGLONG, defines.MYSQL_TYPE_VARCHAR, defines.MYSQL_TYPE_DATE, defines.MYSQL_TYPE_DATETIME, 249 defines.MYSQL_TYPE_BOOL, defines.MYSQL_TYPE_DECIMAL, defines.MYSQL_TYPE_JSON} 250 for i := 0; i < len(col); i++ { 251 col[i].SetColumnType(colType[i]) 252 oq.mrs.AddColumn(&col[i]) 253 } 254 var data = make([]interface{}, len(col)) 255 data[1] = 0 256 data[2] = 1 257 data[3] = 1 258 data[4] = 1.0 259 data[5] = 1 260 data[6] = 1 261 data[7] = []byte{1} 262 data[8] = types.Date(1) 263 data[9] = "2022-02-28 23:59:59.9999" 264 data[10] = true 265 data[11] = 1.2 266 data[12], _ = types.ParseStringToByteJson(`{"a":1}`) 267 268 oq.mrs.AddRow(data) 269 270 oq.ep.Symbol = make([][]byte, len(col)) 271 oq.ep.ColumnFlag = make([]bool, len(col)) 272 273 stubs := gostub.StubFunc(&formatOutputString, nil) 274 defer stubs.Reset() 275 276 convey.So(exportDataToCSVFile(oq), convey.ShouldBeNil) 277 }) 278 279 convey.Convey("exportDataToCSVFile fail", t, func() { 280 var oq = &outputQueue{ 281 mrs: &MysqlResultSet{}, 282 ep: &ExportParam{ 283 ExportParam: &tree.ExportParam{ 284 Lines: &tree.Lines{}, 285 Fields: &tree.Fields{}, 286 Header: true, 287 FilePath: "test/export.csv", 288 }, 289 LineSize: 1, 290 Writer: &bufio.Writer{}, 291 }, 292 } 293 var col = make([]MysqlColumn, 1) 294 var colType = []defines.MysqlType{defines.MYSQL_TYPE_TIMESTAMP} 295 for i := 0; i < len(col); i++ { 296 col[i].SetColumnType(colType[i]) 297 oq.mrs.AddColumn(&col[i]) 298 } 299 300 var data = make([]interface{}, len(col)) 301 data[0] = 1 302 oq.mrs.AddRow(data) 303 oq.ep.Symbol = make([][]byte, len(col)) 304 oq.ep.ColumnFlag = make([]bool, len(col)) 305 306 stubs := gostub.StubFunc(&formatOutputString, nil) 307 defer stubs.Reset() 308 309 convey.So(exportDataToCSVFile(oq), convey.ShouldBeNil) 310 }) 311 }