MySQL ONLY_FULL_GROUP_BY禁用后自动恢复?求永久禁用或查询适配方案
解决ONLY_FULL_GROUP_BY自动恢复及查询兼容问题
一、永久禁用ONLY_FULL_GROUP_BY
通过phpMyAdmin修改的SQL模式是临时生效的,MySQL服务重启后会恢复默认配置,需修改配置文件实现永久禁用:
- 找到配置文件:
- Linux系统:通常位于
/etc/my.cnf、/etc/mysql/my.cnf或/etc/mysql/mysql.conf.d/mysqld.cnf - Windows系统:一般在MySQL安装目录的
my.ini,或C:\ProgramData\MySQL\MySQL Server X.X目录下(ProgramData是隐藏文件夹)
- Linux系统:通常位于
- 修改配置:
打开配置文件,找到[mysqld]段落,添加或修改sql_mode参数,移除其中的ONLY_FULL_GROUP_BY。示例:[mysqld] sql_mode = "STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_ENGINE_SUBSTITUTION" - 重启服务:
- Linux:执行命令
sudo systemctl restart mysql - Windows:打开「服务」找到MySQL服务,右键选择「重启」
- Linux:执行命令
- 验证生效:
登录MySQL执行以下命令,确认输出中无ONLY_FULL_GROUP_BY:SELECT @@sql_mode;
二、修改SQL查询适配ONLY_FULL_GROUP_BY
ONLY_FULL_GROUP_BY要求SELECT子句中的所有非聚合列必须出现在GROUP BY子句中,或通过聚合函数(如MAX、MIN、GROUP_CONCAT等)明确指定分组后的取值。针对你的查询,可做如下修改:
SELECT MAX(a.id) AS assegnazione_id, MAX(d.colore) AS stato_colore, MAX(d.nome) AS stato_label, a.commessa_id AS id, MAX(c.titolo) AS macro, MAX(b.titolo) AS titolo, MAX(a.scadenza) AS scadenza, MAX(a.ore) AS tempo_stimato, a.voce_id, MAX(c.colore) AS colore, a.titolo AS titolo_user, a.user_id, a.stato FROM commesse_assegnazioni a LEFT JOIN commesse_voci b ON a.voce_id = b.id LEFT JOIN commesse_voci c ON b.macro_id = c.id LEFT JOIN sys_stati d ON a.stato = d.id WHERE a.commessa_id = 99 AND a.user_id = 1 AND b.parent_id != 0 AND a.stato != 20 AND a.scadenza IS NOT NULL GROUP BY a.voce_id, a.user_id, a.titolo, a.commessa_id, a.stato ORDER BY MAX(a.scadenza) ASC
修改说明:
- 对不在GROUP BY中的列(如
a.id、d.colore、c.titolo等)使用MAX()聚合函数,确保分组后该列有确定取值;若你需要取分组内的其他值,可替换为MIN()或GROUP_CONCAT()等适合的聚合函数。 - 将
a.commessa_id、a.stato加入GROUP BY子句,因为这两列在WHERE条件中已固定或与分组逻辑关联,加入后符合模式要求。
内容的提问来源于stack exchange,提问作者user3348353
相关产品推荐
相关产品推荐

