Включить доступ к SSH-оболочке, но отключить доступ к SFTP

21

Я искал жизнеспособный ответ на этот вопрос, и большинство ответов содержат советы о том, почему не следует этого делать. Тем не менее, вот сценарий, и что делает это необходимым:

У меня есть консольное приложение, и в .profile каждого пользователя есть команда запуска для приложения, и непосредственно после команды, которая его запускает, есть команда «exit», которая выводит их из системы. Я только хочу, чтобы они могли получить доступ к этому консольному приложению через предоставленный им интерфейс. После запуска приложение предоставляет пользователю список клиентов, к которым можно получить доступ через приложение, причем каждый клиент имеет свой собственный каталог данных. Пользователям предоставляется доступ только к тем клиентам, к которым им потребуется доступ.

Теперь вот проблема: если я предоставлю пользователям доступ по SSH, они также смогут войти в систему с помощью SFTP-клиента, что даст им прямой доступ к каталогам данных для приложения, что ОЧЕНЬ нежелательно, так как это также даст им доступ к каталогам данных, к которым у них не должно быть доступа.

Это было так просто сделать при использовании комбинации telnet / FTP, но теперь, когда я хочу предоставить пользователям доступ из любого места в Интернете, я не смог найти способ отключить их от SFTP, хотя по-прежнему позволяя им получить доступ к оболочке, где они могут запустить приложение.

sosaisapunk
источник
8
Я забываю подробности, но я думаю, что SSH позволяет вам ограничить выполнение одной команды при входе в систему. Они не получают полный доступ к оболочке, если вы это настроите. Это может быть полезно для вашего случая использования. (В конце концов, можно эмулировать доступ к SFTP с использованием SSHFS. Простое отключение SFTP не помешает умеренно определенному пользователю получить доступ к любому файлу, к которому имеет доступ его учетная запись.)
David Z
3
Кроме того, вы, возможно, захотите рассмотреть "chroot" ваших пользователей. и для свободного доступа к данным, это похоже на проблему дизайна
Деннис Нольте
2
Использование .profileдля этого звучит как неправильное решение. Я полагаю, что установка пользователя с альтернативной оболочкой имела бы гораздо больше смысла.
kasperd
3
Не пытайтесь использовать .profileхитрость, чтобы ограничить доступ, поскольку это тривиально, чтобы обойти. (подробности см. в моем ответе)
Алекси Торхамо

Ответы:

22

Редактировать:

В случае, если это не очевидно, следующий ответ не предназначен как безопасный метод предотвращения использования SFTP кем-либо, имеющим доступ к серверу. Это просто ответ, который объясняет, как отключить его от внешней видимости. Обсуждение безопасности на уровне пользователя смотрите в ответах @cpast и @Aleksi Torhamo. Если безопасность находится в центре вашего внимания, этот ответ не является правильным. Если ваше внимание сосредоточено на простом обслуживании, то это ваш ответ.

Теперь перейдем к исходному ответу:


Закомментируйте поддержку sftp в sshd_config (и, конечно, перезапустите sshd):

#Subsystem sftp /usr/lib/openssh/sftp-server

Wesley
источник
1
Иногда линия может бытьSubsystem sftp internal-sftp
Кондыбас
1
У меня есть Subsystem sftp /usr/libexec/sftp-server Но это добилось цели. Большое спасибо
sosaisapunk
16
Это не звучит правдоподобно. Если вы можете выполнять произвольные команды на сервере, вы можете запустить программу на стороне сервера sftp. Даже если он не установлен, вы можете повторно реализовать его как длинную команду оболочки, и клиент sftp отправит эту команду вместо sftp. Этот метод может сделать менее удобным использование sftp, но нет способа помешать пользователю, который может запускать произвольные команды, использовать эти команды для передачи файлов.
R ..
1
@ Sosaisapunk Это не правда. Пользователи могут запускать любую команду по своему усмотрению ssh user@host command, поскольку .profile, если вы это сделаете, она вообще не будет запускаться, и, следовательно, ваше приложение вообще не запустится. Они могут получить полный доступ к оболочке, просто сказав ssh -t user@host bash. Просто попробуйте, и вы увидите. Подсистема - это просто псевдоним команды; если бы они могли использовать sftp раньше, они все равно могли бы использовать его - и любую другую команду, которую они хотят. Прочитайте мой ответ ниже.
Алекси Торхамо
1
@sosaisapunk: Нет, дело в том, что вы можете сделать это с помощью ssh, но не с помощью, .profileпоскольку он не предназначен для безопасности и его легко обойти. В своем ответе я перечислил три разных способа сделать это с помощью ssh. Короче говоря, просто переместите вызов вашего приложения из .profileсценария оболочки и либо 1) установите сценарий оболочки в качестве оболочки пользователя 2) установите сценарий оболочки как (правильно подобранный) ForceCommandв sshd_config3) переключитесь на аутентификацию с открытым ключом и установите скрипт оболочки как commandв .ssh/authorized_keys. (Кроме того, вы должны использовать @name, чтобы люди получали уведомления о комментариях)
Алекси Торхамо
28

