I recently discovered a simply way to get user input in windows cmd.exe batch files using the /p option provided by set command. But for a strange reason that I don’t understand the set /p behaves tricky when used between a if statement.
First, create a batch file named “ScriptRunsOK.bat” code below:
@echo off
rem Gets a User Yes-No Choice
set /p UserInput=Your Choice [Y/N]:
set UserChoice=%UserInput:~0,1%
if "%UserChoice%"=="y" set UserChoice=Y
if "%UserChoice%"=="Y" (
echo You Accepted[%UserChoice%] typing %UserChoice%
) else (
echo You Rejected[%UserChoice%] typing %UserChoice%
)
pause
Second, create a batch file “ScriptRunsBAD.bat” enclosing the “User Input & Evaluation” code in a intentionaly only for example purpouses) between a if statement. Code as follows:
@echo off
rem Gets a User Yes-No Choice. Choice Nested in a IF Statement
set DummyVar=OK
if "%DummyVar%"=="OK" (
set /p UserInput=Your Chiuce [Y/N]:
set UserChoice=%UserInput:~0,1%
if "%UserChoice%"=="y" set UserChoice=Y
if "%UserChoice%"=="Y" (
echo You Accepted[%UserChoice%] typing %UserChoice%
) else (
echo You Rejected[%UserChoice%] typing %UserChoice%
)
)
pause
Third, run “ScriptRunsOK.bat” just double-clicking on it, or directly from de command line repeatedly. It works fine every time you run it. But if you try the same with “ScriptRunsBAD.bat”, it doesn’t work as I espected and furthermore, when you run it from command line it, strangely, preserves the user input typed on the previous excecution.
What has the code for “ScriptRunsBAD.bat” that causes the behavior? Is there an additional consideration I must have when using the set /p command within a if or multi-line statement?
Well. Finally, after reading the content of the links posted by @melpomene and @Wimmel (thanks) I could solve the issue. In short words (further details follow the links posted) cmd scripting evals (by default) variable evaluation when every line is parsed (not the habitual behavior expected when you are a programmer). The script solved uses
SETLOCAL ENABLEDELAYEDEXPANSIONto enable “Delayed Expansion” that allows that variables be expanded at execution time rather than at parse time when referenced using exclamation points (see!UserInput:~0,1!and!UserChoice!).The script solved: