i have created a simple batch, that should get the value from the input, and act according to the choice:
set CA="C:\A\"
set CB="C:\B\"
set SRV="server\"
set /p choice=Insert choice (A/B):
if %choice%== A cd /d %CA%%SRV% & start "" "batch.bat"
if %choice%== B cd /d %CB%%SRV% & start "" "batch.bat"
In the script the first choice works as expected, whereas the second one throws: "The system cannot find the path specified".
The path is correct and the file is there. Directly from CMD the single command works fine. What am i doing wrong in the script?
Sticking with your structure, would the following work for you?
#Echo Off
Set "CA=C:\A\"
Set "CB=C:\B\"
Set "SRV=server\"
Set /P "choice=Insert choice (A/B): "
If /I "%choice%"=="A" If Exist "%CA%%SRV%batch.bat" Start "" /D"%CA%%SRV%" "batch.bat"
If /I "%choice%"=="B" If Exist "%CB%%SRV%batch.bat" Start "" /D"%CB%%SRV%" "batch.bat"
Pause
Related
Im new to batch script and trying to create a script which is going to help me setup a long manual process in a go. i have used if else statement in the batch script but all instructions are executed in one go i have only given 1 as input. code is mentioned below.
call echo 1. Clone a branch from bitbucket
call echo 2. Specify the Absolute path of project
set /P choice=" Enter your Choice : "
if %choice%==1 (
call set /P fo="enter folder name: "
call cd %USERPROFILE%\Desktop\ProjectFolder\%fo%
echo Clone will be created in the following address
call cd
call set /P gitUserName="Enter bitbucket UserName : "
call set /P branch=" Enter Branch Name : "
call echo Git User : %gitUserName%
call echo Branch Name : %branch%
call git clone https://%gitUserName%#bitbucket.org/MyProject/Project-demo.git -b %branch%
call cd Project-demo
) else (
call set /P pathname = "Enter Absolute path of Project-demo : "
cd %pathname%
)
im running it on windows 10. tried disabling #echo off for debugging purposes and found that all instructions are getting executed and at last {call set /P fo="enter folder name: " } <-- this line is executed.
i want it to create a folder and git clone one of my project here. Any Help greatly appreciated.
Also do tell me is call necessary wherever i used it.
The problem you are having has to do with delayed expansion. Everything inside of your parens is processed at once so you can't really do what you are trying to do without more complication. This has to do with Delayed Expansion .
You have two choices.. you can either:
enable EnableDelayedExpansion flag and use "!" instead of "%" within your blocks..
OR
Use "call" properly.. unlike your current use. Call is for calling a label within a batch file.. sort of like a function. If you use goto :EOF at the end of that label.. it will return to the caller like a function in a real programming language.
BTW.. call can also be used to call another batch file but we won't talk about that right now. One bit at a time..
I will show you the call method (which I prefer and other people hate). The call method was the only way to do this before the EnableDelayedExpansion keyword was added.
:)
`
#echo off
:START
cls
echo 1. Clone a branch from bitbucket
echo 2. Specify the Absolute path of project
set /P choice=" Enter your Choice : "
:: If they didn't pick a valid option, show the question again...
if not "%choice%"=="1" if not "%choice%"=="2" goto :START
:: Otherwise, take them down the right path
if "%choice%"=="1" call :DoBitBucketClone
if "%choice%"=="2" call :DoAbsolutePath
:: goto :EOF here will simply exit the script
goto :EOF
:DoBitBucketClone
set /P fo="enter folder name: "
cd %USERPROFILE%\Desktop\ProjectFolder\%fo%
echo Clone will be created in the following address
cd
set /P gitUserName="Enter bitbucket UserName : "
set /P branch=" Enter Branch Name : "
echo Git User : %gitUserName%
echo Branch Name : %branch%
git clone https://%gitUserName%#bitbucket.org/MyProject/Project-demo.git -b %branch%
cd Project-demo
:: we 'could' just exit here but I am trying to
:: show you how the return works..
goto :EOF
:DoAbsolutePath
set /P pathname="Enter Absolute path of Project-demo : "
echo "Path set to %pathname%"
cd /d %pathname%
:: we 'could' just exit here but I am trying to
:: show you how the return works..
goto :EOF
`
When you remove #ECHO OFF it will show you the entire if statement, not just the part that you are running. That's just a limitation of batch scripting.
Also, you are attempting to use variables in the if statement that are also set inside the if statement. Due to the way that parsing and substitution is done, you need to either use Delayed Expansion (using !) or create a subroutine
Some other changes I made are:
Check that the target directory exists. If not, make it.
Explicitly check else case for 2 and add an error case for anything other than 1 or 2.
Wrap paths in quotes
Removed unnecessay usage of call
Added error check for git clone failure
The following illustrates a way you can do it with delayed expansion:
#ECHO OFF
SETLOCAL EnableDelayedExpansion
echo 1. Clone a branch from bitbucket
echo 2. Specify the Absolute path of project
set /P choice=" Enter your Choice : "
if %choice%==1 (
set /P fo="enter folder name: "
SET "DEST=!USERPROFILE!\Desktop\ProjectFolder\!fo!"
IF NOT EXIST "!DEST!" mkdir "!DEST!"
cd "!DEST!"
echo Clone will be created in the following address
echo !DEST!
set /P gitUserName="Enter bitbucket UserName : "
set /P branch=" Enter Branch Name : "
echo Git User : !gitUserName!
echo Branch Name : !branch!
git clone https://!gitUserName!#bitbucket.org/MyProject/Project-demo.git -b !branch!
if errorlevel 1 EXIT /B 1
cd Project-demo
) else if %choice%==2 (
set /P pathname = "Enter Absolute path of Project-demo : "
cd !pathname!
) else (
ECHO:
ECHO ERROR: Unexpected choice '%choice%'
ECHO:
)
(ENDLOCAL
EXIT /B 0)
#echo off
Call :YesNoBox "Press yes or no"
if "%YesNo%"=="6" (
set backupdir=D:\BackupEmail\
cd /d %backupdir%
set folder=%date:~10,4%_%date:~4,2%_%date:~7,2%_%time:~0,2%_%time:~3,2%_%time:~6,2%
mkdir %folder%
echo %folder% created
cd /d %folder%
mkdir Thunderbird
cd Thunderbird
set backupcmd=xcopy /s/h/i/c/k/e/r/y
echo ### Backing Up ...
%backupcmd% "C:\Users\username\AppData\Roaming\Thunderbird\*" "%backupdir%\%folder%\Thunderbird\"
echo Backup Completed!
echo "Deleting Temp files".
del /s /f /q \Windows\Temp\*.*
cmd /k
)
exit
:: Design for pop up window
exit /b
:YesNoBox
REM returns 6 = Yes, 7 = No. Type=4 = Yes/No
set YesNo=
set MsgType=4
set heading=%~2
set message=%~1
echo wscript.echo msgbox(WScript.Arguments(0),%MsgType%,WScript.Arguments(1)) >"%temp%\input.vbs"
for /f "tokens=* delims=" %%a in ('cscript //nologo "%temp%\input.vbs" "%message%" "%heading%"') do set YesNo=%%a
exit /b
:MessageBox
set heading=%~2
set message=%~1
echo msgbox WScript.Arguments(0),0,WScript.Arguments(1) >"%temp%\input.vbs"
cscript //nologo "%temp%\input.vbs" "%message%" "%heading%"
exit /b
I used notepad++ to save this code
Output received in command prompt:
The filename, directory name, or volume label syntax is incorrect.
The syntax of the command is incorrect.
created
The filename, directory name, or volume label syntax is incorrect.
A subdirectory or file Thunderbird already exists.
Here Thunderbird folder is created where the bat file exists, however it should have been created in "BackupEmail" folder in drive D.
When i ran it again on the same command prompt it runs successfully
What this characteristic indicates is that on the first execution there is a variable which is not set but its value is being used - normally in a if statement. However, executing the first time is establishing a value for the variable, so on the second run, the syntax is correct.
It is customary to include a setlocal command immediately after the #echo off. This makes sure that when the code is complete, any changes made to the environment are discarded. In this case, because you have no setlocal command, the variable's value is retained for the second run.
The problem with your code is the #1 FAQ - please search for delayed expansion using the search facility. The variable folder is not established when the if "%YesNo%"=="6" instruction is executed, hence on the first occasion
%folder% has no value BUT it is assigned a value within the code block and it retains that value for the second run (since there is no selocal to discard it).
I'm trying to make a basic Java IDE in Notepad++, which is easy as long as you don't use packages. But if you need to use the -classpath parameter, everything gets difficult.
I want to use these codes, I think you can get the idea:
NPP EXEC code:
NPP_SAVE
SET_ENV NPP_FULL_CURRENT_PATH=$(FULL_CURRENT_PATH)
SET_ENV NPP_CURRENT_DIRECTORY=$(CURRENT_DIRECTORY)
SET_ENV NPP_NAME_PART=$(NAME_PART)
npp_run cmd /k d:\Users\User\Desktop\script.cmd
script.cmd
SETX CLASSPATH %CD%
set /p deep=Deepness:
:START
if /I %deep% EQU 0 goto END
cd ..
set /a deep=deep-1
goto START
:END
SETX CLASSPATH %CD%
javac -g -cp %CLASSPATH% %NPP_FULL_CURRENT_PATH%
set /p input=Package:
SETX PACKAGE %input%
java -cp %CLASSPATH% %PACKAGE%.%NPP_NAME_PART%
cmd windows
D:\Users\User\Desktop\programozas\java\P05\konyves>SETX CLASSPATH D:\Users\User\Desktop\programozas\java\P05\konyves
SIKERÜLT: A megadott értéket sikerült menteni.
D:\Users\User\Desktop\programozas\java\P05\konyves>set /p deep=Deepness:
Deepness:1
D:\Users\User\Desktop\programozas\java\P05\konyves>if /I 1 EQU 0 goto END
D:\Users\User\Desktop\programozas\java\P05\konyves>cd ..
D:\Users\User\Desktop\programozas\java\P05>set /a deep=deep-1
D:\Users\User\Desktop\programozas\java\P05>goto START
D:\Users\User\Desktop\programozas\java\P05>if /I 0 EQU 0 goto END
D:\Users\User\Desktop\programozas\java\P05>SETX CLASSPATH D:\Users\User\Desktop\programozas\java\P05
SIKERÜLT: A megadott értéket sikerült menteni.
D:\Users\User\Desktop\programozas\java\P05>javac -g -cp NULL D:\Users\User\Desktop\programozas\java\P05\konyves\KonyvProba.java
(SIKERÜLT means SUCCESS, it managed to save the value)
THE PROBLEM
You can see the problem in the last line of the cmd window. -cp NULL
I don't understand why it's NULL, I've set it in the previous line.
These codes seem to work now, but may be unstable:
set CLASSPATH=%CD%
REM Type in the relative path deepness, for
REM example "package xxx.xxx.xxx;" means 3 deepness
REM No package means 0 deepness
set /p deep=Deepness:
set /a DEEP_FINAL=deep
:START
if /I %deep% EQU 0 goto END
cd ..
set /a deep=deep-1
goto START
:END
set CLASSPATH=%CD%
REM Compiling
javac -g -cp %CLASSPATH% %NPP_FULL_CURRENT_PATH%
REM Executing
if /I %DEEP_FINAL% EQU 0 goto NOPATH
REM May include a "cls" here
REM Type in the package name, for example
REM "package java.util;" becomes "java.util"
set /p PACKAGE=Package:
cls
java -cp %CLASSPATH% %PACKAGE%.%NPP_NAME_PART%
goto FINISH
:NOPATH
cls
java -cp %CLASSPATH% %NPP_NAME_PART%
:FINISH
NPPEXEC code:
cd d:
cd $(CURRENT_DIRECTORY)
NPP_SAVE
SET_ENV NPP_FULL_CURRENT_PATH=$(FULL_CURRENT_PATH)
SET_ENV NPP_CURRENT_DIRECTORY=$(CURRENT_DIRECTORY)
SET_ENV NPP_NAME_PART=$(NAME_PART)
npp_run cmd /k d:\Users\User\Desktop\script.cmd
This may be different for you. For example most users use the c: partition for the source files. Very important: you have to run Notepad++ as administrator! I'll test this from now on, and if it keeps working, I'll post it with more relevant tags, since it would be a Java IDE with Notepad++.
SETX does not set the environment variable in the current cmd instance, but for furure cmd instances. You need to execute a set command to set the value in the current instance.
I'm trying to set the contents of a text file (it contains a single line of text) to a variable. To do this, I'm utilizing "set /p myvariable=
SetLocal EnableExtensions EnableDelayedExpansion
Set RegExist=No
Set RegUnins=HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall
Reg Query "%RegUnins%\{########-####-####-####-############}"
If "%errorlevel%"=="0" Set RegExist=Yes
If "%regexist%"=="Yes" (
Reg Query "%RegUnins%\{########-####-####-####-############}" /V "DisplayName" >"%temp%\appnam1.txt"
Find /I "This is the value for 'DisplayName'" "%temp%\appnam1.txt" >"%temp%\appnam2.txt"
More +2 "%temp%\appnam2.txt" >"%temp%\appnam3.txt"
Set /P _appnam=<"%temp%\appnam3.txt"
Set appnam=%_appnam:~24,53%
If "%appnam%"=="This is the value for 'DisplayName'" (
Echo - Current version installed: Performing reinstall...
Start "Reinstall" /B /High /Wait "\\server\installs\reinstall.exe"
) Else (
Echo - Previous version installed: Performing upgrade...
Start "Upgrade" /B /High /Wait "\\server\installs\upgrade.exe"
)
) Else (
Echo - Existing version not found: Performing new install...
Start "Install" /B /High /Wait "\\server\installs\new.install.exe"
)
However, even though the "%temp%\appnam3.txt" file contains the correct text, when I check the variables "%_appnam%" and "%appnam%" at those points in the code, they are blank. Therefore, if the machine does have the initial registry entry, it will always perform the upgrade process instead of the reinstall process. Any suggestions? I don't understand why the "set /p" line isn't working. Thanks in advance.
PLease use delayed expansion.
I tried to reproduce your case below. It seems the variable are set delayed, If you'll try to run you script several times, the values will be set.
#echo off
setlocal enableDelayedExpansion
set regexist=Yes
If "%regexist%"=="Yes" (
Set /P _appnam=<"C:\result.csv"
echo !_appnam!
Set appnam=!_appnam:~24,53!
echo !appnam!
)
I want to have two batch files install.bat and uninstall.bat that are in the same folder as my command-line program program.exe.
I want the install.bat to add the current location of program.exe to the System Path environment variable.
Then I want the uninstall.bat to remove any paths to program.exe from the System Path environment variable.
Any ideas on how to do this?
Perhaps This earlier solution would be of assistance.
A modified file to custom-fit your situation would be
#ECHO OFF
SETLOCAL
SET "batchdir=%~dp0"
SET "batchdir=%batchdir:~0,-1%"
SET "newpath="
:temploop
SET tempfile=%random%%random%%random%
IF EXIST "%temp%\%tempfile%*" GOTO temploop
SET "tempfile=%temp%\%tempfile%"
CALL :showpath >"%tempfile%"
:: This part removes the current directory from the path
FOR /f "delims=" %%p IN ('type "%tempfile%"') DO (
CALL :addsegment "%%p"
)
DEL "%tempfile%"
IF /i "%1"=="/u" (SET "newpath=%newpath:~1%") ELSE (SET "newpath=%batchdir%%newpath%")
CALL :getresp "Apply new PATH=%newpath% [Y/N/Q]?"
IF /i "%response%"=="Y" ECHO SETX PATH "%newpath%"
GOTO :EOF
:addsegment
SET "segment=%~1"
IF /i NOT "%segment%"=="%batchdir%" SET "newpath=%newpath%;%segment%"
GOTO :eof
:getresp
SET "response="
SET /p "response=%~1 "
IF /i "%response%"=="Y" GOTO :eof
IF /i "%response%"=="Q" SET "response="&GOTO :eof
IF /i NOT "%response%"=="N" ECHO Please respond Y N or Q to quit&GOTO getresp
GOTO :eof
:showpath
ECHO(%path:;=&ECHO(%
GOTO :eof
Essentially, the two batches are the same - the only difference is that for the INSTALL version, the directory is added into the path.
For this reason, I've simply desgned it so that thisbatch would install the file, and thisbatch /u would uninstall it.
Naturally, the calling of the routine to get a final OK to change the path is optional.
I don't know which options you require for the setx, so the command is simply ECHOed. You'd need to remove the ECHO from the SETX line to activate the setting of the path variable.
Note also that SETX does not set the target variable in existing or the current CMD instances - only those created in the future.
It's also important to remember that using the uninstall feature in this routine would remove the directory from the path without regard to the requirements of any other software.