Khi nào nên sử dụng luồng lỗi tiêu chuẩn trong ứng dụng dòng lệnh?


9

Có hướng dẫn khi sử dụng lỗi khi viết ứng dụng dòng lệnh không? Thật ngạc nhiên, tôi đã không tìm thấy bất cứ điều gì khi googling nó.

Cụ thể, câu hỏi tôi quan tâm bây giờ là nên sử dụng stdouthay stderrkhi người dùng gọi chương trình với các đối số bất hợp pháp. Tuy nhiên, một câu trả lời toàn diện hơn được đánh giá rất cao bởi vì đây chắc chắn sẽ không phải là trường hợp duy nhất trong đó cần có một quy tắc rõ ràng để viết một chương trình hành xử theo cách mà người dùng mong đợi.


Có ổn không khi những thông báo lỗi được trộn lẫn với đầu ra thông thường? Ví dụ, chương trình là một bộ lọc cho dữ liệu?
21 giờ 42 phút

Nó không phải là bộ lọc cho dữ liệu. Nó cũng không tương tác. Người dùng gọi nó bằng các đối số (trong số đó là đường dẫn tệp), các chương trình hoạt động, thay đổi các tệp đó, in một vài thông báo, lý tưởng là không in bất kỳ thông báo lỗi nào và chấm dứt.
UTF-8

Câu trả lời:


15

Có, hiển thị thông báo stderrkhi sử dụng các đối số sai. Và nếu điều đó cũng khiến ứng dụng thoát ra, hãy thoát với trạng thái thoát khác không.

Bạn nên sử dụng luồng lỗi tiêu chuẩn cho các thông báo chẩn đoán hoặc cho tương tác người dùng. Thông báo chẩn đoán bao gồm thông báo lỗi, cảnh báo và các thông báo khác không phải là một phần của đầu ra của tiện ích khi nó hoạt động chính xác ("chính xác" có nghĩa là không có gì đặc biệt xảy ra, như không tìm thấy tệp hoặc bất cứ điều gì có thể).

Nhiều shell (tất cả?) Hiển thị lời nhắc, kiểu người dùng và menu, v.v. stderrđể việc chuyển hướng stdoutsẽ không ngăn bạn tương tác với shell theo cách có ý nghĩa.

Sau đây là từ một bài viết trên blog về chủ đề này:

Đây là một trích dẫn từ Doug McIllroy, người phát minh ra các ống Unix, giải thích làm thế nào stderrđể trở thành. 'v6' đang đề cập đến một phiên bản của phiên bản cụ thể của hệ điều hành Unix gốc được phát hành vào năm 1975.

Tất cả các chương trình đặt chẩn đoán trên đầu ra tiêu chuẩn. Điều này luôn gây ra sự cố khi đầu ra được chuyển hướng thành một, nhưng trở nên không thể chịu đựng được khi đầu ra được gửi đến một quy trình không nghi ngờ. Tuy nhiên, không sẵn lòng vi phạm tính đơn giản của mô hình đầu ra tiêu chuẩn-đầu vào-tiêu chuẩn, mọi người chấp nhận tình trạng này thông qua v6. Ngay sau đó Dennis Ritchie đã cắt nút Gordian bằng cách đưa ra lỗi tiêu chuẩn. Điều đó là không đủ. Với chẩn đoán đường ống có thể đến từ bất kỳ chương trình nào đang chạy đồng thời. Chẩn đoán cần thiết để xác định chính mình.
- Doug McIllroy, "Trình đọc UNIX nghiên cứu: Các đoạn trích được chú thích từ Sổ tay lập trình viên, 1971-1986"

Để "nhận diện chính mình" có nghĩa là chỉ cần nói "Này! Tôi đang nói! Điều này đã sai: [...]":

$ ls nothere
ls: nothere: No such file or directory

Làm điều này trên stderrlà tốt hơn, vì nó có thể được đọc bởi bất cứ điều gì đang đọc stdout(nhưng chúng ta không làm điều đó với lsdù sao , phải không?).


Vì vậy, khi bạn hỏi người dùng một cái gì đó khi ứng dụng đang chạy, bạn nên in câu hỏi trên stderr? Điều đó không đúng. Bạn có một nguồn cho nó? Có phải điều này chỉ áp dụng cho các ứng dụng có đầu ra không chỉ là câu hỏi và câu trả lời (đầu ra mà người dùng có thể muốn đặt ở đâu đó)?
UTF-8

@ UTF-8 Văn bản của câu hỏi có nên được coi là một phần của đầu ra của chương trình không? Những gì về người dùng gõ vào? Tôi không nghĩ nó nên như vậy (giống như vỏ ốc không nghĩ nó nên như vậy). Nhưng có lẽ nó phụ thuộc vào ứng dụng?
Kusalananda

1
Cảm ơn bạn đã chỉnh sửa của bạn. Trong khi đó, tôi đã kiểm tra hành vi của các ứng dụng tiêu chuẩn và chúng hoạt động như người ta mong đợi chúng sẽ hành xử sau khi đọc câu trả lời của bạn.
UTF-8

@ UTF-8 bạn có thể tìm thấy câu hỏi và trả lời này có liên quan: unix.stackexchange.com/q/331611/22222
terdon

5

Từ thông số kỹ thuật POSIX cho các luồng tiêu chuẩn:

Khi khởi động chương trình, ba luồng phải được xác định trước và không cần phải mở một cách rõ ràng: đầu vào tiêu chuẩn (để đọc đầu vào thông thường), đầu ra tiêu chuẩn (để ghi đầu ra thông thường) và lỗi tiêu chuẩn (để ghi đầu ra chẩn đoán ).

Nói cách khác, lỗi, thông tin gỡ lỗi và bất cứ điều gì rơi vào danh mục chẩn đoán đều đi vào stderr.

Xem câu hỏi liên quan để biết thêm thông tin: Các báo cáo tiến độ / thông tin đăng nhập có thuộc về thiết bị xuất chuẩn hoặc thiết bị xuất chuẩn không?

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.