Какой наилучший способ перенести файл с удаленного хоста на локальный через сеанс SSH?

StackOverflow https://stackoverflow.com/questions/49896

  •  09-06-2019
  •  | 
  •  

Вопрос

При подключении к удаленным хостам через ssh я часто хочу перенести файл из этой системы в локальную систему для просмотра или обработки.Есть ли способ скопировать файл без (а) открытия нового терминала / приостановки сеанса ssh (б) повторной аутентификации на локальном или удаленном хостах, который работает (в) даже если один или оба хоста находятся за маршрутизатором NAT?

Цель состоит в том, чтобы извлечь как можно больше преимуществ из текущего состояния:что между двумя машинами есть соединение, что я аутентифицирован на обеих, что я нахожусь в рабочем каталоге файла - так что мне не нужно открывать другой терминал и копировать и вставлять удаленный хост и путь к нему, что я и делаю сейчас.Лучшее решение также не потребовало бы никакой настройки до начала сеанса, но если настройка была одноразовой или могла быть автоматизирована, то это вполне приемлемо.

Это было полезно?

Решение 7

Вот мое предпочтительное решение этой проблемы.Настройте обратный ssh-туннель при создании ssh-сеанса.Это упрощается с помощью двух функций bash:функция grabfrom() должна быть определена на локальном хосте, в то время как функция grab() должна быть определена на удаленном хосте.Вы можете добавить любые другие переменные ssh, которые вы используете (например-X или -Y), как вы сочтете нужным.

function grabfrom() { ssh -R 2202:127.0.0.1:22 ${@}; };
function grab() { scp -P 2202 $@ localuser@127.0.0.1:~; };

Использование:

localhost% grabfrom remoteuser@remotehost
password: <remote password goes here>
remotehost% grab somefile1 somefile2 *.txt
password: <local password goes here>

Положительные стороны:

  • Он работает без специального программного обеспечения на любом хосте, кроме OpenSSH
  • Это работает, когда локальный хост находится за маршрутизатором NAT
  • Это может быть реализовано в виде пары из двух однострочных функций bash

Негативы:

  • Он использует фиксированный номер порта, поэтому:
    • не будет работать с несколькими подключениями к удаленному хосту
    • может возникнуть конфликт с процессом, использующим этот порт на удаленном хосте
  • Для этого требуется, чтобы localhost принимал ssh-соединения
  • Для начала сеанса требуется специальная команда
  • Он неявно обрабатывает аутентификацию на локальном хостинге
  • Это не позволяет указать каталог назначения на localhost
  • Если вы подключаетесь с нескольких локальных хостов к одному и тому же удаленному хосту, ssh не понравится смена ключей

Будущая работа:Это все еще довольно запутанно.Очевидно, что проблему с аутентификацией можно было бы решить, соответствующим образом настроив ssh-ключи, и еще проще разрешить спецификацию удаленного каталога, добавив параметр в grab()

Более сложным является устранение других негативных факторов.Было бы неплохо выбрать динамический порт, но, насколько я могу судить, нет элегантного способа передать этот порт командной строке на удаленном хосте;Насколько я могу судить, OpenSSH не позволяет вам устанавливать произвольные переменные окружения на удаленном хосте, а bash не может принимать переменные окружения из аргумента командной строки.Даже если бы вы могли выбрать динамический порт, нет никакого способа гарантировать, что он не используется на удаленном хосте без предварительного подключения.

Другие советы

зссшЗМОДЕМ оболочка поверх openssh) делает именно то, что вы хотите.

  • Установить зссш и используйте его вместо openssh (который, я предполагаю, вы обычно используете)

  • У вас должен быть lrzsz пакет установлен в обеих системах.

Затем, чтобы передать файл zyxel.png с удаленного на локальный хост:

antti@local:~$ zssh remote
Press ^@ (C-Space) to enter file transfer mode, then ? for help
...
antti@remote:~$ sz zyxel.png
**B00000000000000
^@
zssh > rz
Receiving: zyxel.png
Bytes received:  104036/ 104036   BPS:16059729

Transfer complete
antti@remote:~$ 

Загрузка происходит аналогично, за исключением того, что вы просто переключаетесь rz(1) и sz(1).

Пользователи Putty могут попробовать Ле Шпаклевка, который обладает аналогичной функциональностью.

На коробке Linux я использую ssh-агент и sshfs.Вам необходимо настроить sshd так, чтобы он принимал соединения с парами ключей.Затем вы используете ssh-add, чтобы добавить свой ключ к ssh-агенту, чтобы вам не приходилось каждый раз вводить свой пароль.Обязательно используйте -t секунд, чтобы ключ не оставался загруженным вечно.
ssh-add -t 3600 /главная страница/пользователя/.ssh/ssh_dsa

