VBScript - передать команду оболочки, используя условное выполнение с командой выбора

Не уверен, что это выполнимо, но я пытаюсь написать следующий пакетный скрипт в одну строку:

@echo off

echo Shutdown initiated...
echo.
choice /c xy /n /t 10 /d y /m "To cancel shutdown press "X""
if errorlevel 2 goto EXEC
if errorlevel 1 goto ABORT

:EXEC
echo.
echo Computer shutting down 
timeout /t 10 
exit
:ABORT
echo.
echo Shutdown cancelled 
timeout /t 10
exit

Приведенный выше скрипт необходимо передать через команду vbs run в cmd. Ниже приведено самое близкое, что я могу получить:

option explicit
dim wshell, strcmd

set wshell = createobject("wscript.shell")

if hour(now()) >= 0 and hour(now()) < 6 then
strcmd = "cmd /c @echo off & echo ""Pre-Dawn Shutdown initiated"" & echo. & choice /c xy /n /t 10 /d y /m ""To cancel shutdown press ""X"""" & if errorlevel 2 goto exec & if errorlevel 1 goto abort & :exec & echo. & echo ""Computer shutting down"" & timeout /t 10 & exit & :abort & echo. & echo ""Shutdown cancelled"" & timeout /t 10 & exit"
wshell.run strcmd
end if

Вышеприведенное работает, как и ожидалось, до тех пор, пока не будет достигнута команда выбора, после чего сценарий не сможет правильно выполнить оставшуюся часть. Любая помощь в решении этого очень ценится.


person Albert F D    schedule 04.09.2016    source источник


Ответы (2)


Вы можете написать свой пакетный скрипт в одну строку, имея в виду, что GOTO команда направляет пакетный скрипт для перехода к отмеченной строке. Следовательно, вам необходимо переписать свой сценарий, используя IF… ELSE… синтаксис команды следующим образом:

@echo off

echo Shutdown initiated...
echo.
choice /c xy /n /t 10 /d y /m "To cancel shutdown press "X""
if errorlevel 2 (
  rem goto EXEC
  rem :EXEC
  echo.
  echo Computer shutting down 
  timeout /t 10 
  exit
) else if errorlevel 1 (
  rem goto ABORT
  rem :ABORT
  echo.
  echo Shutdown cancelled 
  timeout /t 10
  exit
)

В целях отладки (т. е. для просмотра вывода) в следующем лайнере каждый exit заменяется на pause:

@echo Shutdown initiated...&echo.&choice /c xy /n /t 10 /d y /m "To cancel shutdown press "X""&if errorlevel 2 (echo. &echo Computer shutting down&timeout /t 10&pause) else if errorlevel 1 (echo.&echo Shutdown cancelled&timeout /t 10& pause )

Вывод:

==> @echo Shutdown initiated...&echo.&choice /c xy /n /t 10 /d y /m "To cancel shutdown pres
s "X""&if errorlevel 2 (echo. &echo Computer shutting down&timeout /t 10&pause) else if erro
rlevel 1 (echo.&echo Shutdown cancelled&timeout /t 10& pause )
Shutdown initiated...

To cancel shutdown press X X

Shutdown cancelled

Waiting for  0 seconds, press a key to continue ...
Press any key to continue . . .

==> @echo Shutdown initiated...&echo.&choice /c xy /n /t 10 /d y /m "To cancel shutdown pres
s "X""&if errorlevel 2 (echo. &echo Computer shutting down&timeout /t 10&pause) else if erro
rlevel 1 (echo.&echo Shutdown cancelled&timeout /t 10& pause )
Shutdown initiated...

To cancel shutdown press X Y

Computer shutting down

Waiting for  0 seconds, press a key to continue ...
Press any key to continue . . .

Следующий фрагмент кода VBScript немного изменен, опять же в целях отладки.

option explicit
On Error GoTo 0
Dim strResult: strResult = Wscript.ScriptName

dim wshell, strcmd, Return 

set wshell = createobject("wscript.shell")

if True or (hour(now()) >= 0 and hour(now()) < 6) then
  strcmd = "cmd /c @echo Shutdown initiated...&echo." & _
    "&choice /c xy /n /t 10 /d y /m ""To cancel shutdown press ""X""""" & _ 
    "&if errorlevel 2 (echo. &echo Computer shutting down&timeout /t 10" & _
    "&exit /B 2) else if errorlevel 1 (echo." & _
    "&echo Shutdown cancelled&timeout /t 10&exit /B 1)"
  strResult = strResult & vbNewLine & strcmd
  Return = wshell.run( strcmd, 1, True)
  strResult = strResult & vbNewLine & CStr( Return)
