2

I have a simple bash shell script which is driving me bonkers. All I want to do is run a command which returns a result which I will then use in another command. The result of the first command returns a location on my hard drive with spaces. Here's what I have...

# Get list of virtual machines.  VMname will hold the address of the .vmx file
VMname=`./vmrun list`
echo $VMname

# Get list of snapshots
command="./vmrun listSnapshots "
command=$command"'"
command=$command$VMname
command=$command"'"
echo $command
snapshotList=`$command`

It looks like when I try to append the single quotes around the $VMname it only appends to the left, ie I only the left single quote is appended. Is there something silly I am doing wrong? This really is driving me crazy!

Gilles 'SO- stop being evil'
  • 807,993
  • 194
  • 1,674
  • 2,175
BON
  • 123
  • 5
  • Don't forget to accept the answer you think best solves your problem. Do so by clicking the checkmark to the left of the answer. Welcome to the site! – amphetamachine Aug 26 '11 at 00:37

3 Answers3

3

All you need is:

VMname=$(./vmrun list)
snapshotList=$(./vmrun listSnapshots "$VMname")

If you don't need the intermediate variable VMname, you can also use:

snapshotList=$(./vmrun listSnapshots "$(./vmrun list)")

Use $() instead of `` (unless you're using a very old shell that doesn't understand the former). Nesting of $() constructions is easier.

Stéphane Gimenez
  • 28,527
  • 3
  • 76
  • 87
  • Quotes? .. something="$(. . .)" – Peter.O Aug 24 '11 at 13:12
  • 2
    @fred. Useless, no word-splitting is performed during variable assignation. – Stéphane Gimenez Aug 24 '11 at 13:17
  • @fred, as Stéphane says, they're not needed for assignment, but on the other hand they won't hurt. I learned this lesson just recently. – glenn jackman Aug 24 '11 at 14:17
  • 1
    @glennjackman: Actually they CAN hurt as fred just recently found out: [Why does the exclamation mark `!` sometimes upset bash?](http://unix.stackexchange.com/q/19252). The thing is to understand when to use them and when not to. – Caleb Aug 24 '11 at 21:41
  • 1
    @fred Lesson 1 is to always put the quotes. Lesson 2 is what happens without them and how it can occasionally be useful. Lesson 3 is that assignments and `case` expressions have implicit double quotes already, e.g. `foo=$(bar)` means the same as `foo="$(bar)"` (the reason is that these contexts allow a single word, so word splitting wouldn't make sense). Note that this does not extend to `export foo="$(bar)"`. – Gilles 'SO- stop being evil' Aug 24 '11 at 22:07
2

Just use proper quoting and string security.

You could even simplify it a little and shore up the quoting by not executing variables:

# Get list of virtual machines.  VMname will hold the address of the .vmx file
VMname="$(./vmrun list)"
echo "$VMname"

# Get list of snapshots
echo "./vmrun listSnapshots '$VMname'"
snapshotList="$(./vmrun listsnapshots "$VMName")"
amphetamachine
  • 5,388
  • 2
  • 34
  • 41
0

Oh boy. Why not just write this?

command="./vmrun listSnapshots '$VMname'"

Šimon Tóth
  • 8,098
  • 12
  • 40
  • 67
  • I tried that, but after pulling my hair out I think I have found the answer to the problem... I looks like when I run the command vmrun list, it adds a weird unprintable character to the end that is acting like a carrage return, when I then add the second single quote to the end, it begins to write on the same line. I have no idea why. I am now piping ./vmrun list into | tail -1 | sed 's/[^a-zA-Z0-9\. ]//g' and it seems to get rid of it... Thanks for replying though!! – BON Aug 24 '11 at 09:53