После этого,
имя хоста sshfs:/ /PathToMountTo/
смонтирует файловую систему сервера на вашем компьютере, чтобы у вас был к ней доступ.

Лично я написал небольшой bash-скрипт, который добавляет мой ключ и монтирует серверы, которыми я пользуюсь чаще всего, поэтому, когда я начинаю работать, мне просто нужно запустить скрипт и ввести свою кодовую фразу.

Используя некоторые малоизвестные и редко используемые функции openssh реализация, вы можете добиться именно того, чего хотите!

  • использует преимущества текущего состояния
  • можете использовать рабочий каталог, в котором вы находитесь
  • не требует никакой настройки туннелирования перед началом сеанса
  • не требует открытия отдельного терминала или подключения
  • может использоваться как разовая сделка в интерактивном сеансе или как часть автоматического сеанса.

Вы должны ввести только то, что есть в каждом из local>, remote>, и ssh> подсказки в приведенных ниже примерах.

local> ssh username@remote
remote> ~C
ssh> -L6666:localhost:6666
remote> nc -l 6666 < /etc/passwd
remote> ~^Z
[suspend ssh]
[1]+  Stopped                 ssh username@remote
local> (sleep 1; nc localhost 6666 > /tmp/file) & fg
[2] 17357
ssh username@remote
remote> exit
[2]-  Done                    ( sleep 1; nc localhost 6666 > /tmp/file )
local> cat /tmp/file
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:daemon:/sbin:/sbin/nologin
...

Или, чаще всего, вы хотите пойти в другом направлении, например, если вы хотите сделать что-то вроде переноса вашего ~/.ssh/id_rsa.pub файл с вашего локального компьютера на ~/.ssh/authorized_keys файл удаленной машины.

local> ssh username@remote
remote> ~C
ssh> -R5555:localhost:5555
remote> ~^Z
[suspend ssh]
[1]+  Stopped                 ssh username@remote
local> nc -l 5555 < ~/.ssh/id_rsa.pub &
[2] 26607
local> fg
ssh username@remote
remote> nc localhost 5555 >> ~/.ssh/authorized_keys
remote> cat ~/.ssh/authorized_keys
ssh-rsa AAAAB3NzaC1yc2ZQQQQBIwAAAQEAsgaVp8mnWVvpGKhfgwHTuOObyfYSe8iFvksH6BGWfMgy8poM2+5sTL6FHI7k0MXmfd7p4rzOL2R4q9yjG+Hl2PShjkjAVb32Ss5ZZ3BxHpk30+0HackAHVqPEJERvZvqC3W2s4aKU7ae4WaG1OqZHI1dGiJPJ1IgFF5bWbQl8CP9kZNAHg0NJZUCnJ73udZRYEWm5MEdTIz0+Q5tClzxvXtV4lZBo36Jo4vijKVEJ06MZu+e2WnCOqsfdayY7laiT0t/UsulLNJ1wT+Euejl+3Vft7N1/nWptJn3c4y83c4oHIrsLDTIiVvPjAj5JTkyH1EA2pIOxsKOjmg2Maz7Pw== username@local

Здесь уместно дать небольшое объяснение.

Первый шаг - открыть LocalForward;если у вас еще не установлен один из них, вы можете использовать ~C escape-символ для открытия командной строки ssh, которая выдаст вам следующие команды:

remote> ~C
ssh> help
Commands:
      -L[bind_address:]port:host:hostport    Request local forward
      -R[bind_address:]port:host:hostport    Request remote forward
      -D[bind_address:]port                  Request dynamic forward
      -KR[bind_address:]port                 Cancel remote forward

В этом примере я устанавливаю LocalForward на порту 6666 локального хостинга как для клиента, так и для сервера;номер порта может быть любым произвольный открытый порт.

Тот Самый nc команда исходит от netcat упаковка;он описан как "Швейцарский армейский нож TCP / IP";это простая, но очень гибкая и полезная программа.Сделайте это стандартной частью вашего набора инструментов unix.

На данный момент nc прослушивает порт 6666 и ожидает, пока другая программа подключится к этому порту, чтобы она могла отправить содержимое /etc/passwd.

Далее мы используем другой экранирующий символ ~^Z который является tilde за которым следует control-Z.Это временно приостанавливает процесс ssh и возвращает нас обратно в нашу оболочку.

Один обратно в локальную систему, который вы можете использовать nc для подключения к переадресованному порту 6666.Обратите внимание на отсутствие -l в данном случае, потому что этот параметр указывает nc прослушивать порт так, как если бы это был сервер, что не то, чего мы хотим;вместо этого мы хотим просто использовать nc в качестве клиента для подключения к уже прослушиваемому nc на удаленной стороне.

