UserBasic结构体中三个字段LoginTime、HeartbeatTime、LoginOutTime,字段类型是 time.Time

执行表迁移后,数据库表中三个字段LoginTime、HeartbeatTime、LoginOutTime,字段类型是 datetime,注意“datetime”类型用于存储时间,而时间的零值是'0000-00-00',而由于数据库本身的原因,不支持datetime类型的字段有零值。

当Go通过Gorm操作数据库时,这三个字段没有赋值,Gorm会给字段使用time.Time类型的默认零值,也就是'0000-00-00',那么数据库不愿意接收'0000-00-00',自然就会报错了。

字段使用了 time.Time 类型,插入数据时报错:Error 1292 (22007): Incorrect datetime value: '0000-00-00' for column 'login_out_time' at row 1

下面是终端的SQL语句

INSERT INTO `user_basic` (`created_at`,`updated_at`,`deleted_at`,`name`,`pass_word`,`phone`,`email`,`identity`,`client_ip`,`client_port`,`login_time`,`heartbeat_time`,`login_out_time`,`is_logout`,`device_info`) VALUES ('2024-07-08 14:10:19.712','2024-07-08 14:10:19.712',NULL,'黄鹏举','','','','','','','2024-07-08 14:10:19.711',NULL,'0000-00-00 00:00:00',false,'')

这是因为当前的MySQL不支持datetime为0的情况。

MySQL报incorrect datetime value ‘0000-00-00 00:00:00’ for column错误原因,是由于在MySQL5.7版本以上,默认设置SQL_Mode模式,在模式里有NO_ZERO_DATE,NO_ZERO_IN_DATE,存在表示系统里DATE类型字段不能有0值,所以在执行操作时会报此错误。

问题总结:字段(DATE类型)的零值,都不会保存到数据库内


一、找出问题字段

代码片段:

LoginOutTime  time.Time 

插入数据时login_out_time字段的值:0000-00-00 00:00:00,插入数据报错“login_out_time”列的日期时间值“0000-00-00”不正确

二、解决问题

方式1:定义字段类型时,使用指针,从而可以避免零值存入数据库这种情况。

修改代码:把 time.Time 改为  *time.Time

LoginOutTime  *time.Time 

修改后,插入数据时login_out_time字段的值将不是:0000-00-00 00:00:00,而是 Null。

方式2:

执行下面的SQL语句,查看模式。

show variables like 'sql_mode';

执行下面的SQL语句,去掉模式中的:NO_ZERO_IN_DATE,NO_ZERO_DATE

set global sql_mode='ONLY_FULL_GROUP_BY,STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_ENGINE_SUBSTITUTION';

# 原来的 mode(也就是没有修改之前的备份一下)
# set global sql_mode='ONLY_FULL_GROUP_BY,STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_ENGINE_SUBSTITUTION';

修改后,插入数据时login_out_time字段的值:0000-00-00 00:00:00 可以插入成功。

Logo

腾讯云面向开发者汇聚海量精品云计算使用和开发经验,营造开放的云计算技术生态圈。

更多推荐