Доброго времени суток, коллеги. Бьюсь над задачей:
- сделать везде злой 2FA (допустим, я параноик)
- иметь возможность пользоваться ansible
Проблематика в том, что для ansible (насколько мне удалось выяснить) нужна работа по ssh-ключу (по паролю тоже можно, но это такое себе).
ansible (насколько мне известно) не умеет 2FA, да и глупо это пытаться автоматизировать такие подключения.
Настраивал 2FA вот по такой статейке
Допустим в системе есть спец пользователь ans_user для ansible. Допустим хост с которого нужно запускать плейбуки находится строго в приватной сети и имеет адрес 10.10.10.10/24
Пробовал на узлах играться с Match конструкциями, но как показывает практика либо спустя часы раскуренных статей я так ничего и не понял как оно рабтает, либо оно реально работает не так как описано в статьях.
Параметры sshd согласно статье по ссылке выше + PermitRootLogin no
Пробовал задать вот такое:
Match User ans_user Address 10.10.10.10
AuthenticationMethods publickey
PasswordAuthentication no
PubkeyAuthentication yes
Но ничего не работает. Если выкосить 2FA настройки и, например, задать по-умолчанию авторизацию по ключу, а в Match прописать авторизацию по паролю, то работать будет только по паролю и только для указанной комбинации пользователя и хоста (согласно доке), но как только в дело вступает 2FA, то все это превращается в кашу и я начинаю сходить с ума.
Собственно вопрос: можно ли сделать как то адекватно так, чтобы с определенного узла или списка узлов была выключена 2FA для конкретного пользователя и работал строго ключ?
Если да, то ткните носом пожалуйста. Спасибо!
=== UPD. 20200204 16:51 Перепробовав всякое и отчаявшись решил попробовать вариант с 2мя ssh демонами, где основной настроен по классике: ssh-key + google-authenticator где указание обоих атрибутов является обязательным и второй демон огороженный фаерволом разрешенный только в частной сети с конфигурацией:
PasswordAuthentication no
PublickeyAuthentication yes
ChallengeResponseAuthentication no
AuthenticationMethods publickey
AllowUsers ans_user@10.10.10.10
Протестировал. Работает так как я хотел. Теперь получается нужно на все узлы подобное разложить и запустить.
Не могу сказать что рад за такое решение, все же думал о чем то более элегантном и простом. Но пока от безысходности оставлю так.
=== UPD. 20200206 18:37
Помог режим дебага (а могло помочь элементарное, но внимательное чтение манов).
В мануале на Step 3 было сказано добавить параметры в конец файла (bottom).
Match директивы я объявлял выше + в примерах после match все ниже переопределяемые параметры шли с отступами. Я ОШИБОЧНО подумал, что строки ниже где отступов нет не являются частью MATCH конструкции. В итоге не выполняющийся match не выставлял 2FA и я рвал волосы на голове от того, что не могу понять логику работы.
В итоге для меня правильным решением стало такое:
/etc/pam.d/sshd
#%PAM-1.0
#auth substack password-auth
auth include postlogin
account required pam_sepermit.so
account required pam_nologin.so
account include password-auth
password include password-auth
# pam_selinux.so close should be the first session rule
session required pam_selinux.so close
session required pam_loginuid.so
# pam_selinux.so open should only be followed by sessions to be executed in the user context
session required pam_selinux.so open env_params
session required pam_namespace.so
session optional pam_keyinit.so force revoke
session optional pam_motd.so
session include password-auth
session include postlogin
-session optional pam_reauthorize.so prepare
auth required pam_google_authenticator.so
/etc/ssh/sshd_config
HostKey /etc/ssh/ssh_host_rsa_key
HostKey /etc/ssh/ssh_host_ecdsa_key
HostKey /etc/ssh/ssh_host_ed25519_key
SyslogFacility AUTHPRIV
PermitRootLogin no
AuthorizedKeysFile .ssh/authorized_keys
PasswordAuthentication no
PubkeyAuthentication yes
ChallengeResponseAuthentication yes
GSSAPIAuthentication no
GSSAPICleanupCredentials no
UsePAM yes
X11Forwarding yes
PrintMotd no
UseDNS no
AcceptEnv LANG LC_CTYPE LC_NUMERIC LC_TIME LC_COLLATE LC_MONETARY LC_MESSAGES
AcceptEnv LC_PAPER LC_NAME LC_ADDRESS LC_TELEPHONE LC_MEASUREMENT
AcceptEnv LC_IDENTIFICATION LC_ALL LANGUAGE
AcceptEnv XMODIFIERS
Subsystem sftp /usr/libexec/openssh/sftp-server
ClientAliveInterval 120
ClientAliveCountMax 2
AuthenticationMethods publickey,keyboard-interactive
Match User ans_user Address 10.10.10.10
AuthenticationMethods publickey
Match User ans_user Address 127.0.0.1
AuthenticationMethods publickey
Match Address *,!10.10.10.10,!127.0.0.1
DenyUsers ans_user
AuthenticationMethods publickey,keyboard-interactive
Всем спасибо за помощь.