Navicat执行sql报错 [Err] 1055 - Expression # 1 of ORDER BY clause is not in GROUP BY

一、 问题描述

 

开发反馈Navicat无论执行什么语句都会有以下报错,不过实际能执行成功。

[Err] 1055 - Expression #1 of ORDER BY clause is not in GROUP BY clause and contains nonaggregated column 'information_schema.PROFILING.SEQ' which is not functionally dependent on columns in GROUP BY clause; this is incompatible with sql_mode=only_full_group_by

二、 问题分析

打开 general_log,在Navicat执行语句,然后关闭

Show Variables like '% Gen%';
SET Global general_log =. 1;
Update XXXXX SET XXXX; -- navicat中执行
SET Global general_log = 0;
Show Variables like '% Gen%';

会发现以下结果:

2020-01-08T15:20:47.934694+08:00 2605922 Query SHOW GLOBAL STATUS
2020-01-08T15:20:48.837771+08:00 2608143 Query SET PROFILING=1
2020-01-08T15:20:48.840037+08:00 2608143 Query SHOW STATUS
2020-01-08T15:20:48.845610+08:00 2608143 Query SHOW STATUS
2020-01-08T15:20:48.853304+08:00 2608143 Query UPDATE shx_xxx.user_xxx SET roxx_id='xxxxxxxxxxxxxxxxxx0001' WHERE usxx_id='xxxxxxxxxxxxxxxxxx35';
2020-01-08T15:20:48.857803+08:00 2608143 Query SHOW STATUS
2020-01-08T15:20:48.863344+08:00 2608143 Query SELECT QUERY_ID, SUM(DURATION) AS SUM_DURATION FROM INFORMATION_SCHEMA.PROFILING GROUP BY QUERY_ID
2020-01-08T15:20:48.867054+08:00 2608143 Query SELECT STATE AS `状态`, ROUND(SUM(DURATION),7) AS `期间`, CONCAT(ROUND(SUM(DURATION)/0.000846*100,3), '%') AS `百分比`
FROM INFORMATION_SCHEMA.PROFILING WHERE QUERY_ID=39 GROUP BY STATE ORDER BY SEQ

会执行 SET PROFILING=1 是因为navicat默认自动把profiling功能打开了。

三、 问题原因

navicat默认自动开启profiling,为了展示profiling内容,在执行sql后,低版本navicat会执行以下语句做一个统计(如果用中文版Navicat看到的字段名就是以下三个,英文版就如上图):

SELECT STATE AS `状态`, ROUND(SUM(DURATION),7) AS `期间`, CONCAT(ROUND(SUM(DURATION)/0.000846*100,3), '%') AS `百分比`
FROM INFORMATION_SCHEMA.PROFILING WHERE QUERY_ID=39 
GROUP BY STATE 
ORDER BY SEQ

这个语句是不符合sql 92规范的,only_full_group_by选项要求:order by的内容,应该是group by中其中一项的内容。比如:

  • group by column_a,column_b order by column_a 是正确的。
  • group by column_a,column_b order by column_c 是错误的。

5.5的时候,如果不符合sql 92规范的语句,是不会报错的;5.6之后,sql_mode 中默认包含了 only_full_group_by,所以不符合规范的就报错出来了。

高版本的navicat就不会有这个报错了,估计就是修复了做profiling统计的内置sql语句,做到了order by 和group by 一致。

四、 问题处理

主要有以下方法:

  • 置之不理。该报错实际不影响sql执行,只是一个提示,可以忽略
  • 升级Navicat版本,例如使用 Navicat 12.1.8
  • 使用其他客户端工具,例如 datagrip、workbench 等等
  • 在执行sql前手动执行  SET sql_mode=(SELECT REPLACE(@@sql_mode,'ONLY_FULL_GROUP_BY',''));

参考

https://www.codetd.com/en/article/8461455

