Thanks for the feedback. You'll probably find out a lot
more about batch files as you go on, especially when it
comes to the "set" and "for" commands. Try this from
a Command Prompt just for fun:
echo Today is %date:~0,3%
or
echo The time is %time::=.%
About testing equality without surrounding quotes or brackets
if %result%==OK
you must make sure that neither side of the = sign is ever blank.
If there is the slightest possibility, add some extra characters.
If you don't then the batch file will fail.
Hi Pegasus,
Great batch template! Thanks.
I tested all the features. I was surprised by a couple of things,
like the "/i" switch and the use of OK without surrounding quotes.
But the piece de resistance was the "start" command, which you
mentioned earlier but I hadn't picked up on right away. Along with the
other improvements, I got to it now and got exactly what I've got
exactly what I want:
Startup.bat
----------------
START "BAT1 Commands" Bat1.bat
START "BAT2 Commands" Bat2.bat
: etc
let's me double-click its name and get precisely the command windows I
want to support my Ruby/Rails application development efforts.
It's embarrassing to admit that I've used Windows' bat files for
decades but never noticed some of the features you've mentioned.
Again, thanks for your expert help.
Best wishes,
Richard
Pegasus (MVP) wrote:
When you ask about combining your various batch files
into the one file then you're spot on. The general idea is:
- Have all code for the one project in one single batch file.
- Make it highly structured.
- Avoid spaghetti code.
- Set global variables.
- Add lots of comments.
If you adhere to these rules then you will find that your
batch files become much more robust and are very easy
to maintain. You also skirt around the environmental variable
issue that triggered this thread.
I have seen contiguous (rather than modular) batch files that
extend over 300 lines, with numerous goto statements that
resemble the path taken by a hare in full flight. They are almost
impossible to maintain. In a structured form even a beginner
could debug and modify them.
Here is how I structure all my batch files:
=============================
@echo off
goto Start
--------------------------------------------
Program description:
Parameters:
Prerequisites:
Version:
Author:
Date:
--------------------------------------------
:Start
set SourceDir=D:\Some Folder
set TargetDir=E:\Other folder
call :Sub1
call :Sub2 %name%
if /i "%result%"==OK call :Sub3
goto :eof
--------------------------------------------
Some comments about Sub1
--------------------------------------------
:Sub1
Code for Sub1
goto :eof
--------------------------------------------
Some comments about Sub2
--------------------------------------------
:Sub2
Code for Sub2
goto :eof
message
Hi Pegasus,
OK, I've simplified these scripts substantially, e.g.
C130_StartLocalWebServer.bat
(down to 8 lines instead of 20 because the error checking no longer
needed)
---------------------------------------------
@echo off
call CreatePathAndSymbols.bat _Pf Prmp
echo ::
echo :: Starting WebBrickServer
echo :: in %AppDir%
echo ::
@echo on
ruby script/server
That's just what I wanted.
I appreciate the observations you made, i.e.:
1. Checking for existence of %2 obviates the need to check for %1
2. :EOF is built-in, obviating the need to define a symbol at the
end
of the script
Mainly, I rely on 3 of my ~20 batch commands to start-up testing a
Ruby/Rails app. I keep those command windows open for the duration of
a testing/developing session.
Heretofore, I opened three command windows and exectuted two bath
commands in each.
With your help, I've cut that down to one command in each.
Is there a way to combine that into a single batch command, e.g.
CombineCommand.bat (pseudocode)
---------------------------------
run cmd.exe; execute batch1.bat
run cmd.exe; execute batch2.bat
run cmd.exe; execute batch3.bat
and achieve the same result I'm getting now?
Again, thanks for your help.
Regards,
Richard
Pegasus (MVP) wrote:
Wow! This is one complex script!
Unfortunately it would take me far too long to analyse and
reverse-engineer it. There is certainly scopy for simplification.
Here are a few minor ones:
Of the two successive statements
if (%1) == () goto PARM_MISSING
if (%2) == () goto PARM_MISSING
the first one is superfluous. If %2 is blank then %1
must be blank too!
You have lots of "goto EOJ" statements. Replace them
with "goto EOF". This is an inbuilt label that does not
need to be defined.
You write
%RubyDisk%
cd %AppDir%
This should be simplyfied to
cd /d %AppDir%
(where %AppDir% now includes the drive letter).
However, this is just cosmetic stuff. I suspect that the whole
set of batch files can be condensed to perhaps twenty lines
in a single batch file, which will solve your variable problems
and will make debugging and further development much, much
easier. You would get a short, sharp and robust batch file.
To suggest how it could be done requires your functional
description of what you're attempting to do. But then you may
decide that "GO"s suggestion solves your problem, in which
case I will leave you to it.
message
Hi Pegasus,
Thanks for responding.
I've got PATH= ... ; K:\_Projects\Ruby\__Links; ...
Below are four batch files. Typically, when I boot up and want to
work
on the Prmp project, I open several Command windows in
succession.
The first thing I do with each of them is drag in the name of and
execute a couple of batch commands, e.g.
1a. Drag the name of C000_CreateSymbols.bat into a new command
window
1b. Click the command window to give it focus
1c. Press Enter to execute the command, where upon
cwd=K:\_Projects\Ruby\_Pf\Prmp
(and symbols RubyDisk, RubyProj, CliName and AppName are
defined)
2a. Drag the name of C130_StartLocalWebServer.bat into the command
window
2b. Click the command window to give it focus
2c. Press Enter to execute the command,
whereupon the ruby starts up the WEBrick web server.
Then I open a second command window, repeat the compound step 1
and
follow that with a command step 2 with a different batch command,
e.g.
C160_StartBreakpointer.bat, which starts a listener for any
breakpoint
command executed in my Ruby/Rails application and starts an
interactive
ruby session initialized with the application's state.
BTW, as I was documenting my environment for you, it occurs to me
that
I can install an invocation of the followin line at the start of
all
my
commands (other than C000_...) and ignore C000_... completely (and
eliminate all the error traps):
CreatePathAndSymbols.bat _Pf Prmp
I think that'll work. But you can probably show a less kludgy way
to
do the whole thing.
Best wishes,
Richard
K:\_Projects\Ruby\__Links\CreatePathAndSymbols.bat
--------------------------------------------------------------------------
------
@echo off
::: Call with arguments ClientName and ApplicationName
:: Note: Names may not include spaces nor most special characters
::
if (%1) == () goto PARM_MISSING
if (%2) == () goto PARM_MISSING
::
set RubyDisk=K:
set RubyProj=%RubyDisk%\_Projects\Ruby
::
set CliName=%1
set AppName=%2
::
set CliDir=%RubyProj%\%CliName%
set AppDir=%CliDir%\%AppName%
::
%RubyDisk%
cd %AppDir%\
::
path=%CliDir%\Cmds\;%path%
goto EOJ
::
ARM_MISSING
echo ::
echo :: ERROR ERROR ERROR ERROR
echo :: Usage: %0 ClientName ApplicationName
echo :: ERROR ERROR ERROR ERROR
echo ::
:EOJ
K:\_Projects\Ruby\_Pf\Cmds\C000_CreateSymbols.bat
--------------------------------------------------------------------------
------
@echo off
CreatePathAndSymbols.bat _Pf Prmp
pause
C130_StartLocalWebServer.bat
---------------------------------------------
@echo off
if [%CliDir%] == [] goto ERROR
if [%AppDir%] == [] goto ERROR
if [%RubyDisk%] == [] goto ERROR
%RubyDisk%
cd %AppDir%
echo ::
echo :: Starting WebBrickServer
echo :: in %AppDir%
echo ::
@echo on
ruby script/server
@echo off
goto EXIT
:ERROR
@echo ERROR ERROR ERROR ERROR
@echo Symbol "AppDir", etc., not defined!
@echo ... run CreatePathAndSymbols.bat in your Command Window
@echo ERROR ERROR ERROR ERROR
:EXIT
C160_StartBreakpointer.bat
----------------------------------------
@echo off
if [%CliDir%] == [] goto ERROR
if [%AppDir%] == [] goto ERROR
if [%RubyDisk%] == [] goto ERROR
%RubyDisk%
cd %AppDir%
echo ::
echo :: Starting a Breakpointer
echo ::
@echo on
ruby script/breakpointer
@echo off
goto EXIT
:ERROR
@echo ERROR ERROR ERROR ERROR
@echo Symbol "AppDir", etc., not defined!
@echo ... run CreatePathAndSymbols.bat in your Command Window
@echo ERROR ERROR ERROR ERROR
:EXIT
Pegasus (MVP) wrote:
in
message
I've got a .bat file that sets a number of symbols
(environment
vars)
that are useful in a number of other command windows
associated
with
one of several projects. Right now, I operate by
1 opening a command window
2 draging the name of the symbol-setting bat file into the new
cmd
window and pressing Enter
3 draging the name of one of my utility bat files in the cmd
window
and
pressing Enter
4 proceeding manually entering other commands as needed.
I'd like to eliminate step 2 by invoking the symbol-setter at
the
beginning of every other utility file. I tried this by using
"cmd
/c
symbol-setter.bat" to no avail. I believe that fails because
the
"cmd
/c" command starts a new session in which to set local env.
vars
and
then ends, never communicating with the invoking session.
The best solution I can conceive of is to manually write a
.reg
file
appropriate to each project in which I want persistant env.
vars,
thus
only needing to invoke that once at the inception of a
project,
maybe
with another one to delete all such entries should the project
ultimately be destroyed.
Any comments?
Regards,
Richard
It seems you're trying to combine two different techniques
with each other: Running batch files (which is fundamentally
a Command Prompt activity) and dragging files (which is
a GUI activity). A better way would be to run a single batch
file and perhaps specify some parameters for it.
To obtain correct advice about your environmental variables
you should post the contents of your batch file. You should
also state if the variables are supposed to be valid within
the context of this batch file only, within the context of the
Command Prompt session it runs or within the context of
all programs, regardless of when they are launched.