MySQL存储过程更新失败:末尾加注释后丢失且报错
MySQL Workbench更新存储过程时末尾注释引发的异常问题
问题场景
我创建了一个简单的存储过程,运行完全正常:
CREATE DEFINER=`someuser`@`%` PROCEDURE `sp_foundRows`() READS SQL DATA SQL SECURITY INVOKER BEGIN SELECT FOUND_ROWS() AS count; END
但用MySQL Workbench尝试更新该存储过程时,工具自动生成了如下代码:
USE `mydb`; DROP procedure IF EXISTS `sp_foundRows`; USE `mydb`; DROP procedure IF EXISTS `mydb`.`sp_foundRows`; ; DELIMITER $$ USE `mydb`$$ CREATE DEFINER=`someuser`@`%` PROCEDURE `sp_foundRows`() READS SQL DATA SQL SECURITY INVOKER BEGIN SELECT FOUND_ROWS() AS count; END -- Just a comment to procedure$$ DELIMITER ; ;
执行时直接弹出错误:
Error getting DDL for object PROCEDURE sp_foundRows does not exist.
之后原存储过程直接从数据库中消失,只能重新创建,无法完成正常的更新操作。经过测试发现,只有当注释放在存储过程定义的最后一行时才会触发这个问题,修改其他行的内容则能正常保存。
问题原因
核心问题出在MySQL Workbench生成的代码格式上:注释和存储过程结束的分隔符$$被放在了同一行。此时注释会将$$一并注释掉,导致存储过程的定义没有正确结束,后续切换分隔符的语句执行前,新的存储过程并未成功创建;而之前的DROP语句已经删除了原存储过程,因此报错“存储过程不存在”,最终导致存储过程丢失。
解决方法
- 调整注释位置
不要把注释放在END之后与$$同行的位置,可以将注释移到END之前,或者单独占一行,保证$$是独立的一行:
DELIMITER $$ USE `mydb`$$ CREATE DEFINER=`someuser`@`%` PROCEDURE `sp_foundRows`() READS SQL DATA SQL SECURITY INVOKER BEGIN SELECT FOUND_ROWS() AS count; -- 这里放置注释 END$$ DELIMITER ;
- 手动修正生成的代码
如果必须在末尾添加注释,确保注释和$$分隔开,让$$单独成一行:
DELIMITER $$ USE `mydb`$$ CREATE DEFINER=`someuser`@`%` PROCEDURE `sp_foundRows`() READS SQL DATA SQL SECURITY INVOKER BEGIN SELECT FOUND_ROWS() AS count; END -- Just a comment to procedure $$ DELIMITER ;
- 升级MySQL Workbench版本
这大概率是旧版本Workbench的BUG,升级到最新的稳定版本,工具会自动生成正确格式的代码,避免此类问题。
内容的提问来源于stack exchange,提问作者Doom
相关产品推荐
相关产品推荐

