2016-08-20 44 views
1

以下.VBS建立一个没有任何问题所需的任务(请原谅的语法):的VBScript - 传递的schtasks命令到run方法

Option Explicit 

Dim wshell 
Set wshell = CreateObject("WScript.Shell") 
wshell.Run "schtasks /create /sc once /tn ""Reminder"" /tr ""C:\Windows\System32\cmd.exe \""/c title Alert & mode con: cols=40 lines=10 & color f0 & cls & echo *** Message goes here *** & echo. & echo. & echo. & echo. & echo. & echo. & echo. & echo Press any key to exit & pause > nul\"""" /st 18:00 /sd 08/20/2016 /f" 

但是,如果我尝试通过一个变量传递schtasks命令字符串如下:

Option explicit 
dim strdate, strtime, strmessage, strtask, wshell 

strdate = "08/20/2016" 
strtime = "18:30" 
strmessage = "Turn off pump" 

WScript.Echo strdate 
WScript.Echo strtime 
WScript.Echo strmessage 

strtask = """schtasks /create /sc once /tn """"Reminder"""" /tr """"C:\Windows\System32\cmd.exe \""""/c title Alert & mode con: cols=40 lines=10 & color f0 & cls & echo " & strmessage & " & echo. & echo. & echo. & echo. & echo. & echo. & echo. & echo Press any key to exit & pause > nul"""""""" /st " & strtime & " /sd " & strdate & " /f""" & " ,0" & " ,true" 

WScript.Echo strtask 

Set wshell = CreateObject("WScript.Shell") 
wshell.Run strtask 

我得到以下错误:

enter image description here

我不明白为什么我得到这个,被解析的变量毕竟与前面的片段(包括引号)相同......有人能向我解释我失踪的是什么吗?

编辑

由于安斯加尔Wiechers的指导。我已经设法通过删除运行命令选项来获得一个工作的,尽管不雅的脚本,并且内在地检查外部命令错误。见下文:

option explicit 
dim strdate, strtime, strmessage, strtask, exitcode, wshell 

strdate = "08/21/2016" 
strtime = "13:45" 
strmessage = "Turn off pump" 

WScript.Echo strdate 
WScript.Echo strtime 
WScript.Echo strmessage 

strtask = "schtasks /create /sc once /tn ""Reminder"" /tr ""C:\Windows\System32\cmd.exe \""/c title Alert & mode con: cols=40 lines=10 & color f0 & cls & echo " & strmessage & " & echo. & echo. & echo. & echo. & echo. & echo. & echo. & echo Press any key to exit & pause > nul\"""" /st " & strtime & " /sd " & strdate & " /f" 

set wshell = CreateObject("WScript.Shell") 
exitcode = wshell.Run(strtask, 0, True) 
if exitcode <> 0 
then WScript.Echo "External command failed: " & Hex(exitcode) 
End If 

回答

2

我严重怀疑你的原始命令有效。围绕参数列表的嵌套引号至CMD.exe应该始终使其引发错误。删除嵌套的引号(只留下整个CMD语句的双引号),并从strTask中删除Run方法的参数,并且任务创建应该按照您的预期工作。

strtask = "schtasks /create /sc once /tn ""Reminder""" & _ 
      " /tr ""C:\Windows\System32\cmd.exe /c title Alert" & _ 
      " & mode con: cols=40 lines=10 & color f0 & cls" & _ 
      " & echo " & strmessage & _ 
      " & echo. & echo. & echo. & echo. & echo. & echo. & echo." & _ 
      " & echo Press any key to exit & pause > nul""" & _ 
      " /sd " & strdate & " /st " & strtime & " /f" 

exitcode = wshell.Run(strtask, 0, True) 

If exitcode <> 0 Then 
    WScript.Echo "External command failed: " & Hex(exitcode) 
End If 

它总是添加一些代码来检查外部命令的退出状态是一个好主意,这样你就可以检测是否出现了错误。

虽这么说,你可以大大提高该代码的可维护性有一些修改:

  • 不要创建命令行作为一个大的字符串。从里到外构建它。
  • 如果可能,请使用环境变量(例如,%COMSPEC%,而不是文字路径CMD.exe
  • 仅在需要时才使用引号。
  • 使用引用函数添加转义双引号。
Function qq(str) 
    qq = """" & str & """" 
End Function 

cmdargs = "/c title Alert & mode con: cols=40 lines=10 & color f0 & cls" & _ 
      " & echo " & strmessage & " & echo. & echo. & echo. & echo." & _ 
      " & echo. & echo. & echo. & echo Press any key to exit & pause > nul" 
strtask = "schtasks /create /f /sc once /tn Reminder" & _ 
      " /tr " & qq("%COMSPEC% " & cmdargs) & _ 
      " /sd " & strdate & " /st " & strtime 

exitcode = wshell.Run(strtask, 0, True) 

更重要的是,把批号为实际的批处理文件:

@echo off 
title Alert 
mode con: cols=40 lines=10 
color f0 
cls 
echo %~1 
echo. 
echo. 
echo. 
echo. 
echo. 
echo. 
echo. 
echo Press any key to exit 
pause > nul 

,并创建任务运行与您的消息批处理文件:

Function qq(str) 
    qq = """" & Replace(str, """", "\""") & """" 
End Function 

batchfile = "C:\path\to\your.bat" 
strtask = "schtasks /create /f /sc once /tn Reminder" & _ 
      " /tr " & qq(qq(batchfile) & " " & qq(strmessage)) & _ 
      " /sd " & strdate & " /st " & strtime 

exitcode = wshell.Run(strtask, 0, True) 
+0

我很非常感谢你的帮助。我肯定会在我的脚本中使用错误检查(即检查外部命令的状态 - 我可以用'on error'声明来做到这一点)?我选择不使用批处理文件,尽管它很清楚最好的选择,尽管复杂性我更喜欢在一个文件中执行所有的事情......如果可能的话,我有一个后续问题,为什么'strtask'只在稍后添加运行命令选项时解析? –

+1

对于外部命令,您需要检查他们的退出代码,如我的答案中所示。 'On Error'仅控制VBScript错误的错误处理。它不知道外部命令的错误。您的后续问题由[文档](https://msdn.microsoft.com/en-us/library/d5fk67ky%28v=vs.84%29.aspx)回答。 'Run'方法需要一个命令字符串和其他两个选项。它不会从命令字符串中解析这些选项。 –

+0

谢谢Ansgar! :) –