dr jerry
dr jerry

Reputation: 10026

variable assignment in shell script

Our directory structure looks like

/long/dir/name/bin/exec.sh
/long/dir/name/logs
/long/dir/name/input
/long/dir/name/output.

in exec.sh I want to retrieve the root directory (/long/dir/name in this case), store this in a variable so I can use it to refer to $DIR/output, $DIR/input etc.

I got as far as [exec.sh]:

#!/bin/sh
export DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )" | sed -e 's,/*[^/]\+/*$,,'
echo "$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )" | sed -e 's,/*[^/]\+/*$,,'
echo "My Dir: '$DIR'"

This outputs:

/long/dir/name   <-- Which is what I want
My Dir: ''

What is going wrong when assigning it to the DIR variable?

Upvotes: 1

Views: 248

Answers (2)

John Zwinck
John Zwinck

Reputation: 249592

I think you want this:

DIR=${BASH_SOURCE%/*/*}

That is, strip the last two path parts from the script's own path, and use that. Run it through realpath or readlink -f if you need to get a canonical path.

Upvotes: 2

Etan Reisner
Etan Reisner

Reputation: 81052

To answer the "what went wrong" question.

You stuck the pipe to sed outside the subshell for the assignment (and technically export var=... isn't an assignment it is a call to export (see ksh get exit status in assignment as an example of this).

Anyway, what happens on that first line therefore is the shell sees

export DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )" | sed -e 's,/*[^/]\+/*$,,'

(note the whitespace around the pipe there). And pipelines execute in sub-shells so your export is happening in a su-shell and then being lost.

Stick the sed in the sub-shell and you fix the problem.

export DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd | sed -e 's,/*[^/]\+/*$,,')"

Upvotes: 3

Related Questions