2015-04-13 16 views
5

Tôi đang sử dụng VM (trong trường hợp của tôi chỉ cần boot2docker) để chạy các vùng chứa docker trên máy chủ Windows. Đối với convinience, các tệp nguồn của tôi được ánh xạ từ hệ thống tệp máy chủ, do đó các tệp văn bản theo mặc định sử dụng các đầu cuối dòng CRLF kiểu Windows thay vì các kết thúc LF kiểu Unix.Bash - chạy liên tục các tập lệnh có dòng kết thúc CRLF

Khi tôi cố gắng để chạy một số file sh từ thùng chứa Docker, tôi sẽ nhận được một lỗi

bash: ./script.sh: /bin/bash^M: bad interpreter: No such file or directory 

Có cách nào làm thế nào tôi có thể bằng cách nào đó nói với bash/sh phiên dịch tự động chuyển đổi \ r \ n để \ n và chạy một tệp?

Chắc chắn, tôi có thể làm một số piplelining như thế này cat script.sh | tr -d "\r" | sh hoặc thậm chí tạo một bí danh cho điều đó, nhưng nó sẽ không bao gồm tình huống mà một kịch bản bao gồm một kịch bản khác.

Giải pháp duy nhất có thể chấp nhận được mà tôi đã tìm thấy cho đến nay, là đặt Git thành các tệp nguồn thanh toán ở định dạng UNIX.

+0

bạn có thể đăng 'echo $ TERM' không? – user2915097

+0

Đây là vùng chứa docker tiêu chuẩn, 'echo $ TERM' trả về' câm' – trebi

+0

thử 'xuất TERM = xterm' hoặc' exec>/dev/tty 2>/dev/tty user2915097

Trả lời

1

Giải pháp tốt nhất mà tôi có là đảm bảo sử dụng trình chỉnh sửa (như Notepad ++ hoặc Văn bản siêu văn bản) có thể lưu trực tiếp với kiểu eol phù hợp.

Bằng cách đó, tôi không phải dos2unix bất kỳ tệp nào trong phiên boot2docker của mình.

2

Đối với một số tập lệnh, giải pháp ln -s /bin/bash /bin/bash^M sẽ không thành công.
Vì vậy, hãy tạo tập lệnh/bin/bash^M để dos2unix các đối số nhận được và chạy chúng với "[email protected]".

Edit: Tôi đã thử nó với bash sau^M kịch bản:

#!/bin/bash 
PROG=$1 
shift 
dos2unix $PROG > /dev/null 2>&1 
$PROG "[email protected]" 

này sẽ thất bại khi kịch bản của bạn bao gồm các kịch bản khác với một dấu chấm, trong trường hợp đó bạn nên tránh việc xung quanh này và đi cho định dạng Unix.
Bạn cho biết bạn có thể thanh toán ở định dạng Unix hoặc bạn có thể tự thay đổi các tệp.
Và cam kết thành git, đó là một cải tiến để có các tệp unix được lưu trữ trong git ở định dạng unix. Khi bạn thực sự muốn chỉnh sửa chúng trong cửa sổ, hãy thay đổi cài đặt của trình chỉnh sửa hoặc dos2unix sau đó.

+0

Điều này trông giống như cách tiếp cận thông minh! Vì vậy, khi tôi tạo tệp '/ bin/bash^M', tôi sẽ loại bỏ lỗi 'bash: ./script.sh:/bin/bash^M: thông dịch viên xấu: Không có tệp hoặc thư mục', nhưng tôi sẽ giới thiệu một lỗi khác 'script.sh: dòng 2: $ '\ r': lệnh không tìm thấy', trong đó dòng 2 được cho là dòng trống, nhưng trình thông dịch nghĩ rằng có một lệnh có tên là' \ r. – trebi

+0

Đó là lý do tại sao bash^M của bạn không nên gọi bash trực tiếp, nhưng trước tiên dos2unix/tr tập lệnh sẽ được chạy. –

0

Tôi tưởng tượng bạn có thể viết một kịch bản như

#!/bin/bash 
#bash_run_unixified 
#unixify and run in bash 
dos2unix < "$1" | /bin/bash 

và giả sử bạn lưu nó trong/urs/local/bin/bash_run_unixified có quyền phù hợp (sudo chmod o+r,o+x), sau đó bạn có thể thêm tiền tố kịch bản của bạn với

#!/usr/local/bin/bash_run_unixified 
#This script has CRLFs in it 

Nếu bạn không muốn dòng công việc không bình thường như vậy, bạn có thể

$ ln -s /usr/local/bin/{bash_run_unixified,bash} 

và sau đó sử dụng (Như Walter A. ghi chú, nó có thể là một ý tưởng tốt để liên kết nó với bash^M quá)

#!/usr/bin/env bash 

như dòng công việc của bạn (/usr/local/bin/ thường gần gũi hơn với sự khởi đầu của bạn $PATH hơn /bin do đó lệnh env nên chọn bash liên kết đến bash_run_unixified).

(Lời cảnh báo: Tôi đã không kiểm tra bất kỳ này)

2

Bạn có thể cam kết một tập tin .gitattributes trong repo của bạn trong thư mục gốc để tự động nói với Git để áp dụng kết thúc dòng LF để tất cả các file sh khi kiểm tra, ngay cả trên Windows. Bằng cách này bạn hoặc các nhà phát triển khác không cần phải nhớ cấu hình Git trên mỗi máy mà bạn sao chép repo của bạn.

# Set line endings to LF, even on Windows. Otherwise, execution within Docker fails. 
# See https://help.github.com/articles/dealing-with-line-endings/ 
*.sh text eol=lf 
Các vấn đề liên quan