Как уже упоминали другие, отключение sftpдалеко не достаточно - пользователь с неограниченным sshдоступом может просматривать любой файл, доступ к которому имеет его учетная запись, может изменять все, что он имеет право изменять, и может легко загружать все, что он может читать, для своих собственных машина. Единственный способ помешать им сделать это - фактически ограничить их доступ. Также не стоит полагаться на .profileограничение пользователей, поскольку это не то, для чего это (Правка: как упоминает Алекси в своем ответе, на самом деле тривиально обойтись .profile; суть в том, .profileчто это для удобства, а не безопасности, поэтому это не так. предназначен для ограничения пользователей. Используйте средства, разработанные для обеспечения безопасности (например, приведенные ниже, для обеспечения безопасности).

Есть два основных способа сделать это: вы можете ограничить их с помощью прав доступа к файлу или заставить их выполнять только ваше консольное приложение. Второй способ лучше: назначить группу пользователей, которые должны быть ограничены консольным приложением (например customers); затем sshd_configдобавьте следующие строки:

Match Group customers
ForceCommand /path/to/app

Это делает так, чтобы все соединения от пользователей в этой группе открывали консольное приложение; они не могут запускать что-либо еще, включая sftpинструмент сервера. Это также мешает им делать что - либо еще с системой, и, в отличие от этого .profile, делает это с использованием самого SSH-сервера ( .profileограничивает их в оболочке, а ForceCommandтакже предотвращает другие действия, не связанные с запуском оболочки). Также в отличие от .profileэтого, это разработано как вещь безопасности; это специально сделано, чтобы противостоять злоумышленнику, уклоняющемуся от него.

Альтернатива (вероятно, низшая) может включать создание нового пользователя для запуска консольного приложения. Затем вы ограничите каталоги данных этим пользователем, установите консольное приложение, принадлежащее этому пользователю, и включите u+sпрограмму. Это setuidбит; это означает, что тот, кто запускает консольную программу, делает это с разрешениями владельца программы. Таким образом, пользователь сам не имеет доступа к каталогам, он получает его только через программу. Тем не менее, вы, вероятно, должны просто использовать ForceCommand, поскольку это ограничивает весь доступ к «просто запустить эту программу».

cpast
источник
4
Я хотел бы добавить, что ForceCommandэто не мешает переадресации портов SSH.
nyuszika7h
1
На самом деле, полагаться на .profileнечто большее, чем «не идеально»; его легко обойти (подробности см. в моем ответе) и, таким образом, он не обеспечивает никакой защиты, только ложное чувство безопасности.
Алекси Торхамо
@AleksiTorhamo Ах. Я подозревал, что вы могли бы обойти это, но не был уверен, как (обычно я подозреваю, что вещи, не предназначенные для безопасности, можно обойти). Спасибо за подробности о том, как!
cpast
15

Не пытайтесь делать это, .profileпотому что это не обеспечивает никакой безопасности и абсолютно ничего не ограничивает!

Это не имеет значения , что вы положили в .profile, так как вы можете обойти это, просто давая команду для запуска в командной строке SSH, например: ssh user@host command. Вы все еще можете получить нормальный доступ к оболочке, выполнив ssh -t user@host bash.

Отключение подсистемы sftp, как упоминалось в другом ответе, совсем не помогает. Подсистемы по сути являются просто псевдонимами команд, и вы все равно можете нормально использовать sftp sftp -s /path/to/sftp-executable user@host.

Как говорили cpast и некоторые комментаторы, вы должны использовать надлежащие механизмы для ограничения доступа. То есть,

  • Использовать ForceCommandвsshd_config
  • Используйте логин без пароля и command="..."в.ssh/authorized_keys
  • Измените оболочку пользователя на что-то, что ограничивает возможности пользователя

Заметки:

  • command="..." применяется только к одному ключу, поэтому он не ограничивает ssh вход в систему для пользователя, использующего пароль или другой ключ
  • Возможно, вы также захотите ограничить переадресацию портов и т. Д. (О которых я слышал - переадресация портов, пересылка x11, переадресация агентов и распределение pty)
    • AllowTcpForwarding и т. д. в sshd_config
    • no-port-forwarding и т. д. в .ssh/authorized_keys
  • Если у вас запущены другие демоны (например, FTP), вы должны убедиться, что они не впускают пользователя (некоторые демоны принимают это решение на основе оболочки пользователя, поэтому, если вы измените это, вы можете захотеть еще раз проверить это)
  • Вы можете изменить оболочку пользователя на скрипт, который делает то, что вы хотите; это либо без аргументов, либо какscript -c 'command-the-user-wanted-to-run'
  • Обе команды ForceCommandи command="..."запускают команду через пользовательскую оболочку, чтобы они не работали, если для пользовательской оболочки установлено, например,. /bin/falseили/sbin/nologin

Отказ от ответственности: я ни в коем случае не являюсь экспертом в этом вопросе, поэтому, хотя я могу сказать, .profileчто это небезопасно, я не могу обещать, что с другими методами, которых я не знаю, нет никакой «ошибки» около. Насколько я знаю, они в безопасности, но я не был бы первым, кто ошибся в Интернете.

Алекси Торхамо
источник
1
Кажется , что по крайней мере, ForceCommandи заставил беспарольный вход с command=в authorized_keys, в то время как он был обойден до того , что происходит из - за ошибки на сервере: он предназначен , чтобы быть защищенными от злоумышленника, и пользователя в обходе он считается серьезной уязвимостью в SSH-сервере (и, таким образом, является приоритетом). Как вы .profileуказали, по замыслу это обходится: так как это не считается функцией безопасности, пользователь, обходя ее, совершенно нормально с точки зрения разработчика оболочки.
cpast
1
@cpast: Да, я думал о существовании дополнительных функций, таких как переадресация портов. Я имею в виду, что если вы не знали, что ssh позволяет переадресацию портов и просто использовали ForceCommandдля ограничения доступа, и у вас был демон, который только прослушивает соединения локально и не выполняет аутентификацию, пользователь ssh мог бы по-прежнему обращаться к демону. Функции, которые я перечислил, являются такими, например. Решения для git-хостинга обычно отключаются, и я не видел никаких дополнительных «зловещих» решений на страницах man-страниц, но я еще не нашел никакого официального документа «это то, как вы используете ForceCommandбезопасно» - также.
Алекси Торхамо
По общему признанию, ~/.profileэто редактируемый пользователем и не полезный для безопасности, но могли бы вы сделать метод cpast значимым, вставив его в /etc/profile? Вы можете проверить UID, чтобы ограничить его нужным пользователям.
птенцы
1
@chicks: Нет, у него точно такая же проблема. Проблема не в том, что файл редактируется пользователем; Проблема в том, что оба файла можно полностью обойти. Файлы используются только для оболочек входа в систему, которые вы получаете, если вы просто скажете ssh user@host, но если вы скажете ssh запустить команду - т.е. ssh user@host command- вы больше не получаете оболочку входа в систему и файлы не затрагиваются вообще. Таким образом, вы можете просто обойти ограничения, которые кто-то пытался создать с помощью файлов, просто предоставив дополнительный аргумент ssh.
Алекси Торхамо
2
@chicks: Кроме того, я только что понял, что вы ссылались на cpast; метод в ответе cpast не использует .profile, он использует sshd_configи должен быть безопасным. Он упоминает только .profileкак метод, который вы не должны использовать для этого.
Алекси Торхамо
1

Можно включить SSH и отключить SFTP как глобально, так и для каждого пользователя / группы.

Лично мне это нужно, потому что я хочу предоставить доступ к некоторым git-репозиториям через SSH, и мне нравится отключать ненужные системы. В этом случае SFTP не нужен.

глобально

Вы можете отключить SFTP для всех пользователей несколькими способами.

Недостающая подсистема

SFTP-демон, используемый SSH, можно настроить через Subsystemключевое слово. Из sshd_config(5)руководства:

Subsystem
        Configures an external subsystem (e.g. file transfer daemon).
        Arguments should be a subsystem name and a command (with optional
        arguments) to execute upon subsystem request.

        The command sftp-server(8) implements the “sftp” file transfer
        subsystem.

        Alternately the name “internal-sftp” implements an in-process
        “sftp” server.  This may simplify configurations using
        ChrootDirectory to force a different filesystem root on clients.

        By default no subsystems are defined.

Последняя строка предполагает, что этого должно быть достаточно, чтобы не определять подсистему для «sftp».

Ложная ложь

Вы также можете отключить SFTP, установив демон SFTP, используемый SSH, на что-то непригодное. Например, настройте подсистему "sftp" на /bin/false:

Subsystem sftp /bin/false

Когда что-то пытается войти через SFTP, демон SSH пытается запустить «демон sftp» /bin/false. /bin/falseПрограмма делает только одну вещь, и это возвращает код ошибки. Попытка подключения SFTP фактически отклонена.

На пользователя / группу

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

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

согласование

Чтобы соответствовать группе пользователей, вы можете настроить SSH с Matchключевым словом. Из sshd_config(5)руководства:

Match
        ...

        The arguments to Match are one or more criteria-pattern pairs or the
        single token All which matches all criteria.  The available criteria
        are User, Group, Host, LocalAddress, LocalPort, and Address.  The
        match patterns may consist of single entries or comma-separated
        lists and may use the wildcard and negation operators described in
        the PATTERNS section of ssh_config(5).

        ...

Пара примеров:

  • Match User eva соответствует пользователю "eva"
  • Match User stephen,maria соответствует пользователям "Стивен" и "Мария"
  • Match Group wheel,adams,simpsons соответствует группам "колесо", "адамс", "симпсоны"

Если вы хотите получить больше информации, в sshd_config(5)руководстве есть грузы .

Принудительная команда

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

Команду force можно настроить с помощью ForceCommandключевого слова. Из sshd_config(5)руководства:

ForceCommand
        Forces the execution of the command specified by ForceCommand,
        ignoring any command supplied by the client and ~/.ssh/rc if
        present.  The command is invoked by using the user's login shell
        with the -c option.  This applies to shell, command, or subsystem
        execution.  It is most useful inside a Match block.  The command
        originally supplied by the client is available in the
        SSH_ORIGINAL_COMMAND environment variable.  Specifying a command of
        “internal-sftp” will force the use of an in-process sftp server that
        requires no support files when used with ChrootDirectory.  The
        default is “none”.

Таким образом, вы можете использовать ограниченную команду, которую хотите использовать ForceCommand <your command>. Например:

Match User kim
        ForceCommand echo 'successful login man, congrats'

пример

В моем случае, когда я хочу дать доступ к git, мне нужен только доступ к пользователю git-shell. Это раздел, который отключает SFTP для моих пользователей git, а также некоторые параметры безопасности:

Match Group git

        # have to do this instead of setting the login shell to `git-shell`,
        # to disable SFTP
        ForceCommand /usr/bin/git-shell -c "$SSH_ORIGINAL_COMMAND"

        # disable stuff we don't need
        AllowAgentForwarding no
        AllowTcpForwarding no
        AllowStreamLocalForwarding no
        PermitOpen none
        PermitTunnel no
        PermitTTY no
        X11Forwarding no
Од
источник
В моем случае я хотел разрешить доступ к MySQL (запретив доступ как к SFTP, так и к окнам терминала SSH) для определенного авторизованного ключа (т. Е. Никаких изменений в файле sshd_config). Мне удалось сделать это с помощью следующих параметров ~ / .ssh / authorized_keys для конкретного ключа: command = "/ usr / bin / echo 'Разрешен только доступ к MySQL.'", No-pty, no-X11-forwarding, allowopen = "127.0.0.1:3306"
Martin_ATS