<think>好的,用户现在遇到了在Navicat执行DELETE语句后出现的1055错误,并且想了解sql_mode=only_full_group_by的影响及解决方案。根据用户提供的引用内容,特别是引用[1]、[3]、[4]都提到了1055错误与sql_mode的only_full_group_by模式有关。首先,我需要回忆一下MySQL中这个模式的作用。 only_full_group_bySQL模式中的一个选项,启用后,GROUP BY子句中的查询必须满足更严格的条件,即SELECT列表中的列必须要么在GROUP BY子句中,要么被聚合函数包裹,或者功能依赖于GROUP BY的列。这样可以避免查询结果的不确定性。但是,用户的问题是关于DELETE语句的,而通常1055错误出现在SELECT语句中,特别是带有GROUP BY的情况下。为什么会出现在DELETE语句之后呢? 需要仔细分析用户的描述。用户提到执行DELETE语句后返回Err 1055错误。可能DELETE语句本身没有问题,但可能在删除操作后的某个触发器或者后续查询中涉及到了GROUP BY的问题。或者,用户可能在执行DELETE的同时,Navicat自动执行了某些后续查询,比如分析或日志记录,导致错误。例如,引用[1]中提到的错误发生在执行update语句时,错误信息涉及information_schema.PROFILING表,这可能与Navicat的性能分析功能有关。 接下来,需要确认DELETE语句的结构是否有潜在的GROUP BY问题。例如,如果在DELETE语句中使用了子查询,并且子查询中存在GROUP BY子句,而该子查询没有遵守only_full_group_by规则,那么可能会导致1055错误。或者,如果DELETE语句的WHERE条件中包含子查询,该子查询涉及GROUP BY但没有正确聚合,也可能触发此错误。 另外,引用[4]提到,在GROUP BY查询中,columns必须是聚合函数或在GROUP BY列表中,并且如果表有主键,GROUP BY必须包含主键。这可能意味着在DELETE操作相关的子查询中,GROUP BY的使用不符合要求,从而触发了错误。 解决方案方面,用户可能需要调整SQL查询,确保所有GROUP BY子句符合only_full_group_by的要求,或者临时修改sql_mode,关闭only_full_group_by模式。但需要注意的是,修改sql_mode可能会影响其他查询的严格性,因此推荐的方法是优化查询语句而非直接关闭模式。此外,检查Navicat的设置,看看是否有自动执行的查询或分析功能,例如性能分析工具可能在DELETE后执行了某些查询,导致错误。这种情况下,可以尝试禁用这些功能或调整相关查询的SQL模式。 总结可能的原因: 1. DELETE语句中的子查询包含GROUP BY子句,未遵守only_full_group_by规则。 2. Navicat在DELETE操作后自动执行的分析或日志查询存在GROUP BY问题。 3. 触发器或其他数据库对象在DELETE后触发,涉及有问题的GROUP BY查询。 解决方案步骤: 1. 检查DELETE语句是否存在子查询,特别是带有GROUP BY的部分,确保符合only_full_group_by要求。 2. 分析Navicat的行为,确认是否在操作后执行了其他查询,并调整这些查询或关闭相关功能。 3. 临时或永久修改sql_mode,移除only_full_group_by选项,但需谨慎评估影响。 4. 优化相关查询,使用聚合函数或调整GROUP BY子句以符合模式要求。</think>### 原因分析与解决方案 #### 一、DELETE 语句与 1055 错误的关系 **1055 错误本身与 `DELETE` 语句无直接关联**,但可能由以下间接原因引发: 1. **Navicat 自动分析查询**:执行 `DELETE` 后,Navicat 可能自动触发 `SHOW PROFILE` 等性能分析查询[^1] 2. **关联子查询缺陷**:若 `DELETE` 语句的 `WHERE` 子句包含涉及 `GROUP BY` 的子查询,且不满足 `sql_mode=only_full_group_by` 的要求 #### 二、`sql_mode=only_full_group_by` 核心影响 该模式强制要求: 1. `SELECT` 列表中的非聚合字段必须出现在 `GROUP BY` 子句中 2. 或字段必须与 `GROUP BY` 字段存在**函数依赖关系**(如主键) **错误触发场景示例**: ```sql -- 错误写法:name 未出现在 GROUP BY 中 SELECT department, name, AVG(salary) FROM employees GROUP BY department; -- 触发 1055 错误 ``` #### 三、解决方案 ##### 方案 1:优化 SQL 语句(推荐) ```sql -- 正确写法 1:包含所有非聚合字段 SELECT department, name, AVG(salary) FROM employees GROUP BY department, name; -- 正确写法 2:使用聚合函数包裹 SELECT department, MAX(name), AVG(salary) FROM employees GROUP BY department; ``` ##### 方案 2:调整 sql_mode(需评估风险) **临时修改(会话级)**: ```sql -- 查看当前模式 SELECT @@sql_mode; -- 移除 ONLY_FULL_GROUP_BY SET SESSION sql_mode = &#39;STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION&#39;; ``` **永久修改(需 MySQL 配置文件)**: ```ini # my.cnf 或 my.ini [mysqld] sql_mode = "STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION" ``` ##### 方案 3:禁用 Navicat 自动分析(针对工具触发) 1. 进入 Navicat 设置 → 工具 → 选项 2. 取消勾选 **"自动分析查询"** 相关选项 #### 四、验证步骤 1. **检查执行计划**: ```sql EXPLAIN EXTENDED [你的DELETE语句]; ``` 2. **分析关联查询**: ```sql -- 查看外键依赖 SELECT TABLE_NAME, COLUMN_NAME, CONSTRAINT_NAME FROM INFORMATION_SCHEMA.KEY_COLUMN_USAGE WHERE REFERENCED_TABLE_NAME = &#39;re_center&#39;; ``` ### 关键总结 | 方法 | 优点 | 风险 | |------|------|------| | 优化 SQL | 符合 SQL 标准 | 需要修改业务逻辑 | | 调整 sql_mode | 快速生效 | 可能影响其他查询 | | 禁用自动分析 | 工具级修复 | 丧失性能分析功能 | --相关问题--: 1. 如何检测 MySQL 中哪些查询违反 ONLY_FULL_GROUP_BY 规则? 2. 主键在 GROUP BY 查询中起什么特殊作用? 3. Navicat 执行更新操作时如何避免自动触发分析查询?
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Hehuyi_In

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值