I have 2 projects for which I am trying to create a generic Post-Build event batch file.
Here is the command in Visual Studio:
Post-Build event
if $(ConfigurationName) == Release ("$(ProjectDir)PostBuildRelease.bat" "$(TargetDir)" #(VersionNumber) "$(TargetFileName)" "$(TargetName)")
So I am calling the file PostBuildRelease.bat with 4 parameters:
Bin\Release Directory
Project Version
File Name With Extension
File Name Without Extension
Project 1
This works perfectly with this batch script:
CMD
SET parameter=%1 REM Full path to new bin\release\
SET parameter=%2 REM Full Version Number
SET parameter=%3 REM File name + extension
SET parameter=%4 REM File name - extension
SET "productionpath=Z:\Unused\Apps\LyncVdiChecker\"
MOVE %productionpath%%3 %productionpath%"_archive\"%4"."%DATE:~0,2%%DATE:~3,2%%DATE:~6,4%"-"%2
XCOPY %3 %productionpath%
Where the assembly is copied to Z:\Unused\Apps\LyncVdiChecker\ and the existing version copied to _archive in the same folder. The archived version also has the date and version number replace the file extension.
Project 2
This batch script also works perfectly (it does the same thing but in a different folder and for a different project):
CMD
SET parameter=%1 REM Full path to new bin\release\
SET parameter=%2 REM Full Version Number
SET parameter=%3 REM File name + extension
SET parameter=%4 REM File name - extension
SET "productionpath=Z:\Unused\Apps\IT Support App\"
MOVE "Z:\Unused\Apps\IT Support App\"%3 "Z:\Unused\Apps\IT Support App\_archive\"%4"."%DATE:~0,2%%DATE:~3,2%%DATE:~6,4%"-"%2
XCOPY %3 "Z:\Unused\Apps\IT Support App"
However, if I try using the same script from Project1 (the more generic version) in Project2, I get errors, even though the 2 scripts are equivalent:
Errors
The command "if Release == Release ("C:\Users\Seb.Kotze\Source\Repos\Applications\ITSelfHelp\ITHelp\PostBuildRelease.bat" "C:\Users\Seb.Kotze\Source\Repos\Applications\ITSelfHelp\ITHelp\bin\Release\" 2.0.6100.20905 "IT Self Help.exe" "IT Self Help")" exited with code 4.
Output Window:
The syntax of the command is incorrect.
Invalid number of parameters
This error is rather unhelpful, so I tried commenting out the 2 lines MOVE and XCOPY and build again:
Removed MOVE
Same error as above.
Output window:
Invalid number of parameters
Remove XCOPY
No Visual Studio Error, but this appears in the output window:
The syntax of the command is incorrect.
Parameter Output
When I echo out the parameters being used in Project2, everything seems to be in order:
"Path\to\Bin\Release"
2.0.6100.21082
"IT Self Help.exe"
"IT Self Help"
Z:\Unused\Apps\IT Support App\
How can I debug this issue? How is it possible that my script runs fine without any issues, but when run against a different project none of the commands are recognised? Any help with this is much appreciated!
You should normalize all your arguments, so they don't contain outer quotes.
Then you can use them in a reliable way.
The syntax set "variable=%~1" avoids outer quotes in the variable itself.
set "TargetDir=%~1"
set "VersionNumber=%~2"
set "TargetFileName=%~3"
set "TargetName=%~4"
SET "productionpath=Z:\IT Support App\"
set "dateStamp=%DATE:~0,2%%DATE:~3,2%%DATE:~6,4%"
MOVE "Z:\IT App\%TargetFileName%" "Z:\IT App\_archive\%TargetName%.%dateStamp%-%VersionNumber%"
XCOPY "%TargetFileName%" "Z:\IT App"
The problem is that the script is messing with the double quotes resulting in invalid paths and invalid number of arguments passed. When dealing with paths built dynamically, it's best to strip any existing " from the parts, and after the path is complete, surround it in ".
Dealing with batch arguments is explained on MSDN. Same thing for variables can be found on SS64.
I've played a bit with the file, and I was able to run it (from command line). The changes you should make in your (Project1) file:
SET productionpath="Z:\Unused\Apps\LyncVdiChecker\"
MOVE "%productionpath:"=%%~3" "%productionpath:"=%_archive\%~4.%DATE:~0,2%%DATE:~3,2%%DATE:~6,4%-%~2"
XCOPY "%~3" "%productionpath:"=%"
I moved the " from the productionpath line to the beginning of its contents. That way will work with paths that contain SPACE s.
In the MOVE and XCOPY lines, I did what I explained above: even if the syntax is not that clear, it's more robust (the last "%productionpath:"=%" could be simple written as %productionpath%, but I left it in the the 1st form for consistency).
Note: You could remove the CMD command at the beginning of your batch, since it starts a new cmd instance(process) that doesn't end.
I found a solution to this, but I am still not sure what the cause was.
I suspect it has something to do with either one of:
Spaces in productionpath causing the command parameter declaration to escape
Quotes around one or more of the parameters creating a non-existent file path
After trying out a few changes to the script, I found that changing the productionpath declaration to SET productionpath="Z:\Unused\Apps\IT Support App\" solved the issue:
CMD
SET parameter=%1 REM Full path to new bin\release\
SET parameter=%2 REM Full Version Number
SET parameter=%3 REM File name + extension
SET parameter=%4 REM File name - extension
SET productionpath="Z:\Unused\Apps\IT Support App\"
MOVE "Z:\Unused\Apps\IT Support App\"%3 "Z:\Unused\Apps\IT Support App\_archive\"%4"."%DATE:~0,2%%DATE:~3,2%%DATE:~6,4%"-"%2
XCOPY %3 "Z:\Unused\Apps\IT Support App"
Making the same change to the Project1 script did not cause that to break either, so this seems safe.
Update
After reading some of the other answers, I amended the script once again to the following:
CMD
SET "TargetDir=%~1"
SET "VersionNumber=%~2"
SET "TargetFileName=%~3"
SET "TargetName=%~4"
SET "ProductionPath=Z:\Unused\Apps\IT Support App\"
SET "ArchivePath=%ProductionPath%_archive\"
SET "DateStamp=%DATE:~0,2%%DATE:~3,2%%DATE:~6,4%"
MOVE "%ProductionPath%%TargetFileName%" "%ArchivePath%%TargetName%.%DateStamp%-%VersionNumber%"
XCOPY "%TargetFileName%" "%ProductionPath%"
Notice the "normalisation" of the paramaters - this removes all quotation marks from their values.
Also now using named parameters.
Related
I have a program shortcut on my desktop with the target set to:
"c:\folder\program.exe"
When drag'droping a folder on to this I get:
"c:\folder\program.exe" d:\myfolder
This used to work well for many years, but a newer version of the program only excepts paths with quotes like:
"c:\folder\program.exe" "d:\myfolder"
Windows automatically adds the quotes for paths with spaces, but not if the paths do not contain any spaces.
How can I force Windows to add the quotes or is there any easy way to change the target to enclose drag'dropped paths with quotes?
Thanx for reading, Needly
You can try to add an explicit parameter placeholder %1 in the target field:
"c:\folder\program.exe" "%1"
This should work since Windows does nothing else than to fill the drag&dropped file or folder path into %1 ("parameter one") or %2 etc. if a list of files/folders was dropped.
HTH, GL, HF :)
I'm trying to change the output file name, fOut, in a bat file, but have no luck so far.
I'm developing on Windows 7 and will deploy the code to Windows 2003 server.
The code looks like this:
set fName=%1
set fExt=%fName:~-5,-1%
set fOut=%fName:~0,-5%_PAD%fName:~-5%
Examples of fOut:
abcdc2evv_PAD.dat
abcdefgh33ij_3737_PAD.dat
How can I change fOut to get the following file names?
A. Adding FMT_ at the beginning of the file name:
FMT_abcdc2evv_PAD.dat
FMT_abcdefgh33ij_3737_PAD.dat
B. Adding FMT_ at the beginning of the file name and remove _PAD before .dat:
FMT_abcdc2evv.dat
FMT_abcdefgh33ij_3737.dat
Addendum:
Just one argument is passed to the bat file: path + file name.
x.bat "C\test\xxx.dat"
In the bat file:
#echo ^-input file name = ^%1
set fName=%1
set fExt=%fName:~-5,-1%
set fOut==%fName:~0,-5%_PAD%fName:~-5%
I don't know if I'm missing something obvious - it's not clear what the input to this script is.
However adding FMT_ before should just be a case of changing:
set fOut=%fName:~0,-5%_PAD%fName:~-5%
to:
set fOut=FMT_%fName:~0,-5%_PAD%fName:~-5%
or if you want to put the FMT_ version into another variable, then:
set bob=FMT_%fOut%
As for removing _PAD, can you not just repeat the SET fOut line without the _PAD? This would seem to be the simplest way to do it. In fact, removing _PAD and prefixing FMT_ would seem to simply be this:
set bob=FMT_%1
if you want to remove pad just take it out of your assignment statement
you have:
set fOut=%fName:~0,-5%_PAD%fName:~-5%
you want:
set fOut=%fName:~0,-5%fName:~-5%
to add FMT_ just add it at the beginning of the file name:
set fOut=%FMT_%fName:~0,-5%_PAD%fName:~-5%
If you want to separate the filename from the extension, don't mess around counting chars; there is a built-in method (described in for /?):
echo Filename=%~n1
echo Extension=%~x1
echo resulting file="FMT_%~1"
REM without _PAD, following with _PAD
set filename="FMT_%~n1_PAD%~x1"
If there is really need to remove _PAD (as Chris already noted, you are explicitely adding it with your code), just replace _PAD. with . only:
set filename=%filename:_PAD.=.%
I am writing a batch script which will copy a file from a folder into the C:\ drive:
#ECHO ON
COPY C:\RANDOMFILES\Weekly Reprort_Hew*.xls C:\Weekly Reprort_Hew???????????.xls
The filename in the RANDOMFILES folder is: Weekly Reprort_Hew, 6-29-2014 10-30-00 PM-642.xls (The date and time and the number at the end will always change so I used the * in the filename being copied in the script)
When I run the batch script, I get the following message:
c:\RANDOMFILES>COPY C:\RANDOMFILES\Weekly Reprort_Hewlett*.xls C:\Weekly Reprort
_Hewlett???????????.xls
The system cannot find the file specified.
How can I fix the issue?
You need double quotes to handle spaces etc. Double check the spelling too.
#ECHO ON
COPY "C:\RANDOMFILES\Weekly Reprort_Hew*.xls" "C:\Weekly Reprort_Hew???????????.xls"
Don't know why it is not working - is it hidden? Maybe the spaces in the name?
The following will work though:
FOR %%I in (C:\RANDOMFILES\Weekly Reprort_Hew*.xls) DO COPY "%%I" C:\
The destination file name isn't necessary; if not otherwise specified, it will remain unchanged provided the destination is different. That may be why the plain COPY command isn't working.
Also:
"It is an not-so-well-known fact that the question mark wildcard will match exactly one character only when the wildcard does not appear at the end of a file name. " from http://www.thefriendlycoder.com/2011/11/24/batch-file-gotcha-question-mark-wildcard/
I have a batch file that I use to copy a folder and it's contents to a new location, it also creates the folder name based on the date and time (and this works):
SET TODAY=%DATE:/=-%
SET NOW=%TIME::=-%
XCOPY /S /Y "C:\BuildAgent\temp\buildTmp" "C:\Automation Results\%TODAY%_%NOW%\"
I added a new Configuration Step to my Team City setup, to include this batch file. The build step is a Command Line - Custom Script:
But this has an adverse effect on the TC Agent Requirements and I cannot start my TC builds:
This issue seems to be related to TC Implicit Requirements:
http://confluence.jetbrains.com/display/TCD8/Agent+Requirements
"Implicit Requirements
Any reference (name in %-signs) to an unknown parameter is considered an "implicit requirement". That means that the build will only run on the agent which provides the parameters named. Otherwise, the parameter should be made available for the build configuration by defining it on the build configuration or project levels."
How can I get around this TC conflict with % symbol which I need in my batch file?
Use %% instead of %
SET TODAY=%%DATE:/=-%%
SET NOW=%%TIME::=-%%
XCOPY /S /Y "C:\BuildAgent\temp\buildTmp" "C:\Automation Results\%%TODAY%%_%%NOW%%\"
This will ensure the variables are treated as batch file variables instead of TeamCity variables.
put the contents of your build script inside a file, eg copy.bat and call this batch file from TeamCity
Addtionally, change from Custom script to Executable with parameters
I am trying to run following code through cmd.
"C:\Program Files\Beyond Compare 2\BC2.exe" #"C:\New Folder\Myscript.txt" "C:\New Folder\A.txt" "C:\New Folder\B.txt"
This will actually open Beyond Compare and compare two text files.
The problem is ,when i run this code on cmd[Version 6.1.7601] it runs correctly but when i run it on version 5.1.2600 , it shows a fatal error :- Could not find C:/New .
I understand the error is due to space in the name(New Folder) , but why is it running fine on Win 7 .Does two versions of cmd have some difference in the way they accept arguments ?
Content of Myscript.txt :-
file-report layout:side-by-side &
options:display-all &
output-to:%3 output-options:html-color,wrap-word %1 %2
I can't explain why it is not working, but I have some potential solutions
1) Run with the current directory at the location of the files
Since the space is in the folder name, and all files are in the same location, you can avoid the folder name by simply changing directory to that folder and using a relative path.
pushd "c:\new folder"
"C:\Program Files\Beyond Compare 2\BC2.exe" #Myscript.txt A.txt B.txt
Of course this will not work if your files are in different locations, or if the file names have spaces (assuming spaces are really the problem)
2) Use the short 8.3 names
I hate the short 8.3 names because of the many bugs associated with them. But sometimes they can be useful.
You can get the short name of a file or folder by using DIR /X. Or you could use the following in a batch script to programmatically get the short paths.
for %%A in ("C:\New Folder\Myscript.txt") do (
for %%B in ("C:\New Folder\A.txt") do (
for %%C in ("C:\New Folder\B.txt") do (
"C:\Program Files\Beyond Compare 2\BC2.exe" #"%%~fsA" "%%~fsB" "%%~fsC"
)
)
)
Of course the above will not do any good if short 8.3 names are disabled on your volume.
If i understood correctly Raymond's comment ,the parsing is done by Beyond Compare not cmd.
I tried to use
file-report layout:side-by-side &
options:display-all &
output-to:"%3" output-options:html-color,wrap-word "%1" "%2"
and it worked fine on XP but shows error on windows 7 .It seems the beyond compare behaves differently for different OS.