tags:

views:

2620

answers:

7

Im trying to get my commit-build.bat to exceute other bat files as part of our build process.

content of commit-build.bat:

"msbuild.bat"
"unit-tests.bat"
"deploy.bat"

Seems simple enough? But the commit-build.bat only executes the first item in the list (msbuild.bat).

I have run each of the files seperately with no problems.

+22  A: 

use

call msbuild.bat
call unit-tests.bat
call deploy.bat

When not using CALL, the current batch file stops and the called batch file starts executing. It's a peculiar behavior dating back to the early MS-DOS days

Philippe Leybaert
perfect. thanks!
+1 some seconds faster than me...
Jonathan
+6  A: 

try

call msbuild.bat
call unit-tests.bat
call deploy.bat
Jonathan
+2  A: 
call msbuild.bat
call unit-tests.bat
call deploy.bat
butterchicken
+2  A: 

To call a .bat file within a .bat file, use

call foo.bat

(Yes, this is silly, it would make more sense if you could call it with foo.bat, like you could from the command prompt, but the correct way is to use call.)

Zifre
+1  A: 

looking at your filenames, have you considered using a build tool like nant or ant (the java version). You'll get a lot more control than bat files

David Archer
Thanks for the tip!
Actually, this is probably the most useful answer to the question so far... :-)
Zifre
+11  A: 

All the other answers are correct: use call.

History

In ancient dos versions it was not possible to recoursively execute batch files. Then the call command was introduced that called another cmd shell to execute the batch file and returned execution back to the calling cmd shell when finished.

Obviously in later versions no other cmd shell was necessary anymore.

In the early days many batch files depended on the fact that calling a batch file would not return to the calling batch file. Changing that behaviour without additional syntax would have broken many systems like batch menu systems (using batch files for menu structures).

As in many cases with Microsoft, backward compatibility therefore is the reason for this behaviour.

Tips

If your batch files have spaces in their names, use quotes around the name:

call "unit tests.bat"

By the way: if you do not have all the names of the batch files, you could also use for to do this: (dfoes not garantee the correct order of batch file calls, follows order of file system)

FOR %x IN (*.bat) DO call "%x"

You can also react on errorlevels after a call. Use

exit /B 1   # or any other integer value in 0..255

to give back an errorlevel. 0 denotes correct execution. In the calling batch file you can react using

if errorlevel neq 0 <batch command>

Use if errorlevel 1 if you have a an older Windows then NT4/2000/XP to catch all errorlevels 1 and greater.

To control the flow of a batch file, there is goto :-(

if errorlevel 2 goto label2
if errorlevel 1 goto label1
...
:label1
...
:label2
...

As others pointed out: have a look at build systems to replace batch files.

Ralph Rickenbach
agreed, but the loop could, in this case, process the files in the wrong (alphabetical?) order
David Archer
A: 

You are calling multiple batches in an effort to compile a program. I will take for granted that: 1) if an error occure, the program within the batch will give an errorlevel 2) if an error occure, you want to know about it.

for %%b in ("msbuild.bat" "unit-tests.bat" "deploy.bat") do call %%b|| exit /b 1

'||' testing for any errorlevel higher than 0, this way all batches are called in order, but will stop at any error, leaving the screen as it is for you to see any error message.

Jay