2

How do you store, and later execute, a command with redirection and and a pipe? (And is it the pipe, or the redirection, or both, that's causing my problem?)

I tried to print the urxvt version in a script, as well as echo the actual command.

The command I use to get the version is urxvt -help 2>&1 | head -n 2 - for some reason, urxvt prints help to stderr; as for the head, only the two first rows contain version and configuration data.

In the shell, it works great, but, in the script (isolated the problem, below), it seems the third line loses its head:

#!/bin/bash

VER_URXVT='urxvt -help 2>&1 | head -n 2'
echo $VER_URXVT
$VER_URXVT
10
  • 1
    You probably meant to use backticks: ` instead of single quotes: ' - their meaning is quite different.
    – peterph
    Commented Dec 22, 2012 at 22:45
  • @RahulPatil: That doesn't seem to work. Commented Dec 22, 2012 at 22:48
  • @peterph: What I can see, that doesn't work. Commented Dec 22, 2012 at 22:49
  • You don't need the third line if you use backticks. Commented Dec 22, 2012 at 22:56
  • echo $VER_URXVT | bash Commented Dec 22, 2012 at 23:00

4 Answers 4

4

Use:

VER_URXVT=`urxvt -help 2>&1 | head -n 2`

which is the same as:

VER_URXVT=$(urxvt -help 2>&1 | head -n 2)

to get the first two lines of urxvt help into VER_URXVT.

If you want to evaluate the command in shell variable, you should use eval:

VER_URXVT='urxvt -help 2>&1 | head -n 2'
eval $VER_URXVT
3

I keep on thinking functions are better than evaluing variables

#!/bin/bash

version() { uname -a;}
wm() { head -n1 <(openbox --version);}
for f in $(compgen -A function)
do declare -f $f | sed '1,2d; $d'
   $f
done
1
  • Hi Watael , nice info, if possible put comment :) Commented Dec 24, 2012 at 11:11
2

don't ever use eval unless you really know what will be evaled.

instead use a function.

#!/bin/bash

ver_urxvt() { urxvt -help 2>&1 | head -n 2;}
declare -f ver_urxvt | sed '1,2d; $d'
ver_urxvt

but it's silly, as it is a waste of time to print those informations.

if you want to debug your script use the -x option of the set builtin

7
  • 1
    You can take a look at the script in which I need this. So you see, individual functions is not an option. As for what you think is silly or not, that's irrelevant as this is a Q&A site. Downvote. Commented Dec 22, 2012 at 23:23
  • @UlrichDangel: When I said I needed it, that referred to a general solution, as opposed to individual functions for all commands. As for eval, I don't know how that differs from backticks/$(), but if you care to explain why it is considered unsafe, sure, I'll change it. Commented Dec 22, 2012 at 23:35
  • You ask. I answer. The answer is an opinion on how things should be handled, instead of your non-working, and counter-productive idea. Q&A can also show what are best practices, and tell what are worst. btw: no "hi", no "please", no "thanks"... do you think we owe you something? learn to live with others, that'll improve your coding too.
    – watael
    Commented Dec 23, 2012 at 0:14
  • What on earth are you talking about?! 1. The script works exactly as intended with the eval solution, 2. ... which I thanked, if you read the comment above, 3. the moderators frequently remove greetings, so I've stopped using them, although I fail to see how that's a big issue, and 4. do you actually expect me to thank you after calling my question silly, and my wish to print information "a waste of time"? Commented Dec 23, 2012 at 0:26
  • ah, ok! you misunderstood me: you don't waste my time, you uselessly occupy the resources of the machine for printing such informations.
    – watael
    Commented Dec 23, 2012 at 0:41
1

You need to use the eval expression

#!/bin/bash

VER_URXVT='urxvt -help 2>&1 | head -n 2'
echo $VER_URXVT
eval $VER_URXVT

From the man page eval

          The  args  are read and concatenated together into a single com-
          mand.  This command is then read and executed by the shell,  and
          its  exit status is returned as the value of eval.  If there are
          no args, or only null arguments, eval returns 0.
1
  • Thanks a lot, this is exactly what I wanted. Thanks not only for your solution, but also for you taking your time understanding the question. Commented Dec 22, 2012 at 23:03

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .