github.com/gogf/gf@v1.16.9/database/gdb/gdb_z_mysql_struct_test.go (about)

     1  // Copyright GoFrame Author(https://goframe.org). All Rights Reserved.
     2  //
     3  // This Source Code Form is subject to the terms of the MIT License.
     4  // If a copy of the MIT was not distributed with this file,
     5  // You can obtain one at https://github.com/gogf/gf.
     6  
     7  package gdb_test
     8  
     9  import (
    10  	"database/sql"
    11  	"github.com/gogf/gf/database/gdb"
    12  	"github.com/gogf/gf/errors/gcode"
    13  	"github.com/gogf/gf/errors/gerror"
    14  	"github.com/gogf/gf/frame/g"
    15  	"github.com/gogf/gf/os/gtime"
    16  	"github.com/gogf/gf/test/gtest"
    17  	"github.com/gogf/gf/util/gconv"
    18  	"reflect"
    19  	"testing"
    20  )
    21  
    22  func Test_Model_Embedded_Insert(t *testing.T) {
    23  	table := createTable()
    24  	defer dropTable(table)
    25  
    26  	gtest.C(t, func(t *gtest.T) {
    27  		type Base struct {
    28  			Id         int    `json:"id"`
    29  			Uid        int    `json:"uid"`
    30  			CreateTime string `json:"create_time"`
    31  		}
    32  		type User struct {
    33  			Base
    34  			Passport string `json:"passport"`
    35  			Password string `json:"password"`
    36  			Nickname string `json:"nickname"`
    37  		}
    38  		result, err := db.Model(table).Data(User{
    39  			Passport: "john-test",
    40  			Password: "123456",
    41  			Nickname: "John",
    42  			Base: Base{
    43  				Id:         100,
    44  				Uid:        100,
    45  				CreateTime: gtime.Now().String(),
    46  			},
    47  		}).Insert()
    48  		t.AssertNil(err)
    49  		n, _ := result.RowsAffected()
    50  		t.Assert(n, 1)
    51  		value, err := db.Model(table).Fields("passport").Where("id=100").Value()
    52  		t.AssertNil(err)
    53  		t.Assert(value.String(), "john-test")
    54  	})
    55  }
    56  
    57  func Test_Model_Embedded_MapToStruct(t *testing.T) {
    58  	table := createTable()
    59  	defer dropTable(table)
    60  
    61  	gtest.C(t, func(t *gtest.T) {
    62  		type Ids struct {
    63  			Id  int `json:"id"`
    64  			Uid int `json:"uid"`
    65  		}
    66  		type Base struct {
    67  			Ids
    68  			CreateTime string `json:"create_time"`
    69  		}
    70  		type User struct {
    71  			Base
    72  			Passport string `json:"passport"`
    73  			Password string `json:"password"`
    74  			Nickname string `json:"nickname"`
    75  		}
    76  		data := g.Map{
    77  			"id":          100,
    78  			"uid":         101,
    79  			"passport":    "t1",
    80  			"password":    "123456",
    81  			"nickname":    "T1",
    82  			"create_time": gtime.Now().String(),
    83  		}
    84  		result, err := db.Model(table).Data(data).Insert()
    85  		t.AssertNil(err)
    86  		n, _ := result.RowsAffected()
    87  		t.Assert(n, 1)
    88  
    89  		one, err := db.Model(table).Where("id=100").One()
    90  		t.AssertNil(err)
    91  
    92  		user := new(User)
    93  
    94  		t.Assert(one.Struct(user), nil)
    95  		t.Assert(user.Id, data["id"])
    96  		t.Assert(user.Passport, data["passport"])
    97  		t.Assert(user.Password, data["password"])
    98  		t.Assert(user.Nickname, data["nickname"])
    99  		t.Assert(user.CreateTime, data["create_time"])
   100  
   101  	})
   102  }
   103  
   104  func Test_Struct_Pointer_Attribute(t *testing.T) {
   105  	table := createInitTable()
   106  	defer dropTable(table)
   107  
   108  	type User struct {
   109  		Id       *int
   110  		Passport *string
   111  		Password *string
   112  		Nickname string
   113  	}
   114  
   115  	gtest.C(t, func(t *gtest.T) {
   116  		one, err := db.Model(table).FindOne(1)
   117  		t.AssertNil(err)
   118  		user := new(User)
   119  		err = one.Struct(user)
   120  		t.AssertNil(err)
   121  		t.Assert(*user.Id, 1)
   122  		t.Assert(*user.Passport, "user_1")
   123  		t.Assert(*user.Password, "pass_1")
   124  		t.Assert(user.Nickname, "name_1")
   125  	})
   126  	gtest.C(t, func(t *gtest.T) {
   127  		user := new(User)
   128  		err := db.Model(table).Scan(user, "id=1")
   129  		t.AssertNil(err)
   130  		t.Assert(*user.Id, 1)
   131  		t.Assert(*user.Passport, "user_1")
   132  		t.Assert(*user.Password, "pass_1")
   133  		t.Assert(user.Nickname, "name_1")
   134  	})
   135  	gtest.C(t, func(t *gtest.T) {
   136  		var user *User
   137  		err := db.Model(table).Scan(&user, "id=1")
   138  		t.AssertNil(err)
   139  		t.Assert(*user.Id, 1)
   140  		t.Assert(*user.Passport, "user_1")
   141  		t.Assert(*user.Password, "pass_1")
   142  		t.Assert(user.Nickname, "name_1")
   143  	})
   144  }
   145  
   146  func Test_Structs_Pointer_Attribute(t *testing.T) {
   147  	table := createInitTable()
   148  	defer dropTable(table)
   149  
   150  	type User struct {
   151  		Id       *int
   152  		Passport *string
   153  		Password *string
   154  		Nickname string
   155  	}
   156  	// All
   157  	gtest.C(t, func(t *gtest.T) {
   158  		one, err := db.Model(table).All("id < 3")
   159  		t.AssertNil(err)
   160  		users := make([]User, 0)
   161  		err = one.Structs(&users)
   162  		t.AssertNil(err)
   163  		t.Assert(len(users), 2)
   164  		t.Assert(*users[0].Id, 1)
   165  		t.Assert(*users[0].Passport, "user_1")
   166  		t.Assert(*users[0].Password, "pass_1")
   167  		t.Assert(users[0].Nickname, "name_1")
   168  	})
   169  	gtest.C(t, func(t *gtest.T) {
   170  		one, err := db.Model(table).All("id < 3")
   171  		t.AssertNil(err)
   172  		users := make([]*User, 0)
   173  		err = one.Structs(&users)
   174  		t.AssertNil(err)
   175  		t.Assert(len(users), 2)
   176  		t.Assert(*users[0].Id, 1)
   177  		t.Assert(*users[0].Passport, "user_1")
   178  		t.Assert(*users[0].Password, "pass_1")
   179  		t.Assert(users[0].Nickname, "name_1")
   180  	})
   181  	gtest.C(t, func(t *gtest.T) {
   182  		var users []User
   183  		one, err := db.Model(table).All("id < 3")
   184  		t.AssertNil(err)
   185  		err = one.Structs(&users)
   186  		t.AssertNil(err)
   187  		t.Assert(len(users), 2)
   188  		t.Assert(*users[0].Id, 1)
   189  		t.Assert(*users[0].Passport, "user_1")
   190  		t.Assert(*users[0].Password, "pass_1")
   191  		t.Assert(users[0].Nickname, "name_1")
   192  	})
   193  	gtest.C(t, func(t *gtest.T) {
   194  		var users []*User
   195  		one, err := db.Model(table).All("id < 3")
   196  		t.AssertNil(err)
   197  		err = one.Structs(&users)
   198  		t.AssertNil(err)
   199  		t.Assert(len(users), 2)
   200  		t.Assert(*users[0].Id, 1)
   201  		t.Assert(*users[0].Passport, "user_1")
   202  		t.Assert(*users[0].Password, "pass_1")
   203  		t.Assert(users[0].Nickname, "name_1")
   204  	})
   205  	// Structs
   206  	gtest.C(t, func(t *gtest.T) {
   207  		users := make([]User, 0)
   208  		err := db.Model(table).Scan(&users, "id < 3")
   209  		t.AssertNil(err)
   210  		t.Assert(len(users), 2)
   211  		t.Assert(*users[0].Id, 1)
   212  		t.Assert(*users[0].Passport, "user_1")
   213  		t.Assert(*users[0].Password, "pass_1")
   214  		t.Assert(users[0].Nickname, "name_1")
   215  	})
   216  	gtest.C(t, func(t *gtest.T) {
   217  		users := make([]*User, 0)
   218  		err := db.Model(table).Scan(&users, "id < 3")
   219  		t.AssertNil(err)
   220  		t.Assert(len(users), 2)
   221  		t.Assert(*users[0].Id, 1)
   222  		t.Assert(*users[0].Passport, "user_1")
   223  		t.Assert(*users[0].Password, "pass_1")
   224  		t.Assert(users[0].Nickname, "name_1")
   225  	})
   226  	gtest.C(t, func(t *gtest.T) {
   227  		var users []User
   228  		err := db.Model(table).Scan(&users, "id < 3")
   229  		t.AssertNil(err)
   230  		t.Assert(len(users), 2)
   231  		t.Assert(*users[0].Id, 1)
   232  		t.Assert(*users[0].Passport, "user_1")
   233  		t.Assert(*users[0].Password, "pass_1")
   234  		t.Assert(users[0].Nickname, "name_1")
   235  	})
   236  	gtest.C(t, func(t *gtest.T) {
   237  		var users []*User
   238  		err := db.Model(table).Scan(&users, "id < 3")
   239  		t.AssertNil(err)
   240  		t.Assert(len(users), 2)
   241  		t.Assert(*users[0].Id, 1)
   242  		t.Assert(*users[0].Passport, "user_1")
   243  		t.Assert(*users[0].Password, "pass_1")
   244  		t.Assert(users[0].Nickname, "name_1")
   245  	})
   246  }
   247  
   248  func Test_Struct_Empty(t *testing.T) {
   249  	table := createTable()
   250  	defer dropTable(table)
   251  
   252  	type User struct {
   253  		Id       int
   254  		Passport string
   255  		Password string
   256  		Nickname string
   257  	}
   258  
   259  	gtest.C(t, func(t *gtest.T) {
   260  		user := new(User)
   261  		err := db.Model(table).Where("id=100").Scan(user)
   262  		t.Assert(err, sql.ErrNoRows)
   263  		t.AssertNE(user, nil)
   264  	})
   265  
   266  	gtest.C(t, func(t *gtest.T) {
   267  		one, err := db.Model(table).Where("id=100").One()
   268  		t.AssertNil(err)
   269  		var user *User
   270  		t.Assert(one.Struct(&user), nil)
   271  		t.Assert(user, nil)
   272  	})
   273  
   274  	gtest.C(t, func(t *gtest.T) {
   275  		var user *User
   276  		err := db.Model(table).Where("id=100").Scan(&user)
   277  		t.AssertNil(err)
   278  		t.Assert(user, nil)
   279  	})
   280  }
   281  
   282  func Test_Structs_Empty(t *testing.T) {
   283  	table := createTable()
   284  	defer dropTable(table)
   285  
   286  	type User struct {
   287  		Id       int
   288  		Passport string
   289  		Password string
   290  		Nickname string
   291  	}
   292  
   293  	gtest.C(t, func(t *gtest.T) {
   294  		all, err := db.Model(table).Where("id>100").All()
   295  		t.AssertNil(err)
   296  		users := make([]User, 0)
   297  		t.Assert(all.Structs(&users), nil)
   298  	})
   299  	gtest.C(t, func(t *gtest.T) {
   300  		all, err := db.Model(table).Where("id>100").All()
   301  		t.AssertNil(err)
   302  		users := make([]User, 10)
   303  		t.Assert(all.Structs(&users), nil)
   304  	})
   305  	gtest.C(t, func(t *gtest.T) {
   306  		all, err := db.Model(table).Where("id>100").All()
   307  		t.AssertNil(err)
   308  		var users []User
   309  		t.Assert(all.Structs(&users), nil)
   310  	})
   311  
   312  	gtest.C(t, func(t *gtest.T) {
   313  		all, err := db.Model(table).Where("id>100").All()
   314  		t.AssertNil(err)
   315  		users := make([]*User, 0)
   316  		t.Assert(all.Structs(&users), nil)
   317  	})
   318  	gtest.C(t, func(t *gtest.T) {
   319  		all, err := db.Model(table).Where("id>100").All()
   320  		t.AssertNil(err)
   321  		users := make([]*User, 10)
   322  		t.Assert(all.Structs(&users), nil)
   323  	})
   324  	gtest.C(t, func(t *gtest.T) {
   325  		all, err := db.Model(table).Where("id>100").All()
   326  		t.AssertNil(err)
   327  		var users []*User
   328  		t.Assert(all.Structs(&users), nil)
   329  	})
   330  }
   331  
   332  type MyTime struct {
   333  	gtime.Time
   334  }
   335  
   336  type MyTimeSt struct {
   337  	CreateTime MyTime
   338  }
   339  
   340  func (st *MyTimeSt) UnmarshalValue(v interface{}) error {
   341  	m := gconv.Map(v)
   342  	t, err := gtime.StrToTime(gconv.String(m["create_time"]))
   343  	if err != nil {
   344  		return err
   345  	}
   346  	st.CreateTime = MyTime{*t}
   347  	return nil
   348  }
   349  
   350  func Test_Model_Scan_CustomType_Time(t *testing.T) {
   351  	table := createInitTable()
   352  	defer dropTable(table)
   353  	gtest.C(t, func(t *gtest.T) {
   354  		st := new(MyTimeSt)
   355  		err := db.Model(table).Fields("create_time").Scan(st)
   356  		t.AssertNil(err)
   357  		t.Assert(st.CreateTime.String(), "2018-10-24 10:00:00")
   358  	})
   359  	gtest.C(t, func(t *gtest.T) {
   360  		var stSlice []*MyTimeSt
   361  		err := db.Model(table).Fields("create_time").Scan(&stSlice)
   362  		t.AssertNil(err)
   363  		t.Assert(len(stSlice), TableSize)
   364  		t.Assert(stSlice[0].CreateTime.String(), "2018-10-24 10:00:00")
   365  		t.Assert(stSlice[9].CreateTime.String(), "2018-10-24 10:00:00")
   366  	})
   367  }
   368  
   369  func Test_Model_Scan_CustomType_String(t *testing.T) {
   370  	type MyString string
   371  
   372  	type MyStringSt struct {
   373  		Passport MyString
   374  	}
   375  
   376  	table := createInitTable()
   377  	defer dropTable(table)
   378  	gtest.C(t, func(t *gtest.T) {
   379  		st := new(MyStringSt)
   380  		err := db.Model(table).Fields("Passport").WherePri(1).Scan(st)
   381  		t.AssertNil(err)
   382  		t.Assert(st.Passport, "user_1")
   383  	})
   384  	gtest.C(t, func(t *gtest.T) {
   385  		var sts []MyStringSt
   386  		err := db.Model(table).Fields("Passport").Order("id asc").Scan(&sts)
   387  		t.AssertNil(err)
   388  		t.Assert(len(sts), TableSize)
   389  		t.Assert(sts[0].Passport, "user_1")
   390  	})
   391  }
   392  
   393  type User struct {
   394  	Id         int
   395  	Passport   string
   396  	Password   string
   397  	Nickname   string
   398  	CreateTime *gtime.Time
   399  }
   400  
   401  func (user *User) UnmarshalValue(value interface{}) error {
   402  	if record, ok := value.(gdb.Record); ok {
   403  		*user = User{
   404  			Id:         record["id"].Int(),
   405  			Passport:   record["passport"].String(),
   406  			Password:   "",
   407  			Nickname:   record["nickname"].String(),
   408  			CreateTime: record["create_time"].GTime(),
   409  		}
   410  		return nil
   411  	}
   412  	return gerror.NewCodef(gcode.CodeInvalidParameter, `unsupported value type for UnmarshalValue: %v`, reflect.TypeOf(value))
   413  }
   414  
   415  func Test_Model_Scan_UnmarshalValue(t *testing.T) {
   416  	table := createInitTable()
   417  	defer dropTable(table)
   418  	gtest.C(t, func(t *gtest.T) {
   419  		var users []*User
   420  		err := db.Model(table).Order("id asc").Scan(&users)
   421  		t.AssertNil(err)
   422  		t.Assert(len(users), TableSize)
   423  		t.Assert(users[0].Id, 1)
   424  		t.Assert(users[0].Passport, "user_1")
   425  		t.Assert(users[0].Password, "")
   426  		t.Assert(users[0].Nickname, "name_1")
   427  		t.Assert(users[0].CreateTime.String(), CreateTime)
   428  
   429  		t.Assert(users[9].Id, 10)
   430  		t.Assert(users[9].Passport, "user_10")
   431  		t.Assert(users[9].Password, "")
   432  		t.Assert(users[9].Nickname, "name_10")
   433  		t.Assert(users[9].CreateTime.String(), CreateTime)
   434  	})
   435  }
   436  
   437  func Test_Model_Scan_Map(t *testing.T) {
   438  	table := createInitTable()
   439  	defer dropTable(table)
   440  
   441  	gtest.C(t, func(t *gtest.T) {
   442  		var users []*User
   443  		err := db.Model(table).Order("id asc").Scan(&users)
   444  		t.AssertNil(err)
   445  		t.Assert(len(users), TableSize)
   446  		t.Assert(users[0].Id, 1)
   447  		t.Assert(users[0].Passport, "user_1")
   448  		t.Assert(users[0].Password, "")
   449  		t.Assert(users[0].Nickname, "name_1")
   450  		t.Assert(users[0].CreateTime.String(), CreateTime)
   451  
   452  		t.Assert(users[9].Id, 10)
   453  		t.Assert(users[9].Passport, "user_10")
   454  		t.Assert(users[9].Password, "")
   455  		t.Assert(users[9].Nickname, "name_10")
   456  		t.Assert(users[9].CreateTime.String(), CreateTime)
   457  	})
   458  }
   459  
   460  func Test_Scan_AutoFilteringByStructAttributes(t *testing.T) {
   461  	table := createInitTable()
   462  	defer dropTable(table)
   463  
   464  	type User struct {
   465  		Id       int
   466  		Passport string
   467  	}
   468  	//db.SetDebug(true)
   469  	gtest.C(t, func(t *gtest.T) {
   470  		var user *User
   471  		err := db.Model(table).OrderAsc("id").Scan(&user)
   472  		t.AssertNil(err)
   473  		t.Assert(user.Id, 1)
   474  	})
   475  	gtest.C(t, func(t *gtest.T) {
   476  		var users []User
   477  		err := db.Model(table).OrderAsc("id").Scan(&users)
   478  		t.AssertNil(err)
   479  		t.Assert(len(users), TableSize)
   480  		t.Assert(users[0].Id, 1)
   481  	})
   482  }