Reputation: 958
A predecessor of mine installed a crappy piece of software on an old machine (running Linux) which I've inherited. Said crappy piece of software installed flotsam all over the place, and also is sufficiently bloated that I want it off ASAP -- it no longer has any functional purpose since we've moved on to better software.
Vendor provided an uninstall script. Not trusting the crappy piece of software, I opened the uninstall script in an editor (a 200+ line Bash monster), and it starts off something like this:
SWROOT=`cat /etc/vendor/path.conf`
...
rm -rf $SWROOT/bin
...
It turns out that /etc/vendor/path.conf
is missing. Don't know why, don't know how, but it is. If I had run this lovely little script, it would have deleted the /bin
folder, which would have had rather amusing implications. Of course this script required root
to run!
I've dealt with this issue by just manually running all the install commands (guh) where sensible. This kind of sucked because I had to interpolate all the commands manually. In general, is there some sort of way I can "dry run" a script to have it dump out all the commands it would execute, without it actually executing them?
Upvotes: 15
Views: 29259
Reputation: 438123
bash
does not offer dry-run functionality (and neither do ksh
, zsh
, or any other shell I know).
It seems to me that offering such a feature in a shell would be next to impossible: state changes would have to be simulated and any command invoked - whether built in or external - would have to be aware of these simulations.
The closest thing that bash
, ksh
, and zsh
offer is the ability to syntax-check a script without executing it, via option -n
:
bash -n someScript # syntax-check a script, without executing it.
2
in bash
3
in ksh
1
in zsh
Separately, bash
, ksh
, and zsh
offer debugging options:
-v
to print each raw source code line[1]
to stderr before it is executed.
-x
to print each expanded simple command to stderr before it is executed (env. var. PS4
allows tweaking the output format).
Combining -n
with -v
and/or -x
offers little benefit:
With -n
specified, -x
has no effect at all, because nothing is being executed.
With -n
specified, -v
will effectively simply print the source code.
-n
always includes the offending line number.[1] Typically, it is individual lines that are printed, but the true unit is however many lines a given command - which may be a compound command such as while
or a command list (such as a pipeline) - spans.
Upvotes: 18
Reputation: 107040
You could try running the script under Kornshell. When you execute a script with ksh -D
, it reads the commands and checks them for syntax, but doesn't execute them. Combine that with set -xv
, and you'll print out the commands that will be executed.
You can also use set -n
for the same effect. Kornshell and BASH are fairly compatible with each other. If it's a pure Bourne shell script, both Kornshell and BASH will execute it pretty much the same.
You can also run ksh -u
which will cause unset shell variables to cause the script to fail. However, that wouldn't have caught the catless cat of a nonexistent file. In that case, the shell variable was set. It was set to null.
Of course, you could run the script under a restricted shell too, but that's probably not going to uninstall the package.
That's the best you can probably do.
Upvotes: 9