【MySQL】探究之TIMESTAMP
背景
之前有业务反馈表中start_time,end_time时间字段随着时间的推移被自动更新,这可不是业务意愿,说的严重点是要出故障的。
MySQL中有DATE,DATETIME,TIMESTAMP时间类型
看看官方文档怎么说
The DATE type is used for values with a date part but no time part. MySQL retrieves and displays DATE values in 'YYYY-MM-DD' format. The supported range is '1000-01-01' to '9999-12-31'.
The DATETIME type is used for values that contain both date and time parts. MySQL retrieves and displays DATETIME values in 'YYYY-MM-DD HH:MM:SS' format. The supported range is '1000-01-01 00:00:00' to '9999-12-31 23:59:59'.
The TIMESTAMP data type is used for values that contain both date and time parts. TIMESTAMP has a range of '1970-01-01 00:00:01' UTC to '2038-01-19 03:14:07' UTC.
这里我们重点介绍下DATATIME和TIMESTMAP
业务反馈start_time,end_time缺失就使TIMESTAMP类型,结合TIMESTAMP的特性,我们来分析原因。
Automatic Initialization and Updating for TIMESTAMP
One TIMESTAMP column in a table can have the current timestamp as the default value for initializing the column, as the auto-update value, or both.
If the column is auto-initialized, it is set to the current timestamp for inserted rows that specify no value for the column.
If the column is auto-updated, it is automatically updated to the current timestamp when the value of any other column in the row is changed from its current value.
什么意思呢?
create table gbtest_with_force_default_val
(
id bigint AUTO_INCREMENT,
t_null_1 timestamp,
t_null_2 timestamp,
t_with_not_null timestamp not null,
t_with_not_null_default timestamp not null default '2016-12-21',
primary key(id)
); mysql> show create table gbtest_with_force_default_val; CREATE TABLE `gbtest_with_force_default_val` (
`id` bigint(20) NOT NULL AUTO_INCREMENT,
`t_null_1` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
`t_null_2` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
`t_with_not_null` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
`t_with_not_null_default` timestamp NOT NULL DEFAULT '2016-12-21 00:00:00',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8
在MySQL5.5版本中,TIMESTAMP特性
- TIMESTAMP字段默认为NOT NULL,如果你在定义“t_null_1 TIMESTAMP DEFAULT NULL” 会提升“ERROR 1067 (42000): Invalid default value for 't_null_1'”。 可以指定为空 null ,“t_null_1 TIMESTAMP NULL" ,这时可以再添加语句改变默认值。
- 如果不做特殊说明,同一个表中会对第一个TIMESTAMP字段设置DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP属性,第二个字段设置DEFAULT '0000-00-00 00:00:00',如果对两个字段都显示指定“DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP”是会被告知“ERROR 1293 (HY000): Incorrect table definition; there can be only one TIMESTAMP column with CURRENT_TIMESTAMP in DEFAULT or ON UPDATE clause”,测试发现在MySQL5.6版本中并没有该限制。
mysql> select version();
+------------------+
| version() |
+------------------+
| 5.6.16.7-rc0-log |
+------------------+
1 row in set (0.00 sec) CREATE TABLE `gbtest_with_force_default_val_null` (
`id` bigint(20) NOT NULL AUTO_INCREMENT,
`t_null_1` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
`t_null_2` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
`t_with_not_null` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
`t_with_not_null_default` timestamp NOT NULL DEFAULT '2016-12-21 00:00:00',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8
那如何解决业务遇到的问题呢,其实很简单,既然“DEFAULT CURRENT_TIMESTAMP”有限制,那不用好了,换成NULL DEFAULT CURRENT_TIMESTAMP去掉自动更新属性,或者显式的允许这两个字段为NULL。
create table gbtest_with_force_default_val_null (
id bigint AUTO_INCREMENT,
t_null_1 timestamp NULL CURRENT_TIMESTAMP,
t_null_2 timestamp NULL DEFAULT 0,
t_with_not_null timestamp not null,
t_with_not_null_default timestamp not null default '2016-12-21', primary key(id) ); mysql> show create table gbtest_with_force_default_val_null; CREATE TABLE `gbtest_with_force_default_val_null` (
`id` bigint(20) NOT NULL AUTO_INCREMENT,
`t_null_1` timestamp NULL CURRENT_TIMESTAMP,
`t_null_2` timestamp NULL DEFAULT '0000-00-00 00:00:00',
`t_with_not_null` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
`t_with_not_null_default` timestamp NOT NULL DEFAULT '2016-12-21 00:00:00',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8
MySQL5.6版本中TIMESTAMP特性
经过学习,发现在5.6版中中多了一个叫“explicit_defaults_for_timestamp”的系统变量,但默认是OFF的,但是也可以支持一个表中多个字段的同时更新。
mysql> show variables like '%explicit_defaults_for_timestamp%';
+---------------------------------+-------+
| Variable_name | Value |
+---------------------------------+-------+
| explicit_defaults_for_timestamp | OFF |
+---------------------------------+-------+
1 row in set (0.00 sec)
那将这个参数打开会有什么不同?
mysql> set @@global.explicit_defaults_for_timestamp=ON;
ERROR 1238 (HY000): Variable 'explicit_defaults_for_timestamp' is a read only variable
该参数并不支持动态修改!!! create table gbtest_with_noforce(
id bigint AUTO_INCREMENT,
t_null_1 timestamp,
t_null_2 timestamp,
t_with_not_null timestamp not null,
t_with_not_null_default timestamp not null default '2016-12-21',
primary key(id)
); CREATE TABLE `gbtest_with_noforce` (
`id` BIGINT(20) NOT NULL AUTO_INCREMENT,
`t_null_1` TIMESTAMP NULL DEFAULT NULL,
`t_null_2` TIMESTAMP NULL DEFAULT NULL,
`t_with_not_null` TIMESTAMP NOT NULL,
`t_with_not_null_default` TIMESTAMP NOT NULL DEFAULT '2016-12-21 00:00:00',
PRIMARY KEY (`id`)
)ENGINE=InnoDB DEFAULT CHARSET=utf8
;
发现如下改变:
- 默认参数为NULL
- 并不会自动添加DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP等属性
结论
那考虑的版本的兼容性,测试发现,在5,5版本中按默认属性创建的表,在5.6版本中迁移是没有任何问题的,是完全兼容的。这说明,使用Mysql5.6以后的版本,应立即将explicit_defaults_for_timestamp参数设置为True,并及时反馈开发TIMESTAMP的行为。
【MySQL】探究之TIMESTAMP的更多相关文章
- MySQL 时间戳(Timestamp)函数
1. MySQL 获得当前时间戳函数:current_timestamp, current_timestamp() mysql> select current_timestamp, curren ...
- mysql的时间戳timestamp精确到小数点后六位
1.mysql的时间戳timestamp精确到小数点后六位. 公司业务使用到Greenplun数据库,根据查询的时间戳来不断的将每个时间段之间的数据,进行数据交换,但是今天发现,mysql的时间戳没有 ...
- MySQL 时间戳(Timestamp)函数
1. MySQL 获得当前时间戳函数:current_timestamp, current_timestamp() mysql> select current_timestamp, curren ...
- Mysql sql_mode设置 timestamp default 0000-00-00 00:00:00 创建表失败处理
往数据库里创建新表的时候报错: [Err] 1067 - Invalid default value for 'updateTime' DROP TABLE IF EXISTS `passwd_res ...
- MySQL datetime 和 timestamp 的区别
[转载]:MySQL中有关TIMESTAMP和DATETIME的总结 1. datetime 和 timestamp 的相同点 两者都可以用来表示YYYY-MM-DD HH:MM:SS[.fracti ...
- mysql多个TimeStamp设置
mysql多个TimeStamp设置 2012-11-02 12:58 轩脉刃 阅读(39590) 评论(3) 编辑 收藏 timestamp设置默认值是Default CURRENT_TI ...
- MySQL中有关TIMESTAMP和DATETIME的总结
一.MySQL中如何表示当前时间? 其实,表达方式还是蛮多的,汇总如下: CURRENT_TIMESTAMP CURRENT_TIMESTAMP() NOW() LOCALTIME LOCALTIME ...
- mysql中的timestamp类型时间比较:unix_timestamp函数
在mysql中,某字段的类型设置为了timestamp,那么我们现在希望取出指定时间段的记录,该如何做呢? 在php中有time()和strtotime()来进行日期和时间戳的格式化,而在mysql中 ...
- mysql 添加[取消]timestamp的自动更新
创建自动更新的 timestamp (插入或修改时 uptime都会自动更新) CREATE TABLE `hello` (`id` int(11) NOT NULL,`uptime` timesta ...
随机推荐
- 内嵌页js与ios和安卓的交互
ios: 一个iframe,改变url会发送一个请求,把url设置成就是bridge://xxxxx客户端就可以拦截请求,并在全局变量xxxxx中取出一个字符串.例如{event:'click'},可 ...
- mybaties 查询 语句正确 但是查不到结果
控制台输出的语句拿到数据库查询就有数据,但是一直显示不出来 也不报错 后来 百度发现数据库连接不对 因为其中引用了两个数据库 所有写混了 ---------------------- ...
- Cisco防火墙配置
帮朋友调试一台ASA,做一下记录(很久没动手了) 三个区: vlan10: inside: 192.168.1.1 vlan20: outside: 202.102.1.1 vlan30: dmz: ...
- JavaScript对象中的属性(可写,可配置,可枚举,value,getter,setter)
JavaScript中,对象包括3个特性,分别为,可扩展性,class标识符,属性. 如果对象的可扩展性为false,则不可为对象动态的添加属性. 对象包含分为存取器属性和值属性.存取属性为 {g ...
- launch文件
launch在ROS应用中,每个节点通常有许多参数需要设置,为了方便高效操作多个节点,可以编写launch文件,然后用roslaunch命令运行roslaunch: roslaunch [option ...
- 【转】Mybatis 3.1中 Mapper XML 文件 的学习详解
MyBatis 真正的力量是在映射语句中.这里是奇迹发生的地方.对于所有的力量,SQL 映射的 XML 文件是相当的简单.当然如果你将它们和对等功能的 JDBC 代码来比较,你会发现映射文件节省了大约 ...
- css定位之绝对定位
绝对定位可以做很多事情,如广告位,弹出框,遮罩层等一些功能 css的定位方式:1.静态定位, 2.绝对定位(固定定位和绝对定位) ,3.相对定位 绝对定位会受到影响的因素有 1.属性的取值. 2.元素 ...
- css布局之两列布局
我们见过两列布局的网站也很多,不过这种两列布局的分为两种:自适应和固定宽度 1.自适应两列布局 <!DOCTYPE html> <html lang="en"&g ...
- linux命令每日一练习-rmdir mv
rmdir 删除一个空的文件夹,当目标文件夹非空的时候不能删除 mv 移动文件或目录 mv source target mv -i *** *** 如果目标文件存在则询问是否覆盖 mv -f *** ...
- Linq二 LinqToSql
虽然微软已经停止更新了LinqToSql,但是目前的已完全满足目前的需求. 第一步:添加LinqToSql 第二步:将其关联的Sqlserver数据库 第三步:数据库已变成实体类 第四步:可以对数据库 ...