字面意思理解是sql_model=only_full_group_by限制了,导致在以往MYSQL版本中能正常查询的SQL,在5.7不能用了。文档指出:ONLY_FULL_GROUP_BY 的设定,将不允许查询字段包括非聚集列。
[SQL]SELECT `member_id`, count(*) as orderCount FROM `gp_order` WHERE `member_id` IN ('1', '2', '4201', '4202', '4203', '4204', '4205', '4206', '4207', '4208')
[Err] 1140 - In aggregated query without GROUP BY, expression #1 of SELECT list contains nonaggregated column 'dev.gp_order.member_id'; this is incompatible with sql_mode=only_full_group_by
直接加下groupBy
子句就好了。
具体如下:
最近由于重新部署网站,服务器配置成apache2.4,php5.6,mysql5.7,但运行网站时发现有一些报错。
其中有一条是:#1055 - Expression #3 of SELECT list is not in GROUP BY clause and contains nonaggregated column 'cash.sdb_login_log.id' which is not functionally dependent on columns in GROUP BY clause; this is incompatible with sql_mode=only_full_group_by
SQL语句如下:
SELECT * FROM `sdb_login_log` group by ip
表结构:
CREATE TABLE `sdb_login_log` (
`id` int(10) NOT NULL AUTO_INCREMENT,
`group_level` int(11) NOT NULL,
`uid` int(11) NOT NULL,
`username` varchar(50) NOT NULL,
`ip` char(15) NOT NULL,
`last_login` datetime DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=MyISAM;
字面意思理解是sql_model=only_full_group_by限制了,导致在以往MYSQL版本中能正常查询的SQL,在5.7不能用了
参考文档:
http://dev.mysql.com/doc/refman/5.7/en/sql-mode.html#sql-mode-setting
文档指出:ONLY_FULL_GROUP_BY的设定,将不允许查询字段包括非聚集列
查询mysql服务器版本:
select @@version
显示:
5.7.10
select @@GLOBAL.sql_mode;
显示结果:
ONLY_FULL_GROUP_BY,STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION
查看sql_mode的语法
select @@GLOBAL.sql_mode;
select @@SESSION.sql_mode;
修改sql_mode的语法
SET GLOBAL sql_mode = 'modes';
SET SESSION sql_mode = 'modes';
或者 set GLOBAL sql_model= '';
解决方法
经过使用修改sql_mode测试,发现可以在不修改sql的情况下,不再报错了。
SET sql_mode = '';
SELECT * FROM `sdb_login_log` group by ip;
如果不想修改sql_mode的话,但还是要输出表的所有 字段,可以修改sql达到。
方法1(返回结果同上SQL)
SELECT ip,max(id) id,max(group_level) group_level,max(uid) uid,max(username) username,max(last_login) last_login FROM `sdb_login_log` group by ip;
方法2(返回结果和上SQL不同):
SELECT ip,id,group_level,uid,username,last_login FROM `sdb_login_log` group by ip,id,group_level,uid,username,last_login;
方法2的返回结果不一样,所以 不能采用。
升级MYSQL5.7是为了更好的性能,据我猜测,MYSQL5.7对sql_mode的限制,也是为了更好的查询性能。所以如果在开发阶段,如果要使用mysql5.7版本建议大家阅读一下5.7的文档,然后将自己的sql写的更严谨,尽量少用select * ,只查出自己想要的数据列即可。
由于 我的程序逻辑上只要不同的ip,和最后登录时间,所以 我的SQL改成以下:
SELECT ip,max(last_login) last_login FROM `sdb_login_log` group by ip;
参考文档: http://dev.mysql.com/doc/refman/5.7/en/sql-mode.html#sql-mode-setting
http://www.520sz.com/mysql-5-7-10-group-by-error.html