end if

'strResult = strResult & vbNewLine & 

Wscript.Echo strResult

Вывод: нажал X при первом запуске и Y (или ничего) при последующем.

==> cscript //nologo D:\VB_scripts\SO\39313751.vbs
39313751.vbs
cmd /c @echo Shutdown initiated...&echo.&choice /c xy /n /t 10 /d y /m "To cancel shutdown p
ress "X""&if errorlevel 2 (echo. &echo Computer shutting down&timeout /t 10&exit /B 2) else
if errorlevel 1 (echo.&echo Shutdown cancelled&timeout /t 10&exit /B 1)
1

==> cscript //nologo D:\VB_scripts\SO\39313751.vbs
39313751.vbs
cmd /c @echo Shutdown initiated...&echo.&choice /c xy /n /t 10 /d y /m "To cancel shutdown p
ress "X""&if errorlevel 2 (echo. &echo Computer shutting down&timeout /t 10&exit /B 2) else
if errorlevel 1 (echo.&echo Shutdown cancelled&timeout /t 10&exit /B 1)
2

==>
person JosefZ    schedule 04.09.2016
comment
Очень дотошный и исчерпывающий ответ, спасибо JosefZ! :) - person Albert F D; 05.09.2016

Это из раздела Win32Shutdown класса Win32_OperatingSystem в справке — https://msdn.microsoft.com/en-us/library/aa394058(v=vs.85).aspx.

Dim testResult 
Dim WMIServiceObject, ComputerObject  

'Now get some privileges 
WMIServiceObject = GetObject(
"Winmgmts:{impersonationLevel=impersonate,(Debug,Shutdown)}")
ForEach ComputerObject In WMIServiceObject.InstancesOf("Win32_OperatingSystem") 
    testResult = ComputerObject.Win32Shutdown(0, 0) 'logoff 
    If testResult <> 0 Then 
        MsgBox("Sorry, an error has occurred while trying to perform selected operation") 
    EndIf 
Next

Это таблица, говорящая о том, что вы хотите, чтобы произошло. (первый параметр)

0 (0x0) Выход из системы — пользователь выходит из системы. Выход из системы останавливает все процессы, связанные с контекстом безопасности процесса, вызвавшего функцию выхода, выводит текущего пользователя из системы и отображает диалоговое окно входа в систему.

4 (0x4) Forced Log Off (0 + 4) — пользователь немедленно выходит из системы и не уведомляет приложения о завершении сеанса входа. Это может привести к потере данных.

1 (0x1) Завершение работы — выключает компьютер до момента, когда можно безопасно отключить питание. (Все буферы файлов сбрасываются на диск, и все запущенные процессы останавливаются.) Пользователи видят сообщение: Теперь можно безопасно выключить компьютер. Во время завершения работы система отправляет сообщение каждому работающему приложению. Приложения выполняют любую очистку во время обработки сообщения и возвращают True, чтобы указать, что они могут быть завершены.

5 (0x5) Forced Shutdown (1 + 4) — выключает компьютер до точки, при которой можно безопасно отключить питание. (Все буферы файлов сбрасываются на диск, и все запущенные процессы останавливаются.) Пользователи видят сообщение: Теперь можно безопасно выключить компьютер. При использовании метода принудительного завершения работы все службы, включая WMI, немедленно отключаются. Из-за этого вы не сможете получить возвращаемое значение, если запускаете скрипт на удаленном компьютере.

2 (0x2) Reboot — выключает, а затем перезагружает компьютер.

6 (0x6) Принудительная перезагрузка (2 + 4) — выключает, а затем перезагружает компьютер. При использовании принудительной перезагрузки все службы, включая WMI, немедленно отключаются. Из-за этого вы не сможете получить возвращаемое значение, если запускаете скрипт на удаленном компьютере.

8 (0x8) Power Off — выключает компьютер и отключает питание (если поддерживается данным компьютером).

12 (0xC) Forced Power Off (8 + 4) — выключает компьютер и отключает питание (если поддерживается данным компьютером). При использовании принудительного отключения питания все службы, включая WMI, немедленно закрываются. Из-за этого вы не сможете получить возвращаемое значение, если запускаете скрипт на удаленном компьютере.

person Community    schedule 04.09.2016
comment
Спасибо за вариант, очень пригодится! :) - person Albert F D; 05.09.2016