0

I am new to the Linux environment. After a quick search I could not find a helpful question about the $ operator used in bash scripting. I do not know if this question relates more to the Ubuntu (or other) flavor of Linux, or my oh-so-small programming experience with it.

Basically I thought the ~ operand in Linux was perfectly equivalent to the string '/home/username'. If I try to execute a program after a certain delay by using a bash script and an external C-based program, I am so stuck: I cannot make use of the ~ operand and keep the program indifferent to the user (though the rest of the file path must be respected).

Please provide comments to the following (finding the getIdle sources is left to the reader):

#!/bin/bash
# call.sh

idle=false
idleAfter=30000     # consider idle after 30000 ms

# EXPLAIN THIS - Begin
# Strings that work
# str_getIdle_exe='/home/seb/Documents/Seb/Prjcts/Idle/getidle/src/getIdle'
# str_getIdle_exe="/home/seb/Documents/Seb/Prjcts/Idle/getidle/src/getIdle"

# Strings that don'work
str_getIdle_exe='~/Documents/Seb/Prjcts/Idle/getidle/src/getIdle'
# str_getIdle_exe="~/Documents/Seb/Prjcts/Idle/getidle/src/getIdle"
# EXPLAIN THIS - End


while true; do
  idleTimeMillis= $str_getIdle_exe
  echo $idleTimeMillis  # just for debug purposes.
  if [[ $idleTimeMillis -gt $idleAfter && $idle = false  ]] ; then
    echo "start idle"   # or whatever command(s) you want to run...
    idle=true
    /usr/bin/xflock4
  else  # just for debug purposes.
    echo "not there yet..."
  fi

  if [[ $idleTimeMillis -lt $idleAfter && $idle = true ]] ; then
    echo "end idle"     # same here.
    idle=false
  fi
  sleep 1      # polling interval

done

What I am trying to explain is: why the two different strings above execute nicely in a shell, but not when called from a script?

I'm using Linux Mint 17.1 "Rebecca" Xfce (64-bit).

Many, many thanks.

1

The tilde is not expanded when in quotes -- ref: https://www.gnu.org/software/bash/manual/bashref.html#Tilde-Expansion

So you want to remove the quotes:

str_getIdle_exe=~/Documents/Seb/Prjcts/Idle/getidle/src/getIdle

If the path under your homedir contains a space, just leave the tilde unquoted:

some_path=~/"dir with spaces/file with spaces"
| improve this answer | |
  • Perhaps worth noting that ~ isn't even expanded within double quotes - unlike $HOME. So $HOME may be preferable when quoting to prevent word-splitting e.g. "$HOME/some path/with spaces/" – steeldriver Jan 25 '15 at 23:18
  • Thank you both. Given a choice I would pick str_getIdle_exe="$HOME/Documents/Seb/Prjcts/Idle/getidle/src/getIdle" but it turns out for my purposes I discovered that I cannot call ANY VARIABLE with $. Got to use idleTimeMillis=$(./getIdle) # doesn't need str_getIdle_exe variable. $ operation on variables may return a number string, but it is not recognized later as .gt $idleAfter . Thanks again. – Tfb9 Jan 25 '15 at 23:43
  • If you are trying to assign the value of a command ~/Documents/Seb/Prjcts/Idle/getidle/src/getIdle (aka command substitution) then I would suggest something like idleTimeMillis="$("$HOME/Documents/Seb/Prjcts/Idle/getidle/src/getIdle")" – steeldriver Jan 26 '15 at 0:24
  • Yes, this perfect thanks! Now I'll try not to forget this lesson... – Tfb9 Jan 26 '15 at 1:24
  • I noticed Thunar (in the path string, top) does expand ~ in "~/Documents/", but does not expand $HOME in "$HOME/Documents"... at least for me. – Tfb9 Feb 18 '15 at 1:40
0

Tilde isn't expanded in quotes (single or double).

You have three options:

  1. remove the quotes:

    string="~/hello" -> string=~/hello (vulnerable to whitespace)

  2. use command substitution:

    string="~/hello" -> string="$(echo ~/hello)" (less vulnerable)

  3. as suggested by @steeldriver, use the HOME environment variable:

    string="~/hello" -> string="$HOME/hello"

| improve this answer | |
  • 4. Change code for: idleTimeMillis=$(./getIdle) # doesn't need str_getIdle_exe variable – Tfb9 Jan 25 '15 at 23:56

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.