Остальная часть магии вокруг nc команда обязательна, потому что, если вы помните, выше я сказал, что ssh процесс был временно приостановлен, поэтому & поставит весь (sleep + nc) выражение уходит на задний план и sleep дает вам достаточно времени для ssh, чтобы вернуться на передний план с fg.

Во втором примере идея в основном та же, за исключением того, что мы создали туннель, ведущий в другом направлении, используя -R вместо того, чтобы -L таким образом, мы устанавливаем RemoteForward.И затем на локальной стороне находится место, где вы хотите использовать -l аргумент в пользу nc.

Экранирующий символ по умолчанию равен ~, но вы можете изменить его с помощью:

 -e escape_char
         Sets the escape character for sessions with a pty (default: ‘~’).  The escape character is only recognized at the beginning of a line.  The escape character followed by a dot
         (‘.’) closes the connection; followed by control-Z suspends the connection; and followed by itself sends the escape character once.  Setting the character to “none” disables any
         escapes and makes the session fully transparent.

Полное объяснение команд, доступных с помощью управляющих символов, доступно в справочная страница ssh

ESCAPE CHARACTERS
     When a pseudo-terminal has been requested, ssh supports a number of functions through the use of an escape character.

     A single tilde character can be sent as ~~ or by following the tilde by a character other than those described below.  The escape character must always follow a newline to be interpreted
     as special.  The escape character can be changed in configuration files using the EscapeChar configuration directive or on the command line by the -e option.

     The supported escapes (assuming the default ‘~’) are:

     ~.      Disconnect.

     ~^Z     Background ssh.

     ~#      List forwarded connections.

     ~&      Background ssh at logout when waiting for forwarded connection / X11 sessions to terminate.

     ~?      Display a list of escape characters.

     ~B      Send a BREAK to the remote system (only useful for SSH protocol version 2 and if the peer supports it).

     ~C      Open command line.  Currently this allows the addition of port forwardings using the -L, -R and -D options (see above).  It also allows the cancellation of existing remote port-
             forwardings using -KR[bind_address:]port.  !command allows the user to execute a local command if the PermitLocalCommand option is enabled in ssh_config(5).  Basic help is avail‐
             able, using the -h option.

     ~R      Request rekeying of the connection (only useful for SSH protocol version 2 and if the peer supports it).

Использование ControlMaster (переключатель -M) - лучшее решение, намного проще и удобнее, чем остальные ответы здесь.Это позволяет вам совместно использовать одно соединение для нескольких сеансов.Похоже, это делает то, чего хочет плакат.Однако вам все равно придется ввести командную строку scp или sftp.Попробуй это.Я использую его для всех своих операций.

Чтобы сделать это, мой домашний маршрутизатор настроен на перенаправление порта 22 обратно на мой домашний компьютер (который защищен брандмауэром, чтобы принимать ssh-соединения только с моего рабочего компьютера), и у меня также есть учетная запись, настроенная на Динадны предоставить динамический DNS, который автоматически преобразуется в мой домашний IP-адрес.

Затем, когда я подключаюсь по ssh к своему рабочему компьютеру, первое, что я делаю, это запускаю скрипт, который запускает ssh-агент (если ваш сервер не делает этого автоматически).Сценарий, который я запускаю, это:

#!/bin/bash

ssh-agent sh -c 'ssh-add < /dev/null && bash'

Он запрашивает мою кодовую фразу ssh-ключа, чтобы мне не приходилось вводить ее каждый раз.Вам не нужен этот шаг, если вы используете ssh-ключ без парольной фразы.

В оставшуюся часть сеанса отправка файлов обратно на ваш домашний компьютер выполняется следующим образом:

scp file_to_send.txt your.domain.name:~/

Вот такой взлом под названием ssh-xfer который решает точную проблему, но требует исправления OpenSSH, который, насколько мне известно, не запускается.

Вы можете использовать протокол SCP для передачи файла.вы можете перейти по этой ссылке

http://tekheez.biz/scp-protocol-in-unix/

Вы должны быть в состоянии настроить открытые и закрытые ключи так, чтобы аутентификация не требовалась.

Какой способ вы это сделаете, зависит от требований безопасности и т.д. (Имейте в виду, что существуют ssh-черви linux / unix, которые будут просматривать ключи, чтобы найти другие хосты, которые они могут атаковать).

Я делаю это постоянно из-за маршрутизаторов linksys и dlink.Я думаю, вам, возможно, придется изменить пару настроек, но это не имеет большого значения.

Используйте переключатель -M.

"Переводит ssh-клиент в режим "master" для совместного использования соединений.Опция Multiple -M переводит ssh в режим `master", при этом требуется подтверждение, прежде чем будут приняты подчиненные соединения.Обратитесь к описанию ControlMaster в ssh_config(5) для получения подробной информации ".

Я не совсем понимаю, как это отвечает на вопрос оператора - не могли бы вы немного подробнее остановиться на этом, Дэвид?

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top