Thêm đường dẫn vào PATH bằng cú pháp nhiều dòng


16

Theo tôi hiểu, cách thông thường để thêm một đường dẫn đến PATHbiến môi trường là bằng cách nối các đường dẫn được phân tách bằng :ký tự.

Ví dụ: nếu tôi muốn thêm ba đường dẫn vào nó /my/path/1, /my/path/2/my/path/3, tôi sẽ phải làm như sau:

PATH=$PATH:/my/path/1:/my/path/2:/my/path/3

mà không dễ đọc

Có cách nào để xác định hoặc thêm đường dẫn đến PATHbiến bằng cú pháp nhiều dòng không? Có lẽ sử dụng mảng? Tôi đang tìm kiếm một cái gì đó như thế này:

PATH = 
$PATH
/my/path/1
/my/path/2
/my/path/3

Trong trường hợp có các giải pháp thú vị là shell cụ thể, tôi đang tìm kiếm một giải pháp trong zsh.

Câu trả lời:


12

Tôi không biết nếu nó hoạt động trong zsh, nhưng nó hoạt động trong bash:

PATH=$(paste -d ":" -s << EOF 
$PATH
/my/path/1
/my/path/2
/my/path/3
EOF
)

Chỉnh sửa và thậm chí ngắn hơn:

PATH=`paste -d ":" -s << EOF 
$PATH
/my/path/1
/my/path/2
/my/path/3
EOF`

Và không sinh ra một quá trình:

new_path=(
"$PATH"
/my/path/1
/my/path/2
/my/path/3)
OLD_IFS="$IFS"
export IFS=":"
PATH="${new_path[*]}"
export IFS="$OLD_IFS"

Các dấu ngoặc kép là arround quan trọng $PATH, $IFS, ${new_path[*]}$OLD_IFSđể giữ cho không gian trong việc giải thích các biến và tránh vỏ của IFS.

Update2 với ý kiến ​​và quản lý dòng trống bằng sed:

PATH=`sed -e '/^#/'d -e '/^$/'d << EOF | paste -d ":" -s 
$PATH
/my/path/1
# This is a comment.
/my/path/2

/my/path/3
EOF`

Ký tự nhận xét phải là ký tự đầu tiên trên dòng và các dòng trống phải hoàn toàn trống. Để quản lý khoảng trắng và tab trước khi nhận xét và trên các dòng trống, sed -e '/^[ \t]*#/'d -e '/^[ \t]*$/'dthay vào đó , hãy sử dụng (các tab được kiểm tra vì nó có thể dành riêng cho việc triển khai sed).


Tôi đã thử đoạn mã cuối cùng trong zsh và nó hoạt động. Tôi cũng thích rằng nó sạch hơn một chút (một đường dẫn trên mỗi dòng) so với các giải pháp khác. Giải pháp có thể chứa các dòng nhận xét (đường dẫn) không? Làm thế nào về dòng trống?
Amelio Vazquez-Reina

Cập nhật với ý kiến ​​và quản lý dòng trống.
jfg956

Và với sed, nếu bạn muốn chơi, bạn có thể tránh quá trình dán với một kịch bản phức tạp hơn.
jfg956

Có thể sử dụng thụt đầu dòng cho các đường dẫn trong pastegiải pháp?
void.pulum

20

Không phải là một giải pháp thú vị, nhưng rất di động:

PATH=${PATH}:/my/path/1
PATH=${PATH}:/my/path/2
PATH=${PATH}:/my/path/3

1
Đây là điển hình của những gì tôi đã thấy trong những năm qua. Người ta có thể dễ dàng sắp xếp lại các đường dẫn hoặc thậm chí thay đổi một yếu tố thành PATH = / my / path / 1: $ {PATH} để buộc trả trước.
bsd

1
Bạn cũng có thể sử dụng +=để tránh phải xây dựng lại hoàn toàn chuỗi.
Chris Xuống

Và bạn thậm chí không cần sử dụng niềng răng. Dấu hai chấm không thể được sử dụng trong tên biến môi trường để không có sự mơ hồ để giải quyết.
Alexios

+1 vì không thú vị. Thú vị đôi khi có thể tốt, nhưng đây không phải là một trong những thời điểm đó! (Đặc biệt là khi OP đề cập rõ ràng "không dễ đọc" là một vấn đề.)
ruakh

@ChrisDown Có cú pháp nào mở rộng mà không xây dựng lại chuỗi không?
John P

12

Trong zsh, $pathlà một mảng:

path=(
    $path
    ~/.local/bin
    ~/.gem/ruby/2.0.0/bin
)

Lưu ý: cả hai đều pathlà chữ thường.


Điều đó phụ thuộc vào vỏ, không phải tất cả xử lý này.
vonbrand

1
@vonbrand: Có, nhưng hoạt động trong zsh. Tôi nghĩ rằng nó đáng để đề cập.
Kabie

3
+1 (Câu hỏi này được gắn thẻ zsh )
Johnsyweb

Vì OP đặc biệt hỏi về zsh, đây là lựa chọn tốt nhất
Daniel Serodio

1
cho bất cứ ai quan tâm đến việc tìm hiểu thêm về phân biệt $ path so với $ PATH, hãy xem bài đăng này
mbigras

7

Trong zsh, nếu bạn thêm thư mục ở cuối đường dẫn:

path+=/my/path/1
path+=/my/path/2
path+=(/path/to/app/{i386,share}/bin)

Có khả năng: Làm thế nào để thêm chính xác đường dẫn đến PATH?

Bạn có thể sử dụng vòng loại toàn cầu để loại trừ các mục không phải là thư mục hiện có hoặc liên kết tượng trưng đến đó. Điều này có thể hoặc không thể mong muốn, tùy thuộc vào việc bạn có mong đợi các thư mục có thể được thêm vào sau trong phiên hay không (ví dụ: nếu chúng nằm trên các hệ thống tệp từ xa). Bạn không thể làm điều đó với path+=/my/pathcú pháp bởi vì phía bên tay phải nằm trong ngữ cảnh chuỗi và do đó không trải qua quá trình toàn cầu hóa; bạn có thể làm điều đó path+=(/my/path)vì mỗi phần tử mảng được mở rộng trong ngữ cảnh danh sách.

path+=(/path/to/app/{i386,share}/bin(-/N))
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.