Hướng dẫn pty python - trăn pty

Mã nguồn: lib/pty.py Lib/pty.py


Mô-đun pty xác định các hoạt động để xử lý khái niệm đầu cuối giả: bắt đầu một quá trình khác và có thể viết và đọc từ thiết bị đầu cuối kiểm soát của nó theo chương trình của nó.

Xử lý đầu cuối giả phụ thuộc vào nền tảng cao. Mã này chủ yếu được kiểm tra trên Linux, FreeBSD và MacOS (nó được cho là hoạt động trên các nền tảng POSIX khác nhưng nó không được kiểm tra kỹ lưỡng).

Mô -đun pty xác định các chức năng sau:

pty.fork ()fork()

Cái nĩa. Kết nối thiết bị đầu cuối kiểm soát trẻ con với một thiết bị đầu cuối giả. Giá trị trả về là (pid, fd). Lưu ý rằng đứa trẻ nhận được PID 0 và FD không hợp lệ. Giá trị trả về cha mẹ là PID của đứa trẻ và FD là bộ mô tả tệp được kết nối với thiết bị đầu cuối điều khiển trẻ con (và cả đầu vào và đầu ra tiêu chuẩn của trẻ con).

pty.openpty () ¶openpty()

Mở một cặp đầu cuối giả mới, sử dụng os.openpty() nếu có thể hoặc mã mô phỏng cho các hệ thống Unix chung. Trả về một cặp mô tả tệp (master, slave), cho Master và đầu nô lệ, tương ứng.

pty.spawn (argv [, master_read [, stdin_read]]) ¶spawn(argv[, master_read[, stdin_read]])

Spawn một quy trình và kết nối thiết bị đầu cuối kiểm soát của nó với IO tiêu chuẩn quy trình hiện tại. Điều này thường được sử dụng để gây vùi dập các chương trình nhấn mạnh vào việc đọc từ thiết bị đầu cuối kiểm soát. Dự kiến ​​quá trình này đã sinh ra phía sau Pty cuối cùng sẽ chấm dứt, và khi nó sinh sản sẽ trở lại.

Một vòng lặp sao chép stdin của quy trình hiện tại cho trẻ và dữ liệu nhận được từ trẻ đến stdout của quy trình hiện tại. Nó không được báo hiệu cho trẻ nếu Stdin của quá trình hiện tại đóng cửa.

Các chức năng master_read và stdin_read được truyền một bộ mô tả tệp mà họ nên đọc từ đó và chúng phải luôn luôn trả về một chuỗi byte. Để buộc sinh sản quay trở lại trước khi quá trình con thoát ra một mảng byte trống nên được trả lại cho tín hiệu cuối tệp.

Việc triển khai mặc định cho cả hai chức năng sẽ đọc và trả lại tới 1024 byte mỗi khi hàm được gọi. Gọi lại master_read được truyền qua bộ mô tả tệp chính Pseudoterminal, để đọc đầu ra từ quy trình con và stdin_read được thông qua bộ mô tả tệp 0, để đọc từ đầu vào tiêu chuẩn của quá trình cha.

Trả về một chuỗi byte trống từ một trong hai cuộc gọi lại được hiểu là một điều kiện cuối tệp (EOF) và cuộc gọi lại đó sẽ không được gọi sau đó. Nếu stdin_read tín hiệu EOF thiết bị đầu cuối kiểm soát không còn có thể giao tiếp với quy trình cha hoặc quy trình con. Trừ khi quá trình con sẽ thoát mà không có bất kỳ đầu vào nào, Spawn sẽ lặp lại mãi mãi. Nếu Master_read tín hiệu EOF cùng kết quả hành vi (ít nhất là trên Linux).

Trả về giá trị trạng thái thoát từ os.waitpid() trên quy trình con.

waitstatus_to_exitcode() có thể được sử dụng để chuyển đổi trạng thái thoát thành mã thoát.

Tăng một sự kiện kiểm toán pty.spawn với đối số argv.auditing event pty.spawn with argument argv.

Đã thay đổi trong phiên bản 3.4: pty0 Bây giờ trả về giá trị trạng thái từ os.waitpid() trên quy trình con.pty0 now returns the status value from os.waitpid() on the child process.

Thí dụ¶

Chương trình sau đây hoạt động giống như tập lệnh lệnh UNIX (1), sử dụng đầu cuối giả để ghi lại tất cả các đầu vào và đầu ra của một phiên đầu cuối trong một bản tóm tắt.

import argparse
import os
import pty
import sys
import time

parser = argparse.ArgumentParser()
parser.add_argument('-a', dest='append', action='store_true')
parser.add_argument('-p', dest='use_python', action='store_true')
parser.add_argument('filename', nargs='?', default='typescript')
options = parser.parse_args()

shell = sys.executable if options.use_python else os.environ.get('SHELL', 'sh')
filename = options.filename
mode = 'ab' if options.append else 'wb'

with open(filename, mode) as script:
    def read(fd):
        data = os.read(fd, 1024)
        script.write(data)
        return data

    print('Script started, file is', filename)
    script.write(('Script started on %s\n' % time.asctime()).encode())

    pty.spawn(shell, read)

    script.write(('Script done on %s\n' % time.asctime()).encode())
    print('Script done, file is', filename)