ls > capture.txt9, cat capture.txt0, và cat capture.txt1 là ba luồng dữ liệu được tạo khi bạn khởi chạy một lệnh Linux. Bạn có thể sử dụng chúng để biết liệu các tập lệnh của bạn đang được chuyển hướng hoặc chuyển hướng. Chúng tôi chỉ cho bạn cách làm. Show Luồng tham gia hai điểmNgay khi bạn bắt đầu tìm hiểu về các hệ điều hành giống như Linux và Unix, bạn sẽ bắt gặp các thuật ngữ ls > capture.txt9, cat capture.txt0, và cat capture.txt4. Đây là ba luồng tiêu chuẩn được thiết lập khi một lệnh Linux được thực thi. Trong máy tính, luồng là thứ có thể truyền dữ liệu. Trong trường hợp của các luồng này, dữ liệu đó là văn bản. Các dòng dữ liệu, giống như dòng nước, có hai đầu. Chúng có một nguồn và một luồng ra. Bất kỳ lệnh Linux nào bạn đang sử dụng đều cung cấp một đầu của mỗi luồng. Đầu kia được xác định bởi trình bao khởi chạy lệnh. Đầu cuối đó sẽ được kết nối với cửa sổ đầu cuối, được kết nối với đường ống hoặc được chuyển hướng đến tệp hoặc lệnh khác, theo dòng lệnh đã khởi chạy lệnh. Luồng chuẩn LinuxTrong Linux, ls > capture.txt9 là dòng đầu vào tiêu chuẩn. Điều này chấp nhận văn bản làm đầu vào của nó. Đầu ra văn bản từ lệnh tới trình bao được gửi qua cat capture.txt0 (tiêu chuẩn ra) luồng. Thông báo lỗi từ lệnh được gửi qua cat capture.txt1 (lỗi tiêu chuẩn) luồng. Vì vậy, bạn có thể thấy rằng có hai luồng đầu ra, cat capture.txt0 và cat capture.txt1và một luồng đầu vào, ls > capture.txt9. Bởi vì các thông báo lỗi và đầu ra bình thường đều có ống dẫn riêng để đưa chúng đến cửa sổ đầu cuối, chúng có thể được xử lý độc lập với nhau. Luồng được xử lý giống như tệpCác luồng trong Linux — giống như hầu hết mọi thứ khác — được coi như thể chúng là tệp. Bạn có thể đọc văn bản từ một tệp và bạn có thể ghi văn bản vào một tệp. Cả hai hành động này đều liên quan đến một luồng dữ liệu. Vì vậy, khái niệm xử lý một luồng dữ liệu dưới dạng tệp không quá phức tạp. Mỗi tệp được liên kết với một quy trình được cấp phát một số duy nhất để xác định nó. Đây được gọi là bộ mô tả tệp. Bất cứ khi nào một hành động được yêu cầu thực hiện trên tệp, bộ mô tả tệp được sử dụng để xác định tệp. Những giá trị này luôn được sử dụng cho ls > capture.txt9, #!/bin/bash echo "About to try to access a file that doesn't exist" cat bad-filename.txt2 và cat capture.txt1:
Phản ứng với Pipes và RedirectsĐể dễ dàng giới thiệu một ai đó về một chủ đề, một kỹ thuật phổ biến là dạy một phiên bản đơn giản hóa của chủ đề. Ví dụ, với ngữ pháp, chúng ta được biết rằng quy tắc là “I trước E, ngoại trừ sau C.” Nhưng trên thực tế, có nhiều trường hợp ngoại lệ đối với quy tắc này hơn là có những trường hợp tuân theo nó. Theo một cách tương tự, khi nói về ls > capture.txt9, cat capture.txt0, và cat capture.txt1 thật tiện lợi khi đưa ra tiên đề được chấp nhận mà một quá trình không biết cũng như không quan tâm đến nơi mà ba luồng tiêu chuẩn của nó được kết thúc. Một quy trình có nên quan tâm đến việc liệu đầu ra của nó đang đi đến thiết bị đầu cuối hay được chuyển hướng thành một tệp không? Nó thậm chí có thể biết liệu đầu vào của nó đến từ bàn phím hay đang được đưa vào nó từ một quá trình khác? Trên thực tế, một quy trình biết — hoặc ít nhất là nó có thể tìm ra, nếu nó chọn kiểm tra — và nó có thể thay đổi hành vi của mình cho phù hợp nếu tác giả phần mềm quyết định thêm chức năng đó. Chúng ta có thể thấy sự thay đổi hành vi này rất dễ dàng. Hãy thử hai lệnh sau: ls ls | cat Các #!/bin/bash echo "About to try to access a file that doesn't exist" cat bad-filename.txt7 lệnh hoạt động khác nếu đầu ra của nó ( cat capture.txt0) đang được đưa vào một lệnh khác. Nó là #!/bin/bash echo "About to try to access a file that doesn't exist" cat bad-filename.txt7 chuyển sang một đầu ra cột duy nhất, nó không phải là chuyển đổi được thực hiện bởi chmod +x error.sh0. Và #!/bin/bash echo "About to try to access a file that doesn't exist" cat bad-filename.txt7 thực hiện điều tương tự nếu đầu ra của nó đang được chuyển hướng: ls > capture.txt cat capture.txt Chuyển hướng stdout và stderrCó một lợi thế khi có thông báo lỗi được gửi bởi một luồng chuyên dụng. Nó có nghĩa là chúng ta có thể chuyển hướng đầu ra của lệnh ( cat capture.txt0) vào một tệp và vẫn thấy bất kỳ thông báo lỗi nào ( cat capture.txt1) trong cửa sổ đầu cuối. Bạn có thể phản ứng với các lỗi nếu bạn cần, khi chúng xảy ra. Nó cũng ngăn các thông báo lỗi làm nhiễm bẩn tệp cat capture.txt0 đã được chuyển hướng vào. Nhập văn bản sau vào một trình soạn thảo và lưu nó vào một tệp có tên là error.sh. #!/bin/bash echo "About to try to access a file that doesn't exist" cat bad-filename.txt Làm cho tập lệnh có thể thực thi được bằng lệnh này: chmod +x error.sh Dòng đầu tiên của tập lệnh lặp lại văn bản tới cửa sổ đầu cuối, thông qua cat capture.txt0 suối. Dòng thứ hai cố gắng truy cập một tệp không tồn tại. Điều này sẽ tạo ra một thông báo lỗi được gửi qua cat capture.txt1. Chạy tập lệnh bằng lệnh này: ./error.sh Chúng ta có thể thấy rằng cả hai luồng đầu ra, cat capture.txt0 và cat capture.txt1, đã được hiển thị trong các cửa sổ đầu cuối. Hãy thử chuyển hướng đầu ra đến một tệp: ./error.sh > capture.txt Thông báo lỗi được gửi qua cat capture.txt1 vẫn được gửi đến cửa sổ đầu cuối. Chúng tôi có thể kiểm tra nội dung của tệp để xem liệu cat capture.txt0 đầu ra được chuyển đến tệp. cat capture.txt Đầu ra từ ls > capture.txt9 đã được chuyển hướng đến tệp như mong đợi. Các ./error.sh2 biểu tượng chuyển hướng hoạt động với cat capture.txt0 theo mặc định. Bạn có thể sử dụng một trong các bộ mô tả tệp số để cho biết luồng đầu ra chuẩn nào bạn muốn chuyển hướng. Để chuyển hướng rõ ràng cat capture.txt0, sử dụng hướng dẫn chuyển hướng này: 1> Để chuyển hướng rõ ràng cat capture.txt1, sử dụng hướng dẫn chuyển hướng này: ls | cat0 Hãy thử kiểm tra lại và lần này chúng ta sẽ sử dụng ./error.sh6: ls | cat1 Thông báo lỗi được chuyển hướng và cat capture.txt0 ./error.sh8 tin nhắn được gửi đến cửa sổ đầu cuối: Hãy xem những gì có trong tệp capture.txt. cat capture.txt Các cat capture.txt1 tin nhắn ở dạng capture.txt như mong đợi. Chuyển hướng Cả stdout và stderrChắc chắn, nếu chúng ta có thể chuyển hướng cat capture.txt0 hoặc là cat capture.txt1 đến một tệp độc lập với nhau, chúng ta phải có thể chuyển hướng cả hai cùng một lúc, đến hai tệp khác nhau? Có, chúng tôi có thể. Lệnh này sẽ hướng cat capture.txt0 vào một tệp có tên là capture.txt và cat capture.txt1 vào một tệp có tên là error.txt. ls | cat3 Bởi vì cả hai luồng đầu ra – đầu ra tiêu chuẩn và lỗi tiêu chuẩn – đều được chuyển hướng đến tệp, không có đầu ra hiển thị trong cửa sổ đầu cuối. Chúng tôi được quay trở lại dấu nhắc dòng lệnh như thể không có gì xảy ra. Hãy kiểm tra nội dung của từng tệp: cat capture.txt ls | cat5 Chuyển hướng stdout và stderr đến cùng một tệpThật gọn gàng, chúng tôi có từng luồng đầu ra tiêu chuẩn đi đến tệp chuyên dụng của riêng nó. Sự kết hợp duy nhất khác mà chúng tôi có thể làm là gửi cả hai cat capture.txt0 và cat capture.txt1 vào cùng một tệp. Chúng ta có thể đạt được điều này bằng lệnh sau: ls | cat6 Hãy phá vỡ điều đó.
Không có đầu ra hiển thị. Điều đó thật đáng khích lệ. Hãy kiểm tra tệp capture.txt và xem có gì trong đó. cat capture.txt Cả hai cat capture.txt0 và cat capture.txt1 luồng đã được chuyển hướng đến một tệp đích duy nhất. Để đầu ra của luồng được chuyển hướng và bị loại bỏ một cách âm thầm, hãy hướng đầu ra tới cat capture.txt3. Phát hiện chuyển hướng trong tập lệnhChúng ta đã thảo luận về cách một lệnh có thể phát hiện xem có bất kỳ luồng nào đang được chuyển hướng hay không và có thể chọn thay đổi hành vi của nó cho phù hợp. Chúng ta có thể thực hiện điều này trong các tập lệnh của riêng mình không? Có, chúng tôi có thể. Và nó là một kỹ thuật rất dễ hiểu và sử dụng. Nhập văn bản sau vào một trình soạn thảo và lưu nó dưới dạng input.sh. ls | cat8 Sử dụng lệnh sau để làm cho nó có thể thực thi được: ls | cat9 Phần thông minh là bài kiểm tra trong ngoặc vuông. Các cat capture.txt4 (terminal) tùy chọn trả về true (0) nếu tệp được liên kết với bộ mô tả tệp kết thúc trong cửa sổ đầu cuối. Chúng tôi đã sử dụng bộ mô tả tệp 0 làm đối số cho kiểm tra, đại diện cho ls > capture.txt9. Nếu ls > capture.txt9 được kết nối với một cửa sổ đầu cuối, thử nghiệm sẽ chứng minh là đúng. Nếu ls > capture.txt9 được kết nối với một tệp hoặc một đường ống, quá trình kiểm tra sẽ không thành công. Chúng tôi có thể sử dụng bất kỳ tệp văn bản thuận tiện nào để tạo đầu vào cho tập lệnh. Ở đây chúng tôi đang sử dụng một tệp có tên là dummy.txt. ls > capture.txt0 Kết quả đầu ra cho thấy rằng tập lệnh nhận ra rằng đầu vào không đến từ bàn phím, nó đến từ một tệp. Nếu bạn đã chọn, bạn có thể thay đổi hành vi của tập lệnh của mình cho phù hợp. Đó là với chuyển hướng tệp, hãy thử nó với một đường ống. ls > capture.txt1 Tập lệnh nhận ra rằng đầu vào của nó đang được đưa vào nó. Hay chính xác hơn, nó nhận ra một lần nữa rằng ls > capture.txt9 luồng không được kết nối với cửa sổ đầu cuối. Hãy chạy tập lệnh mà không có đường dẫn hoặc chuyển hướng. ls > capture.txt2 Các ls > capture.txt9 luồng được kết nối với cửa sổ đầu cuối và tập lệnh báo cáo điều này tương ứng. Để kiểm tra điều tương tự với luồng đầu ra, chúng ta cần một tập lệnh mới. Nhập nội dung sau vào một trình soạn thảo và lưu nó dưới dạng output.sh. ls > capture.txt3 Sử dụng lệnh sau để làm cho nó có thể thực thi được: ls | cat9 Phần thông minh là bài kiểm tra trong ngoặc vuông. Các cat capture.txt4 (terminal) tùy chọn trả về true (0) nếu tệp được liên kết với bộ mô tả tệp kết thúc trong cửa sổ đầu cuối. Chúng tôi đã sử dụng bộ mô tả tệp 0 làm đối số cho kiểm tra, đại diện cho ls > capture.txt9. Hãy thử nó ra. Chúng tôi sẽ chuyển đầu ra thông qua chmod +x error.sh0. ls > capture.txt5 Tập lệnh nhận ra rằng đầu ra của nó không trực tiếp đến cửa sổ đầu cuối. Chúng tôi cũng có thể kiểm tra tập lệnh bằng cách chuyển hướng đầu ra thành một tệp. ls > capture.txt6 Không có đầu ra cho cửa sổ đầu cuối, chúng tôi được đưa trở lại dấu nhắc lệnh một cách âm thầm. Như chúng tôi mong đợi. Chúng ta có thể xem bên trong tệp capture.txt để xem những gì đã được chụp. Sử dụng lệnh sau để làm như vậy. ls > capture.txt7 Một lần nữa, kiểm tra đơn giản trong tập lệnh của chúng tôi phát hiện ra rằng cat capture.txt0 luồng không được gửi trực tiếp đến cửa sổ đầu cuối. Nếu chúng tôi chạy tập lệnh mà không có bất kỳ đường dẫn hoặc chuyển hướng nào, nó sẽ phát hiện ra rằng cat capture.txt0 đang được chuyển trực tiếp đến cửa sổ đầu cuối. ls > capture.txt8 Và đó chính xác là những gì chúng ta thấy. Dòng ý thứcBiết cách biết các tập lệnh của bạn có được kết nối với cửa sổ đầu cuối hay đường ống dẫn hoặc đang được chuyển hướng hay không, cho phép bạn điều chỉnh hành vi của chúng cho phù hợp. Kết quả ghi nhật ký và chẩn đoán có thể chi tiết hơn hoặc ít hơn, tùy thuộc vào việc nó xuất hiện trên màn hình hay một tệp tin. Thông báo lỗi có thể được ghi vào một tệp khác với đầu ra chương trình bình thường. Như thường lệ, nhiều kiến thức hơn mang lại nhiều lựa chọn hơn. |