У нас есть бастионный сервер B. Нам нужен SSH от A до B к C, используя закрытый ключ.
Какой вариант лучше:
Положите закрытый SSH-ключ на сервере Б. Мы читаем, что делать это в производственной среде - плохая идея.
Из Вот:
Никогда не размещайте свои закрытые ключи SSH в экземпляре бастиона. Вместо этого используйте пересылку агента SSH, чтобы сначала подключиться к бастиону, а оттуда - к другим экземплярам в частных подсетях. Это позволяет хранить закрытый ключ SSH только на вашем компьютере.
Использовать Перенаправление агента SSH. Для настройки пересылки агента мне нужно разрешить пересылку TCP. При настройке пересылки агента на хосте пересылки создается файл сокета, который является механизмом, с помощью которого ключ может быть переадресован в пункт назначения. В настройках Bastion в AWS:
TCP forward: установка этого значения в true включает пересылку TCP (SSH-туннелирование). Это может быть очень полезно, но это также угроза безопасности, поэтому мы рекомендуем оставить настройку по умолчанию (отключена), если не требуется.
Также из Вот:
Пересылка агента SSH считается вредной
Что лучше? А как насчет альтернативы по второй ссылке: ProxyCommand, Я понимаю, что это помогает с проблемой файла сокета, но все же я думаю, что мне нужно включить пересылку TCP, так что это достаточно безопасно?
Я бы рекомендовал использовать ProxyCommand
(или даже лучше ProxyJump
поскольку синтаксис проще, но требует openssh 7.3+, я думаю, на стороне клиента), и вам не нужно развертывать закрытый ключ на Bastion, все остается локальным.
На вашем клиентском компьютере вы пишете файл под ~/.ssh/config
с содержанием, аналогичным приведенному ниже:
Host bastion
HostName bastion.example.com
User bastion-user
Port 22
IdentityFile ~/.ssh/id_bastion
Host srvC
HostName srvC.local
User server-user
IdentityFile ~/.ssh/id_protected_lan
ProxyJump bastion
Затем делая ssh srvC
соединит вас с C через B (бастион) без пересылки агентов и без развертывания закрытого ключа в бастионе.
В приведенном выше примере "bastion" - это псевдоним вашего хоста Bastion, а srvC - псевдоним вашего сервера C. HostName
вам нужно указать либо IP-адреса, либо настоящее полное доменное имя для ваших хостов. Для пользователей вам необходимо обновить User
для правильного имени пользователя на Bastion и сервере C. Наконец IdentityFile
не является обязательным, если вы используете локальный агент (например, KeeAgent или ssh-agent), но если он не запущен, он также будет работать и запрашивать у вас все ключевые парольные фразы.
Конечно, вам нужно развернуть общественный ключи к бастиону и srvC. Вы можете использовать (знак $ предназначен только для иллюстрации приглашения, не вводите его):
$ ssh-copy-id -i ~/.ssh/id_bastion.pub \
-o PreferredAuthentications=password \
-o PubkeyAuthentication=no \
bastion
$ ssh-copy-id -i ~/.ssh/id_protected_lan.pub \
-o PreferredAuthentications=password \
-o PubkeyAuthentication=no \
srvC
Примечание: вышеуказанное будет работать, только если аутентификация по паролю все еще разрешена. После вышеуказанного развертывания и проверки того, что все работает должным образом, вы должны запретить аутентификацию по паролю на 2 серверах.
Если у вас более старая версия OpenSSH, которая не поддерживает ProxyJump
(на стороне клиента), затем замените:
ProxyJump bastion
по
ProxyCommand ssh -q -W %h:%p bastion
Насколько я понял, это похоже.
Я видел ответ про ProxyJump. Давайте поговорим о ProxyCommand.
Но подождите, подождите! Я могу написать тебе как взломать сервер который использует переадресацию агента, было бы намного легче понять разницу!
Для основных шагов: вы можете прочитать мой пост Вот
Основные шаги следующие:
-Создайте конфиг в ~ / .ssh / config
Host bast
Hostname BASTION_IP
ForwardAgent yes
User bastion
-Добавьте свой ключ аутентификации в ssh-agent
ssh-add ~/.ssh/name_rsa
-Подключитесь к бастиону
ssh bast
-Подключение сервера приложений от бастиона
ssh app@IP -p PORT
Вы можете задать мне вопрос:
Насколько безопасен мой сервер? И ответ довольно прост:
Зачем?
А в чем проблема?
Зачем?
В каталоге / tmp вы можете увидеть что-то вроде этого:
[root@localhost tmp]# ll
total 12
drwx------ 2 bastion bastion 4096 Sep 7 17:35 ssh-mKX88v0Vlo
Откроем временный файл
[root@localhost tmp]# cd ssh-mKX88v0Vlo/
[root@localhost ssh-mKX88v0Vlo]# ll
total 0
srwxr-xr-x 1 bastion bastion 0 Sep 7 17:35 agent.10507
Посмотрим связи к этому идентификатору процесса.
netstat -nxp | grep 10507
результат:
unix [ ] STREAM CONNECTED 501384 10507/sshd: bastion
и кто подключен?
lsof -i -a -p 10507
результат:
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
sshd 10507 bastion 3u IPv4 501301 0t0 TCP *IP*:ssh->*IP*:8279 (ESTABLISHED)
Мы также можем видеть файлы сокетов:
cd /proc/10507/fd/
ls
результат:
lrwx------ 1 root root 64 Sep 7 17:46 0 -> /dev/null
lrwx------ 1 root root 64 Sep 7 17:46 1 -> /dev/null
lrwx------ 1 root root 64 Sep 7 17:46 10 -> /dev/ptmx
lrwx------ 1 root root 64 Sep 7 17:46 14 -> /dev/ptmx
lrwx------ 1 root root 64 Sep 7 17:46 15 -> /dev/ptmx
lrwx------ 1 root root 64 Sep 7 17:46 2 -> /dev/null
lrwx------ 1 root root 64 Sep 7 17:46 3 -> socket:[501994]
lrwx------ 1 root root 64 Sep 7 17:46 4 -> socket:[502069]
lrwx------ 1 root root 64 Sep 7 17:46 5 -> socket:[502072]
l-wx------ 1 root root 64 Sep 7 17:46 6 -> /run/systemd/sessions/1836.ref
lr-x------ 1 root root 64 Sep 7 17:46 7 -> pipe:[502079]
l-wx------ 1 root root 64 Sep 7 17:46 8 -> pipe:[502079]
lrwx------ 1 root root 64 Sep 7 17:46 9 -> socket:[502080]
И что случается когда клиент будет подключен на удаленный сервер? Посмотрим:
lrwx------ 1 root root 64 Sep 7 17:46 0 -> /dev/null
lrwx------ 1 root root 64 Sep 7 17:46 1 -> /dev/null
lrwx------ 1 root root 64 Sep 7 17:46 10 -> /dev/ptmx
lrwx------ 1 root root 64 Sep 7 17:48 11 -> socket:[502267]
lrwx------ 1 root root 64 Sep 7 17:46 14 -> /dev/ptmx
lrwx------ 1 root root 64 Sep 7 17:46 15 -> /dev/ptmx
lrwx------ 1 root root 64 Sep 7 17:46 2 -> /dev/null
lrwx------ 1 root root 64 Sep 7 17:46 3 -> socket:[501994]
lrwx------ 1 root root 64 Sep 7 17:46 4 -> socket:[502069]
lrwx------ 1 root root 64 Sep 7 17:46 5 -> socket:[502072]
l-wx------ 1 root root 64 Sep 7 17:46 6 -> /run/systemd/sessions/1836.ref
lr-x------ 1 root root 64 Sep 7 17:46 7 -> pipe:[502079]
l-wx------ 1 root root 64 Sep 7 17:46 8 -> pipe:[502079]
lrwx------ 1 root root 64 Sep 7 17:46 9 -> socket:[502080]
Мы даже можем увидеть, используется ли файл сокета, используя netstat:
unix 3 [ ] STREAM CONNECTED 502267 10561/sshd:
bastion /tmp/ssh-oVoMXC6vb8/agent.10561
unix 3 [ ] STREAM CONNECTED 502072 10561/sshd: bastion
Теперь нам нужно украсть информацию о сокете, пока сеанс хоста бастиона открыто. О, нам тоже нужно IP-адрес целевого сервера, поэтому просто используйте netstat:
netstat -tn
В Заключительный этап использовать перенаправленный файл сокета
eval "$(ssh-agent -s)"
SSH_AUTH_SOCK=/tmp/ssh-EAKxOdL4fl/agent.10507
Проверить, загружен ли ключ.
ssh-add -l
результат должен быть что-то как это:
2048 SHA256:2Psdl..B5KQ /home/usr/.ssh/name_rsa (RSA)
Host app
Hostname *.*.*.*
IdentityFile ~/.ssh/your_rsa
User *******
Port ****
ProxyCommand ssh -W %h:%p bast
Host bast
Hostname *.*.*.*
ForwardAgent no
User ******
По основным операциям: как передавать файлы через серверы (с клиента на сервер, с сервера на клиент) вы можете прочитать в моем посте Вот
Вывод
Подробнее см. Мой блог. Вдобавок у меня есть несколько скриншотов, так что они могут быть вам полезны.
Просто используйте Перенаправление агента SSH как и большинство других.
Преимущество: на бастионе нет ключей, которыми можно было бы воспользоваться не по назначению.
Надеюсь, это поможет :)