Saya memiliki file skrip bash, yang diletakkan di bawah beberapa direktori yang ditambahkan ke $ PATH sehingga saya dapat memanggil skrip dari direktori mana pun.
Ada file teks lain di bawah direktori yang sama dengan skrip. Saya ingin tahu bagaimana merujuk ke file teks dalam skrip?
Misalnya, jika skrip hanya untuk menampilkan konten file teks, cat textfile
tidak akan berfungsi, karena ketika memanggil skrip dari direktori yang berbeda, file teks tidak ditemukan.
Jawaban:
Ini harus bekerja sama, selama tidak ada symlink (dalam perluasan jalur atau skrip itu sendiri):
MYDIR="$(dirname "$(realpath "$0")")"
MYDIR="$(dirname "$(which "$0")")"
Versi dua langkah dari yang di atas:
MYSELF="$(realpath "$0")"
MYDIR="${MYSELF%/*}"
Jika ada symlink dalam perjalanan ke skrip Anda, maka
which
akan memberikan jawaban tidak termasuk resolusi tautan itu. Jikarealpath
tidak diinstal secara default pada sistem Anda , Anda dapat menemukannya di sini .[EDIT]: Karena tampaknya
realpath
tidak memiliki kelebihan dibandingkan yangreadlink -f
disarankan oleh Caleb , mungkin lebih baik menggunakan yang terakhir. Tes waktu saya menunjukkan itu sebenarnya lebih cepat.sumber
realpath
datangnya dari sistem Anda. (Untuk orang lain yang tidak memilikinya, Anda dapat menggunakanreadlink -f
realpath
tanggal kembali dari sebelumnyareadlink -f
(dan bahkanreadlink
, IIRC) berada di GNU coreutils (ada beberapa alat serupa di sekitar.readlink -f
akhirnya menjadi standar de facto);realpath
hanya disimpan untuk kompatibilitas dengan skrip yang masih menggunakannya.$(dirname "$(which "$0")")
di$(dirname $0)
manawhich
tidak ada lagi? Bukankah itu sama?readlink -f
tampaknya tidak berfungsi di Mac OS X 10.11.6, tetapirealpath
berfungsi di luar kotak.Sistem saya tidak memiliki
realpath
seperti yang disarankan oleh rozcietrzewiacz .Anda dapat melakukannya dengan menggunakan
readlink
perintah. Keuntungan menggunakan ini daripada parsingwhich
atau solusi lain adalah bahwa bahkan jika bagian dari path atau nama file yang dijalankan adalah symlink, Anda akan dapat menemukan direktori di mana file sebenarnya berada.File teks Anda kemudian dapat dibaca ke dalam variabel seperti ini:
sumber
which
saran Anda . Solusi normal untuk ini melibatkan adildirname
atau kombinasi daricd
danpwd
dalam subkulit. Readlink memiliki keunggulan di sini.realpath
Sepertinya cukup banyak hanya menjadi pembungkusreadlink -f
.realpath
bedanyareadlink -f
. Saya hanya bisa melihatnya memberi saya hasil yang sama (berlawanan denganwhich
).readlink -f
(dari GNU coreutils) TIDAK memerlukan elemen terakhir dari path untuk ada,readlink -e
tidak, tetapi tidak didukung olehbusybox readlink
, yang meniru perilaku-e
dalam-f
pilihan mereka .$0
di skrip akan menjadi path lengkap ke skrip, dandirname
akan mengambil path lengkap dan memberikan Anda hanya direktori, sehingga Anda dapat melakukan ini ke cat textfile:sumber
realpath $0
, Anda salah mengatakan bahwa "$0
dalam skrip akan menjadi jalan penuh ke skrip".$0
adalah perintah sebagaimana dijalankan, yang bisa mis../script.sh
.$(dirname "$0")
mengembalikan path relatif ke skrip, sebagai bagian dari perintah yang dipanggil - bukan path absolut. Ini dapat menyebabkan masalah dalam skrip yang mengubah direktori saat berjalan.Anda dapat meletakkan ini di bagian atas skrip Anda:
Sumber: http://mywiki.wooledge.org/BashFAQ/028
sumber
Saya sedang mencoba ini dan jalan tidak bekerja untuk saya. Solusi yang saya gunakan adalah:
Sejauh ini yang bekerja dengan baik. Saya ingin tahu apakah ada potensi masalah dengan pendekatan tersebut.
sumber
SCRIPT_DIR="$( cd "$(dirname "$( readlink -f ${BASH_SOURCE[0]} )")" >/dev/null 2>&1 && pwd)"
Saya menggunakan:
Yang POSIX dan harus bekerja selama dirname dari
$0
tidak berakhir pada karakter baris baru, tidak-
dan$CDPATH
tidak diatur (dan mungkin beberapa kasus sudut lainnya jika skrip tidak dicari$PATH
).sumber
Saya selalu menggunakan
which
untuk menemukan path lengkap dari executable dari PATH. Contohnya:which python
Jika Anda menggabungkan ini dengan
dirname
perintah maka Anda mendapatkan:sumber