Quando scrivo uno script bash, come posso ottenere il percorso assoluto della posizione del file corrente?


16

Supponiamo di avere un file bash chiamato myBash.bash. Risiede in:

/myDirect/myFolder/myBash.bash

Ora voglio usare la stringa /myDirect/myFolder(la posizione di myBash.bash) all'interno dello script. Esiste un comando che posso usare per trovare questa posizione?

Modifica: L'idea è che voglio impostare una cartella zip con codice che può essere avviato da uno script bash all'interno di quel file zip. Conosco i percorsi di file relativi del codice all'interno di quel file zip, ma non i percorsi assoluti e ne ho bisogno. Un modo sarebbe codificare nel percorso o richiedere che il percorso del file sia indicato come variabile. Tuttavia, troverei più semplice se fosse possibile per il file bash capire dove si trova da solo e quindi creare i percorsi rilevanti per l'altro file dalla sua conoscenza della struttura del file zip.


3
Questo potrebbe essere più adatto per lo stackoverflow. Controlla queste domande: stackoverflow.com/questions/4774054/… stackoverflow.com/questions/59895/… .
Sethos II

1
usa come. per favore chiarisci
Sergiy Kolodyazhnyy,

1
@SethosII questa domanda è totalmente in tema qui
Zanna

1
Ho aggiunto più contesto alla domanda. Ho pensato che potrebbe esserci un comando semplice / ovvio per ottenere il percorso del file in esecuzione, ma sembra che la risposta sia almeno non ovvia.
Dimpol

3
@Zanna Non dico che è offtopico, penso che sia solo più appropriato e come mostrato con i collegamenti già richiesti e risposto lì più volte.
Sethos II

Risposte:


24

È possibile ottenere il percorso completo come:

realpath "$0"

E come sottolineato da Serg , puoi usare dirnameper eliminare il nome del file in questo modo

dirname "$(realpath $0)"

o ancora meglio per evitare citazioni imbarazzanti e divisione di parole con nomi di file difficili:

temp=$( realpath "$0"  ) && dirname "$temp"

Molto meglio della mia idea precedente che era di analizzarlo (sapevo che ci sarebbe stato un modo migliore!)

realpath "$0" | sed 's|\(.*\)/.*|\1|'

Appunti

  • realpath restituisce il percorso effettivo di un file
  • $0 è questo file (lo script)
  • s|old|new|sostituire oldconnew
  • \(.*\)/salva tutti i personaggi prima /per dopo
  • \1 la parte salvata

2
+1 per l'uso $0e la sedmagia. Ma la suddetta sedmagia è davvero superflua quando dirnameesistono strumenti come questo
Sergiy Kolodyazhnyy

2
hai già la risposta, usa realpath: realpath "$( dirname $0 )"personalmente readlinkreadlink -e $(dirname $0)
userei

@Serg: non dirname "$(realpath "$0")"sarebbe meglio? Di solito si desidera conoscere la directory principale del file di riferimento anziché la directory principale del collegamento simbolico che si riferisce a tale file.
David Foerster,

4
@Serg "$(dirname "$(realpath "$0")")"è il modo più semplice. Le citazioni all'interno $()funzionano normalmente.
Depresso

@DepressedDaniel Hai fatto un po 'di ricerche online, hai ragione: $()essere una subshell ti permetterà di avere delle citazioni all'esterno. Non direi che è altrettanto semplice, a meno che non ci si accorga che $()sono tutte
sottotitoli

5

se lo script è sul tuo percorso puoi usare qualcosa di simile

$ myloc=$(dirname "$(which foo.sh)")
$ echo "$myloc"
/path/to/foo.sh

EDIT: dopo aver letto i commenti di Serg, questa potrebbe essere una soluzione generica che funziona indipendentemente dal fatto che lo script sia nel tuo percorso o meno.

myloc==$(dirname "$(realpath $0)")
dirname "$myloc"

whichè più adatto per quando lo script risiede in una delle directory che fanno parte della PATHvariabile. Usa $0da una sceneggiatura, proprio come Zanna mostra. Ma la tua risposta è corretta dato che usi dirnameinvece di scherzare sed, quindi +1 per quello
Sergiy Kolodyazhnyy

5

La risposta accettata sembra perfetta. Ecco un altro modo per farlo:

cd "$(dirname "$0")"
/bin/pwd

/bin/pwdstampa il percorso reale della directory, in contrapposizione al pwdcomando incorporato.


0
wdir="$PWD"; [ "$PWD" = "/" ] && wdir=""
case "$0" in
  /*) scriptdir="${0}";;
  *) scriptdir="$wdir/${0#./}";;
esac
scriptdir="${scriptdir%/*}"
echo "$scriptdir"

È preso come riferimento da kenorb e andro
Nessun dirname, readlink, realpath, BASH_SOURCE
Tutti sono builtin

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.