Vấn đề với câu trả lời từ @jakuje là: nó chỉ hoạt động với các socket , nhưng bạn không thể sử dụng các công cụ UNIX tiêu chuẩn để mong đợi các tệp với chúng:
ssh -R/tmp/sock.remote:/tmp/sock.local "$HOST" 'LANG=C cat >/tmp/sock.remote'
bash: /tmp/sock.remote: Không có thiết bị hoặc địa chỉ như vậy
Ngoài ra, có vấn đề là tệp ổ cắm cục bộ không bị xóa trên máy chủ từ xa; Khi tiếp theo bạn chạy cùng một lệnh, bạn sẽ nhận được cảnh báo và ổ cắm không được tạo lại chính xác. Bạn có thể cung cấp tùy chọn -o StreamLocalBindUnlink=yes
để ssh
bỏ liên kết mà ổ cắm cũ, nhưng trong các thử nghiệm của tôi đó là không đủ; bạn cũng phải chỉnh sửa bạn sshd_config
để chứa StreamLocalBindUnlink=yes
tùy chọn đó hoạt động.
Nhưng bạn có thể sử dụng socat
hoặc netcat
hoặc bất kỳ công cụ tương tự khác hỗ trợ socket địa phương UNIX ( netcat-traditional
là KHÔNG đủ!) Để sử dụng các chuyển tiếp ổ cắm địa phương để chuyển tập tin:
# start local process listening on local socket, which receives the data when ssh opens the connections and saves it to a local file
nc -l -N -U /tmp/sock.local >/tmp/file.local &
# connect to remote $HOST and pipe the remote file into the remote socket end
ssh \
-o ExitOnForwardFailure=yes \
-o StreamLocalBindUnlink=yes \
-R /tmp/sock.remote:/tmp/sock.local \
"$HOST" \
'nc -N -U /tmp/sock.remote </tmp/file.remote'
Bạn cũng có thể chạy các lệnh tương tác, trong trường hợp đó bạn nên sử dụng ssh -t
để phân bổ TTY.
Vấn đề với giải pháp này là bạn phải mã hóa cứng các đường dẫn của các socket cục bộ UNIX: Về mặt cục bộ, đây không phải là vấn đề nhiều như bạn có thể đưa $$
vào đường dẫn để làm cho nó trở thành duy nhất cho mỗi tiến trình hoặc thư mục tạm thời, nhưng trên từ xa, tốt hơn hết bạn không nên sử dụng thư mục có thể ghi trên thế giới /tmp/
như trong ví dụ của tôi. Thư mục cũng phải tồn tại khi ssh
phiên bắt đầu. Và inode ổ cắm sẽ vẫn còn ngay cả sau khi phiên được đóng lại, vì vậy sử dụng cái gì đó như "$ HOME / .ssh. $$" sẽ làm lộn xộn thư mục của bạn với các nút chết theo thời gian.
Bạn cũng có thể sử dụng các socket TCP bị ràng buộc localhost
, điều này sẽ giúp bạn tránh làm lộn xộn các hệ thống tệp của bạn với các nút chết, nhưng ngay cả với chúng, bạn vẫn phải gặp vấn đề khi chọn số cổng không sử dụng (duy nhất). Vì vậy, vẫn không lý tưởng. ( ssh
có mã để phân bổ động các cổng, nhưng tôi không tìm thấy cách nào để lấy thông tin đó trên máy chủ từ xa.)
Có lẽ giải pháp đơn giản nhất để sao chép tệp là sử dụng chức năng chia sẻ kết nối tích hợp của ssh và thực hiện một lệnh scp
hoặc sfrp
trong khi phiên tương tác của bạn vẫn chạy song song. Xem Sao chép tệp trở lại hệ thống cục bộ bằng ssh .
closefrom(STDERR_FILENO + 1)
cuộc gọi khác nhau theo mã nguồn OpenSSH. Bạn đang cố gắng làm gì để đòi hỏi điều này?