批处理在第三次尝试时正确运行,但根本不在任务管理器中运行

时间:2017-03-03 13:55:41

标签: windows batch-file cmd directory exe

我在这里阅读了各种答案并尝试了一些但没有运气。

我的问题是脚本“log_copy_script.cmd”,我有一些子程序,但其中一个表现得很奇怪。该脚本旨在获取今天的日期,减去1年,然后开始删除1年前的文件夹。它有时会起作用。事实上,如果我通过命令行运行它,它将首先尝试删除名为nothing“”的文件夹,然后它将只尝试月份和日期“MMDD”,然后第三次它将正确地执行“YYYYMMDD”。任何进一步的后续时间都将成功,就像缓存某些内容一样。

此外,当我通过Windows任务计划程序运行它时,它将运行并登录到我的日志文件,但每次都会尝试删除“”空白。

有谁知道这里发生了什么?谢谢。 : - /

REM Get IP and Vol Name from file, define variables
for /f "delims=" %%x in (C:/SystemHealthScripts/ip_address.txt) do set IP_ADDRESS=%%x
for /f "delims=" %%x in (C:/SystemHealthScripts/vol_name.txt) do set VOL_NAME=%%x
set MAINDIR="\\%IP_ADDRESS%%VOL_NAME%"
set SUBDIR="\\%IP_ADDRESS%%VOL_NAME%\%LOG_DATE%"
set LOGFILE="\\%IP_ADDRESS%%VOL_NAME%\log.txt"

if [%1]==[delete_oldest] (

  REM Format date
  for /f "tokens=1,2,3,4 delims=/ " %%a in ("%date%") do set month=%%b&set year=%%c&set day=%%a
  set LOG_DATE=%year%%month%%day%

  set /A "DEL_YEAR=year-1"
  set DEL_DATE=%DEL_YEAR%%month%%day%

  REM Basic validation (Greater than or equal to 20160101 then valid date)
  if [%DEL_DATE%] GEQ [20160101] (
    call echo "%LOG_DATE% %LOG_TIME%: Deleting date '%DEL_DATE%' started" >> %LOGFILE%
    call rmdir /s /q %MAINDIR%\%DEL_DATE%
    call echo "%LOG_DATE% %LOG_TIME%: Deleting date '%DEL_DATE%' finished" >> %LOGFILE%

  ) else (
    call echo "%LOG_DATE% %LOG_TIME%: ERROR in deleting date '%DEL_DATE%', validation not met!" >> %LOGFILE%
  )
)

2 个答案:

答案 0 :(得分:2)

由于您没有为变量分配对cmd有意义的字符,因此您应该可以安全地在您的scipt(第一行)顶部插入一行setlocal enabledelayedexpansion

使用任何代码块(带括号的代码),首先解析块 - 解析过程的一部分是将 ANY %var%变量替换为其当前值。由于您在代码块中分配了month实例,因此第一次运行时其值 nothing - setlocal缺席,month的值在第一次运行时将用作第二次运行的初始值,依此类推。

setlocal enabledelayedexpansion做了两件事。首先,当批次结束时,环境将恢复到其原始设置。所有更改都将被撤消,因此在任何运行中分配或更改的任何值都将被重置"。

它做的第二件事是允许语法!var!访问变量的值,因为它在块中发生变化(通常是for的结果循环,但也是if/else操作的结果。

所以 - 添加setlocal enabledelayedexpansion并替换任何变量,其值在%var%!var!

的块内发生变化

这被称为"延迟扩张" - 关于这个问题,SO上有数百个项目。对许多很多例子使用search

答案 1 :(得分:1)

采用任何延迟扩张的替代方法。

WHERE datepart(mm, SomeDate) = 1
and year(SomeDate) = 2016
AND Param1 = ?
AND Param2 = ?;