我是靠谱客的博主 潇洒冷风,最近开发中收集的这篇文章主要介绍BAT中setlocal EnableDelayedExpansion导致mysqldump失败,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

编写BAT文件时,发现setlocal EnableDelayedExpansion语法会导致mysqldump失败,原因不知道。去除那个setlocal语句后,mysqldump运行通过。

我在Windows服务器中有多个MySQL数据库,期望能做到自动备份,查了下资料,决定通过Windows执行计划调用BAT文件的方式实现。然后在写BAT文件时,马上就遇到了一个莫名其妙的问题:

@echo off
setlocal EnableDelayedExpansion
   
set d=%date:~0,4%%date:~5,2%%date:~8,2%
set bin=C:Program Filesxxxxxxxxxxbin
set dbnames=db1,db2,db3,db4,db5
set folder=xxxxxxxxxxx

for %%a in (!dbnames!) do (
	"!bin!mysqldump.exe" --opt --single-transaction=1 --user=root --password=xxxxxxxxxxxxx --host=127.0.0.1 --protocol=tcp --port=3306 --default-character-set=utf8mb4 --routines --events "%%a" > "%folder%%%a_backup_!d!.sql"
)

@echo on

其中的mysqldump.exe语句行,会提示错误:

mysqldump.exe: Got error: 1045: "Access denied for user 'root'@'localhost' (using password: YES)" when trying to connect

但是把那行语句在cmd窗口中执行,却能通过。多方查找资料,没有能找任何跟这个问题相关的。

然后怀疑,是否是批处理里面的语句在for循环里,会被带入一个特殊的执行空间,跟mysqldump冲突了。于是修改批处理文件:

@echo off
setlocal EnableDelayedExpansion
   
set d=%date:~0,4%%date:~5,2%%date:~8,2%
set bin=C:Program Filesxxxxxxxxxxbin
set dbnames=db1,db2,db3,db4,db5
set folder=xxxxxxxxxxx

"!bin!mysqldump.exe" --opt --single-transaction=1 --user=root --password=xxxxxxxxxxxxx --host=127.0.0.1 --protocol=tcp --port=3306 --default-character-set=utf8mb4 --routines --events "db1" > "%folder%db1_backup_!d!.sql"
"!bin!mysqldump.exe" --opt --single-transaction=1 --user=root --password=xxxxxxxxxxxxx --host=127.0.0.1 --protocol=tcp --port=3306 --default-character-set=utf8mb4 --routines --events "db2" > "%folder%db2_backup_!d!.sql"
"!bin!mysqldump.exe" --opt --single-transaction=1 --user=root --password=xxxxxxxxxxxxx --host=127.0.0.1 --protocol=tcp --port=3306 --default-character-set=utf8mb4 --routines --events "db3" > "%folder%db3_backup_!d!.sql"
"!bin!mysqldump.exe" --opt --single-transaction=1 --user=root --password=xxxxxxxxxxxxx --host=127.0.0.1 --protocol=tcp --port=3306 --default-character-set=utf8mb4 --routines --events "db4" > "%folder%db4_backup_!d!.sql"
"!bin!mysqldump.exe" --opt --single-transaction=1 --user=root --password=xxxxxxxxxxxxx --host=127.0.0.1 --protocol=tcp --port=3306 --default-character-set=utf8mb4 --routines --events "db5" > "%folder%db5_backup_!d!.sql"

@echo on

去掉了for,测试,问题依旧。

进一步简化,把!variable!语法全部换成%variable%语法,情况依旧;

把setlocal EnableDelayedExpansion语句行去掉,马上正常了。

原因分析:

我好多年没写BAT了,这个!variable!还从来没用过,百度查询得知:这是加上setlocal EnableDelayedExpansion语句后可用的语法;传统的%variable%更像是C语言里的宏定义,使用时立即替换成内容;!variable!更像编程语言里的变量,使用时看到的还是变量名。比如,BAT文件:

@echo off
setlocal EnableDelayedExpansion
set a=1
echo %a%
echo !a!
set /a b=!a!+1
echo %b%
@echo on

执行结果:

D:>setlocal EnableDelayedExpansion
D:>set a=1
D:>echo 1
1
D:>echo !a!
1
D:>set /a b=!a!+1
D:>echo 2
2

对比BAT文件和执行结果,发现%variable%语法被立即替换成了数值,!variable!语法则保留了原状直到执行,百度得知这叫“变量延迟扩展”,很高大上的概念。

然而,不知道什么原因,这个setlocal EnableDelayedExpansion竟然会影响到mysqldump的执行。

虽然问题解决了,但是遗憾没有找到根本原因。

最后

以上就是潇洒冷风为你收集整理的BAT中setlocal EnableDelayedExpansion导致mysqldump失败的全部内容,希望文章能够帮你解决BAT中setlocal EnableDelayedExpansion导致mysqldump失败所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(45)

评论列表共有 0 条评论

立即
投稿
返回
顶部