123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394 |
- package sql
- import (
- "git.sxidc.com/go-framework/baize/framework/core/infrastructure/logger"
- "git.sxidc.com/go-framework/baize/framework/core/tag/sql/sql_result"
- "git.sxidc.com/go-tools/utils/reflectutils"
- "git.sxidc.com/go-tools/utils/strutils"
- "github.com/pkg/errors"
- "reflect"
- "strings"
- "time"
- )
- const (
- resultTimeMicroFormat = "2006-01-02T15:04:05.000000+08:00"
- resultTimeMilliFormat = "2006-01-02T15:04:05.000+08:00"
- resultTimeSecFormat = "2006-01-02T15:04:05+08:00"
- )
- // Result 查询结果
- type Result map[string]any
- // ColumnValueTime 以time.Time类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - time.Time类型的列值
- func (result Result) ColumnValueTime(columnName string) time.Time {
- value, ok := result[columnName].(string)
- if !ok {
- value, ok := result[columnName].(time.Time)
- if !ok {
- logger.GetInstance().Error(errors.New("无法转换为时间类型"))
- return time.Time{}
- }
- return value
- }
- layout := resultTimeSecFormat
- parseValue := value
- timeZoneIndex := strings.LastIndex(value, "+08:")
- if timeZoneIndex != -1 {
- parseValue = parseValue[:timeZoneIndex]
- afterSecondIndex := strings.LastIndex(parseValue, ".")
- if afterSecondIndex != -1 {
- if len(value)-afterSecondIndex-1 == 6 {
- layout = resultTimeMicroFormat
- } else if len(value)-afterSecondIndex-1 == 3 {
- layout = resultTimeMilliFormat
- }
- }
- }
- t, err := time.ParseInLocation(layout, value, time.Local)
- if err != nil {
- return time.Time{}
- }
- return t
- }
- // ColumnValueBool 以bool类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - bool类型的列值
- func (result Result) ColumnValueBool(columnName string) bool {
- value, err := reflectutils.ToBool(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return false
- }
- return value
- }
- // ColumnValueString 以string类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - string类型的列值
- func (result Result) ColumnValueString(columnName string) string {
- value, err := reflectutils.ToString(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return ""
- }
- return value
- }
- // ColumnValueInt 以int类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - int类型的列值
- func (result Result) ColumnValueInt(columnName string) int {
- value, err := reflectutils.ToInt64(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return 0
- }
- return int(value)
- }
- // ColumnValueInt8 以int8类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - int8类型的列值
- func (result Result) ColumnValueInt8(columnName string) int8 {
- value, err := reflectutils.ToInt64(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return 0
- }
- return int8(value)
- }
- // ColumnValueInt16 以int16类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - int16类型的列值
- func (result Result) ColumnValueInt16(columnName string) int16 {
- value, err := reflectutils.ToInt64(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return 0
- }
- return int16(value)
- }
- // ColumnValueInt32 以int32类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - int32类型的列值
- func (result Result) ColumnValueInt32(columnName string) int32 {
- value, err := reflectutils.ToInt64(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return 0
- }
- return int32(value)
- }
- // ColumnValueInt64 以int64类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - int64类型的列值
- func (result Result) ColumnValueInt64(columnName string) int64 {
- value, err := reflectutils.ToInt64(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return 0
- }
- return value
- }
- // ColumnValueUint 以uint类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - uint类型的列值
- func (result Result) ColumnValueUint(columnName string) uint {
- value, err := reflectutils.ToUint64(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return 0
- }
- return uint(value)
- }
- // ColumnValueUint8 以uint8类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - uint8类型的列值
- func (result Result) ColumnValueUint8(columnName string) uint8 {
- value, err := reflectutils.ToUint64(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return 0
- }
- return uint8(value)
- }
- // ColumnValueUint16 以uint16类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - uint16类型的列值
- func (result Result) ColumnValueUint16(columnName string) uint16 {
- value, err := reflectutils.ToUint64(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return 0
- }
- return uint16(value)
- }
- // ColumnValueUint32 以uint32类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - uint32类型的列值
- func (result Result) ColumnValueUint32(columnName string) uint32 {
- value, err := reflectutils.ToUint64(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return 0
- }
- return uint32(value)
- }
- // ColumnValueUint64 以uint64类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - uint64类型的列值
- func (result Result) ColumnValueUint64(columnName string) uint64 {
- value, err := reflectutils.ToUint64(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return 0
- }
- return value
- }
- // ColumnValueFloat32 以float32类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - float32类型的列值
- func (result Result) ColumnValueFloat32(columnName string) float32 {
- value, err := reflectutils.ToFloat64(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return 0
- }
- return float32(value)
- }
- // ColumnValueFloat64 以float64类型获取列值
- // 参数:
- // - columnName: 列名
- // 返回值:
- // - float64类型的列值
- func (result Result) ColumnValueFloat64(columnName string) float64 {
- value, err := reflectutils.ToFloat64(result[columnName])
- if err != nil {
- logger.GetInstance().Error(err)
- return 0
- }
- return value
- }
- // ParseSqlResult 解析查询结果
- // 参数:
- // - input: sql.Result或者[]sql.Result类型的查询结果
- // - output: 接收查询结果的指针,如果是结构,需要使用sqlresult tag标注字段
- // 返回值:
- // - 错误
- func ParseSqlResult(input any, output any) error {
- return ParseSqlResultWithColumn(input, output, "")
- }
- // ParseSqlResultWithColumn 取查询结果列解析结果
- // 参数:
- // - input: sql.Result或者[]sql.Result类型的查询结果
- // - output: 接收查询结果的指针,如果是结构,需要使用sqlresult tag标注字段
- // - columnName: 获取的列名
- // 返回值:
- // - 错误
- func ParseSqlResultWithColumn(input any, output any, columnName string) error {
- if input == nil {
- return nil
- }
- if output == nil {
- return nil
- }
- typeCheckErr := errors.New("可以接受的输出类型为指针或者slice的指针")
- outputType := reflect.TypeOf(output)
- if outputType.Kind() != reflect.Pointer {
- return typeCheckErr
- }
- outputElemType := reflectutils.PointerTypeElem(outputType)
- // 输出不是slice,直接用result赋值即可
- if outputElemType.Kind() != reflect.Slice {
- result, ok := input.(Result)
- if !ok {
- return errors.New("输出不是slice,输入需要是sql.Result")
- }
- return parseSqlSingle(result, output, columnName)
- }
- // 输出是slice,需要遍历处理
- results, ok := input.([]Result)
- if !ok {
- return errors.New("输出是slice,输入需要是[]sql.Result")
- }
- outputEntities := reflect.MakeSlice(outputElemType, 0, 0)
- for _, result := range results {
- var outputEntityValue reflect.Value
- // slice子类型判断
- if outputElemType.Elem().Kind() == reflect.Pointer {
- outputEntityValue = reflect.New(outputElemType.Elem().Elem())
- err := parseSqlSingle(result, outputEntityValue.Interface(), columnName)
- if err != nil {
- return err
- }
- } else {
- outputEntityValue = reflect.New(outputElemType.Elem()).Elem()
- err := parseSqlSingle(result, outputEntityValue.Addr().Interface(), columnName)
- if err != nil {
- return err
- }
- }
- outputEntities = reflect.Append(outputEntities, outputEntityValue)
- }
- outputElemValue := reflectutils.PointerValueElem(reflect.ValueOf(output))
- outputElemValue.Set(outputEntities)
- return nil
- }
- func parseSqlSingle(result Result, output any, columnName string) error {
- outputValue := reflectutils.PointerValueElem(reflect.ValueOf(output))
- outputKind := reflectutils.GroupValueKind(outputValue)
- var oneResultValue any
- if strutils.IsStringEmpty(columnName) {
- for _, value := range result {
- oneResultValue = value
- break
- }
- } else {
- value, ok := result[columnName]
- if !ok {
- return errors.New("列不存在")
- }
- oneResultValue = value
- }
- switch outputKind {
- case reflect.String:
- return reflectutils.AssignStringValue(oneResultValue, outputValue)
- case reflect.Bool:
- return reflectutils.AssignBoolValue(oneResultValue, outputValue)
- case reflect.Int64:
- return reflectutils.AssignInt64Value(oneResultValue, outputValue)
- case reflect.Uint64:
- return reflectutils.AssignUint64Value(oneResultValue, outputValue)
- case reflect.Float64:
- return reflectutils.AssignFloat64Value(oneResultValue, outputValue)
- case reflect.Struct:
- if outputValue.Type().Name() == "time.Time" {
- return errors.New("不支持转换到time.Time,请使用Result.ColumnValueStringAsTime")
- }
- return sql_result.DefaultUsage(result, output, columnName)
- default:
- return errors.New("不支持的类型")
- }
- }
|