Блок 13
Удалённый доступ: SSH и передача файлов
> Что вас ждёт в этом блоке: вы впервые в курсе по-настоящему войдёте в другой компьютер через сеть — без клавиатуры и монитора у той машины, просто набрав команду в своём терминале. Именно так раб…
Введение в блок
> Что вас ждёт в этом блоке: вы впервые в курсе по-настоящему войдёте в другой компьютер через сеть — без клавиатуры и монитора у той машины, просто набрав команду в своём терминале. Именно так работают системные администраторы с реальными серверами каждый день. Мы разберём протокол SSH от основ до продвинутых настроек, научимся копировать файлы между машинами тремя разными способами и настроим удобный конфиг для быстрого подключения.
>
> Что нужно знать перед началом: весь материал Блока 12 (IP-адреса, порты, DNS, сетевые команды). SSH — это сетевой протокол, работающий поверх всего, что мы там изучили: он использует IP-адрес для нахождения сервера, порт для обращения к нужной службе, и TCP для надёжной передачи данных.
Урок 13.1. Что такое SSH и зачем он нужен
Понять, зачем существует SSH, какую проблему он решает, как устроен «под капотом» на концептуальном уровне, и почему именно SSH стал стандартом де-факто для удалённого управления серверами во всём мире.
Теория
Представьте: вы арендовали сервер в дата-центре в другом городе (мы подробно поговорим об этом в Блоке 20). Там стоит компьютер с Ubuntu, работающий круглосуточно — но у него нет монитора, клавиатуры и мыши, подключённых физически. Как вы будете им управлять? Именно для этого и существует SSH.
SSH (Secure Shell, «безопасная оболочка») — это сетевой протокол и одновременно программа, которая позволяет безопасно управлять удалённым компьютером через терминал по сети. Ключевое слово здесь — безопасно.
Чтобы понять, почему безопасность принципиально важна, нужно сделать маленький исторический экскурс. До SSH администраторы использовали другие протоколы для удалённого доступа — прежде всего Telnet (существует с 1969 года). Telnet работал просто: вы подключались к удалённому компьютеру и вводили команды. Но у него была катастрофическая уязвимость: всё передавалось по сети в открытом виде, как обычный текст. Это означало, что любой, кто мог «прослушивать» сетевой трафик между вами и сервером (а это технически не так уж сложно в локальных сетях), мог видеть всё: ваш пароль, все команды, которые вы вводите, и все ответы сервера. В эпоху, когда серверы начали подключаться к интернету, это стало неприемлемым.
SSH создан в 1995 году финским программистом Тату Юлёненом именно как ответ на реальный инцидент: в его университетской сети кто-то запустил программу-сниффер (перехватчик трафика), которая собирала логины и пароли пользователей. Юлёнен понял, что нужен принципиально другой подход — протокол, при котором даже если злоумышленник перехватит весь передаваемый трафик, он не сможет ничего из него извлечь.
Как SSH решает проблему безопасности — криптография в двух словах.
SSH шифрует весь передаваемый трафик. Когда вы подключаетесь к серверу через SSH, происходит следующее:
- Установка соединения: клиент (ваш компьютер) и сервер «договариваются» об алгоритмах шифрования, которые будут использовать, и обмениваются специальными криптографическими данными для генерации общего секретного ключа сессии.
- Проверка подлинности сервера: ваш SSH-клиент проверяет, что вы подключаетесь именно к тому серверу, к которому намеревались, а не к машине злоумышленника, которая притворяется сервером (атака «человек посередине», man-in-the-middle). Для этого используется fingerprint (отпечаток) — уникальная криптографическая подпись сервера.
- Аутентификация пользователя: сервер проверяет, кто вы. Это можно делать двумя способами — паролем или SSH-ключами (урок 13.3 посвящён именно ключам).
- Шифрованный туннель: после успешной аутентификации все данные — ваши команды, ответы сервера, даже передаваемые файлы — передаются в зашифрованном виде. Перехватив трафик, злоумышленник увидит лишь бессмысленный набор байт.
Архитектура клиент-сервер. SSH работает по уже знакомой нам из Блока 12 (урок 12.5 про порты и службы) модели клиент-сервер:
- SSH-сервер (демон
sshd— SSH Daemon; о том, что такое демон, мы подробно говорили в Блоке 10) работает на удалённой машине, которой вы хотите управлять. Он слушает входящие подключения на порту 22** (стандартный порт SSH, один из тех «зарезервированных» портов до 1024, о которых мы говорили в уроке 12.5). В Ubuntu пакет называетсяopenssh-server. - SSH-клиент** — программа на вашей машине, которой вы инициируете подключение. В Ubuntu это команда
ssh. Пакет называетсяopenssh-clientи обычно предустановлен в Ubuntu по умолчанию.
Версии SSH. Существуют SSHv1 и SSHv2. Первая версия имела серьёзные криптографические уязвимости и сегодня считается устаревшей и небезопасной. Все современные системы используют исключительно SSHv2, и в этом курсе, говоря «SSH», мы всегда имеем в виду именно вторую версию.
Где применяется SSH на практике:
- Управление удалёнными серверами (VPS, выделенные серверы, облачные инстансы) — основное применение.
- Передача файлов между машинами (SCP, SFTP, rsync через SSH — уроки 13.5, 13.6, 13.7).
- Туннелирование (проброс портов) — возможность создавать зашифрованные «туннели» для другого трафика.
- Git-операции с удалёнными репозиториями (мы коснёмся этого в Блоке 16).
- Автоматизация: скрипты (Блок 15) могут выполнять команды на удалённых серверах через SSH без интерактивного входа.
Практика
В этом вводном уроке мы не подключаемся к удалённым машинам (это будет в следующем уроке), а знакомимся с тем, что уже есть в вашей системе.
Шаг 1. Проверьте, установлен ли SSH-клиент в вашей системе:
```bash
ssh -V
```
Что вы увидите: строку вида OpenSSH_9.x, OpenSSL 3.x.x ... — версию установленного OpenSSH. Если команда не найдена, установите клиент: sudo apt install openssh-client.
[Скриншот терминала]
Шаг 2. Проверьте, установлен ли SSH-сервер (он нужен, чтобы другие могли подключаться к вашей машине; для практики следующего урока мы установим его явно):
```bash
dpkg -l | grep openssh
```
Что вы увидите: список установленных пакетов OpenSSH. Строка с openssh-client означает наличие клиента, строка с openssh-server — наличие сервера.
Шаг 3. Если SSH-сервер не установлен — установите его (он понадобится нам в следующем уроке для практики):
```bash
sudo apt install openssh-server
```
Что произойдёт: система установит пакет и автоматически запустит службу sshd. Можете убедиться в этом командой, знакомой из Блока 10:
```bash
sudo systemctl status ssh
```
Что вы увидите: строку Active: active (running) — служба работает.
[Скриншот терминала]
Шаг 4. Посмотрите, на каком порту слушает SSH-сервер (используем команду ss из урока 12.5, которую мы уже применяли для работы с портами):
```bash
sudo ss -tlnp | grep sshd
```
Что вы увидите: строку, подтверждающую, что процесс sshd слушает порт 22 (или другой, если сервер был ранее перенастроен).
[Скриншот терминала]
Разбор команд
Команда ssh -V
- Назначение:** вывести версию установленного SSH-клиента.
- Синтаксис:**
ssh -V - Примечание:**
-V(заглавная буква) — это именно версия (Version). Строчная-v— это verbose (подробный вывод отладочной информации при подключении), совсем другая опция.
Команда dpkg -l | grep openssh
- Назначение:** проверить, какие пакеты OpenSSH установлены в системе.
dpkg -lвыводит список всех установленных пакетов (мы изучалиdpkgв Блоке 9), аgrep(Блок 6) фильтрует только строки, содержащие «openssh». - Синтаксис:**
dpkg -l [фильтр]
Команда sudo systemctl status ssh
- Назначение:** проверить статус службы SSH-сервера. Полное внутреннее имя демона —
sshd, но в Ubuntu командаsystemctlпринимает и краткое имяssh. - Синтаксис:** уже подробно разобрана в Блоке 10 (управление службами через
systemctl).
Возможные ошибки
- Ошибка:** команда
sshне найдена (command not found).
Почему возникает: пакет openssh-client не установлен (на минимальных серверных установках Ubuntu это возможно).
Как определить: запустить ssh — получить сообщение bash: ssh: command not found.
Как исправить: sudo apt install openssh-client.
Как избежать: на Ubuntu Desktop пакет обычно предустановлен; на Server-редакции может отсутствовать.
- Ошибка:** служба
sshdне запускается после установки.
Почему возникает: чаще всего — конфликт портов (что-то другое уже занимает порт 22), реже — повреждённая установка.
Как определить: sudo systemctl status ssh покажет ошибку вместо active (running), а в логах (sudo journalctl -u ssh -n 30 — команда journalctl изучалась в Блоке 10) будет конкретная причина.
Как исправить: изучить сообщение об ошибке в логах и устранить причину; чаще всего достаточно sudo systemctl restart ssh.
Практические задания
- Найдите в уже изученном нами файле
/etc/services(он упоминался в Блоке 12) строку, соответствующую SSH, и запишите в конспект, какой порт и протокол (TCP или UDP) там указан:grep -w ssh /etc/services. - Прочитайте вывод команды
ssh -Vна своей системе и найдите в интернете информацию о том, какие криптографические алгоритмы поддерживает установленная у вас версия OpenSSH. - Своими словами объясните в конспекте (не подглядывая), чем SSH принципиально отличается от Telnet, и почему этот протокол стал стандартом для удалённого управления серверами.
Проверка знаний
Вопрос 1. Что конкретно шифрует SSH при передаче данных по сети — только пароль при входе, или весь последующий трафик тоже?
Ответ: SSH шифрует весь передаваемый трафик целиком: и процесс аутентификации (включая пароль), и все команды, которые вы вводите, и все ответы сервера. После установки зашифрованного соединения ни одна передаваемая единица данных не проходит по сети в открытом виде.
Вопрос 2. Какие два компонента должны быть установлены на разных машинах, чтобы SSH-подключение стало возможным, и как называются соответствующие пакеты в Ubuntu?
Ответ: На машине, к которой подключаются (сервер), должен быть установлен и запущен SSH-сервер — пакет openssh-server (демон sshd, слушающий порт 22). На машине, с которой подключаются (клиент), должен быть установлен SSH-клиент — пакет openssh-client (команда ssh).
Итоги урока
Вы изучили: историю SSH и проблему, которую он решил (небезопасность Telnet), принцип шифрования трафика, архитектуру клиент-сервер, стандартный порт 22, пакеты openssh-client и openssh-server.
Вы умеете: проверить наличие и версию SSH-клиента и сервера, убедиться в работе службы sshd.
В следующем уроке потребуется: понимание того, что SSH-сервер должен быть запущен на машине, к которой мы подключаемся, — именно это вы настроили на шаге 3 практики.
Урок 13.2. Подключение к удалённому серверу: `ssh user@host`
Выполнить первое реальное SSH-подключение, понять синтаксис команды ssh, разобраться с процессом аутентификации, с тем, что такое known_hosts, и освоить типичные параметры команды.
Теория
Базовый синтаксис команды ssh:
```
ssh [опции] пользователь@хост
```
Здесь:
пользователь— имя учётной записи на удалённой машине, под которой вы хотите войти (это не обязательно то же имя, что у вашего локального пользователя — у вас на ноутбуке может быть пользовательanna, а на сервере вы хотите войти какadmin).хост— IP-адрес или доменное имя удалённой машины (подробно про IP и DNS мы говорили в Блоке 12).- Символ
@разделяет пользователя и хост — как в адресе электронной почты.
Что происходит при первом подключении к новому серверу.
Когда вы первый раз подключаетесь к какому-то серверу, SSH-клиент не знает этого сервера. Прежде чем установить соединение, он показывает вам нечто подобное:
```
The authenticity of host '192.168.1.100 (192.168.1.100)' can't be established.
ED25519 key fingerprint is SHA256:AbCdEfGhIjKlMnOpQrStUvWxYz1234567890abcdef.
This key is not known by any other names.
Are you sure you want to continue connecting (yes/no/[fingerprint])?
```
Это не ошибка — это важный механизм защиты. SSH-сервер имеет свой уникальный криптографический ключ (host key, «ключ хоста»), который и идентифицирует именно этот сервер. Клиент говорит вам: «Я вижу этот сервер впервые и не могу подтвердить его подлинность. Вот его отпечаток (fingerprint) — проверьте, тот ли это сервер, к которому вы хотите подключиться».
На практике при подключении к своей виртуальной машине или заведомо известному серверу вы просто вводите yes. Клиент сохраняет fingerprint сервера в файле ~/.ssh/known_hosts (в домашней папке вашего пользователя, в скрытой папке .ssh — о скрытых файлах и папках мы говорили в уроке 5.4). При всех последующих подключениях к тому же адресу SSH автоматически сверяет fingerprint с сохранённым — если он совпадает, всё в порядке. Если fingerprint изменился (например, на сервере была переустановлена ОС, что меняет его ключи), SSH выдаст серьёзное предупреждение — потому что это может означать атаку подмены сервера.
Что происходит после подтверждения.
После ввода yes SSH запрашивает пароль пользователя на удалённой машине. Важно: вводимые символы не отображаются — это стандартное поведение, которое мы уже видели в уроке 8.3 при работе с sudo. После правильного ввода пароля вы получаете приглашение командной строки удалённой машины — с этого момента все команды, которые вы набираете в своём терминале, выполняются на удалённой машине.
Как понять, на какой машине вы сейчас работаете. Приглашение командной строки изменится: вместо user@mycomputer:~$ вы увидите что-то вроде user@remoteserver:~$. Имя хоста (часть после @) — это имя той машины, на которой выполняются команды. Команды whoami и hostname (показывает имя текущей машины) мгновенно прояснят ситуацию.
Завершение SSH-сессии. Чтобы выйти из удалённой машины и вернуться в свой локальный терминал, используйте команду exit или нажмите Ctrl+D — оба способа закрывают SSH-сессию.
Практика на одной машине через loopback. Для практики этого урока вам не обязательно иметь вторую физическую машину. Вы можете подключиться к localhost (IP-адрес 127.0.0.1 — loopback-адрес, который мы изучали в уроке 12.5) — то есть ваша машина выступит одновременно и SSH-клиентом, и SSH-сервером. Это полностью реальный SSH, отличается только то, что клиент и сервер находятся на одном физическом компьютере.
Дополнительные параметры команды ssh, которые часто используются:
-p номер_порта— подключиться на нестандартный порт (например, если администратор сервера перенёс SSH с порта 22 на другой — это популярная мера безопасности, которую мы разберём в Блоке 14).-v— verbose (подробный) режим: SSH выводит детальную информацию о каждом шаге установки соединения. Очень полезно для диагностики проблем с подключением.-i путь/к/ключу— указать конкретный файл приватного SSH-ключа для аутентификации (разбираем ключи в уроке 13.3).-X— включить X11-forwarding (проброс графических приложений — редко нужно, но возможность интересная).
Практика
Для практики этого урока нам нужны два пользователя на одной машине (чтобы наглядно показать: вы входите не как «себя», а как другой пользователь). Создадим тестового пользователя.
Шаг 1. Убедитесь, что SSH-сервер запущен (мы делали это в предыдущем уроке):
```bash
sudo systemctl status ssh
```
Должен быть статус active (running). Если нет — sudo systemctl start ssh.
Шаг 2. Создайте тестового пользователя специально для практики SSH (команды useradd и passwd мы подробно изучили в уроке 8.4):
```bash
sudo useradd -m -s /bin/bash sshtest
sudo passwd sshtest
```
Введите простой запоминаемый тестовый пароль дважды, например TestPass123.
Шаг 3. Выполните SSH-подключение к localhost под именем тестового пользователя:
```bash
ssh sshtest@localhost
```
Что произойдёт: при первом подключении SSH спросит подтверждение fingerprint. Введите yes.
[Скриншот терминала с вопросом о fingerprint]
Шаг 4. После ввода пароля вы окажетесь в SSH-сессии. Обратите внимание на изменившееся приглашение командной строки — теперь там указано имя пользователя sshtest. Убедитесь в этом:
```bash
whoami
hostname
pwd
```
Что вы увидите: whoami вернёт sshtest (не ваш обычный пользователь!), hostname — имя вашей машины, pwd — домашнюю папку пользователя sshtest (/home/sshtest). Это наглядно демонстрирует, что SSH создаёт полноценный сеанс работы от имени другого пользователя.
[Скриншот терминала]
Шаг 5. Попробуйте несколько команд в SSH-сессии — они выполняются точно так же, как если бы вы сидели за этой машиной:
```bash
ls -la
echo "Я внутри SSH-сессии!"
date
```
Шаг 6. Посмотрите файл known_hosts, который SSH создал при первом подключении, перед тем как выйти из сессии (откройте второй терминал или сначала посмотрите, потом выйдите):
```bash
exit
```
Теперь вы вернулись в локальный терминал. Проверьте файл known_hosts:
```bash
cat ~/.ssh/known_hosts
```
Что вы увидите: строку с fingerprint сервера localhost, который SSH сохранил при первом подключении. При следующих подключениях к localhost SSH будет автоматически сверять fingerprint с этой записью.
[Скриншот файла known_hosts]
Шаг 7. Подключитесь снова, на этот раз указав порт явно (хотя 22 — это значение по умолчанию, так что результат тот же):
```bash
ssh -p 22 sshtest@localhost
```
На этот раз вопроса о fingerprint не будет — SSH уже «знает» этот сервер.
```bash
exit
```
Шаг 8. Удалите тестового пользователя после практики:
```bash
sudo userdel -r sshtest
```
Разбор команд
Команда ssh
- Назначение:** установить SSH-соединение с удалённым сервером и открыть интерактивный терминал на нём.
- Синтаксис:**
ssh [опции] [пользователь@]хост [команда] - Основные параметры:**
пользователь@хост— имя пользователя и адрес/имя хоста (еслипользователь@опустить, используется имя текущего локального пользователя).-p порт— указать нестандартный порт (по умолчанию — 22).-i файл_ключа— указать файл приватного ключа для аутентификации.-v— подробный вывод для диагностики (можно-vvи-vvvдля ещё большей детализации).-X— включить проброс X11 (для запуска графических программ через SSH).команда— если указать команду в конце, SSH выполнит её на сервере и вернёт результат, не открывая интерактивный терминал:ssh user@host ls /var/log— вывести список файлов в/var/logна сервере и сразу вернуться в локальный терминал.- Реальные примеры использования:**
ssh admin@192.168.1.100— подключиться к серверу по IP.ssh deploy@mysite.example.com— подключиться к серверу по доменному имени.ssh -p 2222 user@server.com— подключиться на нестандартный порт 2222.ssh user@server.com 'df -h'— выполнить одну команду на сервере (проверить место на диске) и сразу получить результат.- Типичные ошибки:**
- Попытка подключиться к выключенной машине или к машине без запущенного
sshd: соединение «зависает» или сразу выдаёт ошибкуConnection refused(если SSH-сервер не слушает порт) илиConnection timed out(если машина недоступна в сети). - Ввод пароля локального пользователя вместо пароля пользователя на удалённой машине: SSH спрашивает именно пароль пользователя на сервере.
Команда exit
- Назначение:** завершить SSH-сессию и вернуться в локальный терминал.
- Синтаксис:**
exit(без параметров) или нажать Ctrl+D.
Команда hostname
- Назначение:** вывести имя текущего компьютера. Полезна для проверки, на какой именно машине вы сейчас работаете — особенно в SSH-сессиях.
- Синтаксис:**
hostname
Возможные ошибки
- Ошибка:**
Connection refusedпри попытке подключения.
Почему возникает: SSH-сервер не запущен на целевой машине, или запущен на другом порту, или заблокирован firewall.
Как определить: запустить ssh -v user@host для подробного вывода; проверить на сервере sudo systemctl status ssh и sudo ss -tlnp | grep sshd.
Как исправить: запустить SSH-сервер (sudo systemctl start ssh) или убедиться в правильности порта.
Как избежать: перед первым подключением к серверу убедиться, что там установлен и запущен openssh-server.
- Ошибка:**
Host key verification failed— SSH отказывает в подключении, потому что fingerprint сервера изменился.
Почему возникает: сервер был переустановлен (что генерирует новые ключи), или вы подключаетесь к другой машине с тем же IP, или (в редких случаях!) реальная атака подмены сервера.
Как определить: SSH выводит предупреждение с красным текстом REMOTE HOST IDENTIFICATION HAS CHANGED! и указывает номер строки в файле ~/.ssh/known_hosts, которая конфликтует.
Как исправить: если вы точно знаете, что сервер был переустановлен (или изменился IP) — удалите конфликтующую строку из known_hosts: ssh-keygen -R хост_или_ip — и подключитесь снова, подтвердив новый fingerprint. Если причина смены fingerprint вам неизвестна — отнеситесь к этому серьёзно и выясните причину, прежде чем подтверждать.
Как избежать: при переустановке сервера заранее предупреждать себя (и коллег) о том, что fingerprint изменится.
- Ошибка:**
Permission denied (publickey,password)после ввода правильного (как вам кажется) пароля.
Почему возникает: неправильный пароль, не тот пользователь, или аутентификация по паролю отключена в настройках SSH-сервера.
Как определить: убедиться, что вводите правильный пароль именно пользователя на удалённой машине. Запустить ssh -v user@host для диагностики.
Как исправить: проверить правильность имени пользователя и пароля. Если на сервере отключена аутентификация по паролю — нужно использовать SSH-ключи (следующий урок).
Практические задания
- Подключитесь к localhost под своим собственным именем пользователя (без
@localhost— SSH использует текущее имя пользователя по умолчанию; простоssh localhost), выполните командыwhoami,uname -aиuptimeв SSH-сессии, сделайте скриншот для конспекта, затем выйдите. - Попробуйте выполнить одну команду на «сервере» без открытия интерактивного терминала:
ssh ваш_пользователь@localhost 'ls /etc | head -10'— изучите, как это работает. - Найдите файл
~/.ssh/known_hostsи изучите его содержимое: сколько записей там уже есть, что означает каждая колонка каждой строки.
Проверка знаний
Вопрос 1. Почему при первом подключении к новому серверу SSH показывает fingerprint и просит подтверждение — разве это не лишнее неудобство?
Ответ: Это важный механизм защиты от атаки «человек посередине» (man-in-the-middle). Файл known_hosts запоминает fingerprint каждого сервера. При следующих подключениях SSH автоматически проверяет, что fingerprint не изменился — это гарантирует, что вы подключаетесь именно к тому серверу, а не к машине злоумышленника, которая перехватила ваш запрос.
Вопрос 2. Вы подключились по SSH к серверу и хотите выяснить, что именно выполняет сервер прямо сейчас — как это сделать, не выходя из SSH-сессии?
Ответ: Находясь в SSH-сессии, можно использовать все уже изученные команды — например, top или htop (Блок 11) для просмотра активных процессов, df -h для состояния дисков (Блок 9), systemctl status для состояния служб (Блок 10). SSH предоставляет полноценный терминальный доступ, ничем не отличающийся от работы непосредственно за клавиатурой сервера.
Итоги урока
Вы изучили: синтаксис команды ssh, процесс первого подключения и fingerprint, файл known_hosts, важные параметры -p, -v, -i.
Вы умеете: подключаться к серверу (и к localhost) по SSH с аутентификацией по паролю, выполнять команды в SSH-сессии, корректно выходить из сессии.
В следующем уроке потребуется: понимание того, что SSH-соединение устанавливается успешно — следующий шаг замена аутентификации по паролю на значительно более безопасные SSH-ключи.
Урок 13.3. SSH-ключи: `ssh-keygen` и `ssh-copy-id`
Освоить аутентификацию по SSH-ключам — более безопасный и удобный способ входа на сервер, не требующий ввода пароля каждый раз и практически исключающий взлом перебором.
Теория
Мы уже умеем входить на сервер по паролю. Почему этого недостаточно и зачем нужны ключи?
Проблемы аутентификации по паролю:
- Уязвимость к перебору (brute force). Злоумышленник может написать программу, которая будет перебирать тысячи паролей в секунду, пытаясь угадать ваш. Слабые пароли (и даже многие «средние») могут быть подобраны так.
- Неудобство. При каждом подключении нужно вводить пароль — это утомительно, если вы подключаетесь к серверам десятки раз в день, как это делают реальные администраторы.
- Опасность подбора. Если сервер доступен из интернета, на порту 22 постоянно идут автоматические попытки подключения — это можно увидеть в логах реального сервера. Боты сканируют весь диапазон IP-адресов и пробуют стандартные пароли.
SSH-ключи решают все эти проблемы. Они основаны на асимметричной криптографии — математическом принципе, при котором генерируются два связанных ключа:
- Приватный ключ** (private key) — хранится только у вас, никогда не покидает ваш компьютер. Это ваш «секрет». Файл обычно называется
id_ed25519илиid_rsa. - Публичный ключ** (public key) — можно свободно раздавать кому угодно. Файл называется
id_ed25519.pubилиid_rsa.pub(расширение.pub). Этот ключ кладётся на серверы, к которым вы хотите подключаться.
Как работает аутентификация по ключам (упрощённо):
- Вы инициируете подключение к серверу.
- Сервер проверяет, есть ли в файле
~/.ssh/authorized_keysпубличный ключ, соответствующий тому, что предъявляет клиент. - Сервер отправляет клиенту случайное «задание» (challenge), зашифрованное вашим публичным ключом.
- Только тот, у кого есть соответствующий приватный ключ, может расшифровать это задание и дать правильный ответ.
- Клиент расшифровывает задание приватным ключом и отправляет ответ.
- Сервер проверяет ответ — если всё верно, вы вошли, без ввода пароля.
Суть: приватный ключ никогда не покидает вашу машину. Взломать такую аутентификацию перебором практически невозможно — математически это потребовало бы вычислительных ресурсов, которых не существует.
Типы ключей. SSH поддерживает несколько криптографических алгоритмов для ключей:
- Ed25519 — современный, быстрый, короткие ключи, считается наиболее безопасным на сегодняшний день. Рекомендуется для новых ключей.**
- RSA** — более старый, но широко поддерживается; если используете RSA, минимум 4096 бит.
- ECDSA** — промежуточный вариант.
- DSA** — устаревший, не рекомендуется.
Passphrase — ещё один уровень защиты. При создании ключа SSH предлагает установить passphrase (кодовую фразу) — это пароль, которым зашифрован сам файл приватного ключа на вашем диске. Если злоумышленник получит файл вашего приватного ключа (например, украдёт ноутбук), он всё равно не сможет его использовать без passphrase. Для учебных ключей passphrase можно не устанавливать (нажать Enter дважды), но для реальных рабочих ключей она настоятельно рекомендуется.
Где хранятся ключи. По умолчанию всё, связанное с SSH, хранится в папке ~/.ssh/ (в домашней папке текущего пользователя):
~/.ssh/id_ed25519— приватный ключ (права доступа должны быть строго600— читать может только владелец; о правах доступа подробно в уроке 8.6).~/.ssh/id_ed25519.pub— публичный ключ.~/.ssh/authorized_keys— файл на сервере, содержащий публичные ключи всех, кому разрешено входить под этим пользователем.~/.ssh/known_hosts— уже знакомый нам файл с fingerprint'ами серверов.~/.ssh/config— файл конфигурации (урок 13.4).
Команда ssh-keygen генерирует пару ключей (приватный + публичный).
Команда ssh-copy-id копирует ваш публичный ключ на сервер, добавляя его в файл ~/.ssh/authorized_keys нужного пользователя. Это удобная утилита, которая автоматически делает то, что иначе пришлось бы делать вручную.
Практика
Шаг 1. Создайте тестового пользователя для практики:
```bash
sudo useradd -m -s /bin/bash sshkeytest
sudo passwd sshkeytest
```
Шаг 2. Сгенерируйте пару SSH-ключей типа Ed25519:
```bash
ssh-keygen -t ed25519 -C "учебный ключ для курса Linux"
```
Что произойдёт: команда задаст три вопроса:
Enter file in which to save the key (/home/ваш_пользователь/.ssh/id_ed25519):— путь для сохранения ключа. Нажмите Enter, чтобы принять путь по умолчанию.Enter passphrase (empty for no passphrase):— кодовая фраза. Для этого учебного ключа нажмите Enter (без passphrase), чтобы упростить практику.Enter same passphrase again:— подтверждение. Снова Enter.
Что вы увидите: характерный «рисунок» из символов — визуализация fingerprint нового ключа (это просто красивое представление, не несёт функциональной нагрузки), а также строки с путями к созданным файлам.
[Скриншот терминала]
Шаг 3. Убедитесь, что ключи созданы:
```bash
ls -la ~/.ssh/
```
Что вы увидите: как минимум файлы id_ed25519 (приватный ключ, права 600) и id_ed25519.pub (публичный ключ, права 644). Обратите особое внимание на права доступа — SSH намеренно делает приватный ключ нечитаемым для других пользователей.
Шаг 4. Посмотрите на публичный ключ (его можно свободно показывать — это не секрет):
```bash
cat ~/.ssh/id_ed25519.pub
```
Что вы увидите: одну длинную строку вида ssh-ed25519 AAAA...длинный набор символов... учебный ключ для курса Linux. Именно эту строку нужно добавлять в ~/.ssh/authorized_keys на серверах.
[Скриншот публичного ключа]
Шаг 5. Скопируйте публичный ключ на «сервер» (в нашем случае — для пользователя sshkeytest на localhost):
```bash
ssh-copy-id sshkeytest@localhost
```
Что произойдёт: ssh-copy-id спросит пароль пользователя sshkeytest (последний раз — после этого пароль больше не понадобится!) и добавит ваш публичный ключ в файл /home/sshkeytest/.ssh/authorized_keys.
Что вы увидите: сообщение вида Number of key(s) added: 1 и инструкцию, как теперь подключиться.
[Скриншот результата ssh-copy-id]
Шаг 6. Теперь подключитесь по SSH — на этот раз без ввода пароля:
```bash
ssh sshkeytest@localhost
```
Что вы увидите: немедленный вход без запроса пароля! Именно это и делает ключевую аутентификацию такой удобной при частых подключениях.
```bash
whoami
exit
```
[Скриншот беспарольного входа]
Шаг 7. Убедитесь, что произошло «под капотом» — посмотрите файл authorized_keys на стороне «сервера»:
```bash
sudo cat /home/sshkeytest/.ssh/authorized_keys
```
Что вы увидите: ту самую строку вашего публичного ключа, которую ssh-copy-id туда положила.
Шаг 8. Очистите тестовое окружение:
```bash
sudo userdel -r sshkeytest
```
Разбор команд
Команда ssh-keygen
- Назначение:** генерирует пару SSH-ключей (приватный и публичный).
- Синтаксис:**
ssh-keygen [опции] - Основные параметры:**
-t тип— тип алгоритма:ed25519(рекомендуется),rsa,ecdsa.-C "комментарий"— добавить комментарий в конец публичного ключа (обычно email или описание назначения ключа — чтобы потом понять, что это за ключ, если у вас их несколько).-b биты— размер ключа в битах (актуально для RSA:-b 4096; для Ed25519 игнорируется, длина фиксирована).-f путь/к/файлу— явно указать путь и имя файла для ключей (полезно, если хотите создать несколько разных ключей для разных серверов с разными именами).-p— изменить passphrase уже существующего ключа.- Реальные примеры использования:**
ssh-keygen -t ed25519 -C "work laptop 2024"— создать ключ с понятным описанием.ssh-keygen -t rsa -b 4096 -f ~/.ssh/id_rsa_myserver— создать RSA-ключ 4096 бит с нестандартным именем файла.- Типичные ошибки:** перезапись существующего ключа без намерения (
ssh-keygenпредупреждает и спрашивает подтверждение — важно не нажать Yes случайно, иначе старый ключ будет уничтожен и вы потеряете доступ ко всем серверам, куда он был добавлен).
Команда ssh-copy-id
- Назначение:** безопасно копирует публичный ключ на удалённый сервер, добавляя его в файл
~/.ssh/authorized_keysнужного пользователя. - Синтаксис:**
ssh-copy-id [-i путь/к/публичному/ключу] пользователь@хост - Основные параметры:**
-i путь/к/.pub— явно указать, какой публичный ключ копировать (если у вас несколько ключей и нужен не тот, что по умолчанию).-p порт— если SSH слушает на нестандартном порту.- Что делает «под капотом»:** подключается к серверу по паролю, создаёт на сервере папку
~/.ssh/(если её нет) с правами700, и добавляет строку с публичным ключом в файл~/.ssh/authorized_keysс правами600. - Ручной эквивалент** (если
ssh-copy-idнедоступна):cat ~/.ssh/id_ed25519.pub | ssh user@host 'mkdir -p ~/.ssh && cat >> ~/.ssh/authorized_keys && chmod 600 ~/.ssh/authorized_keys'. - Типичные ошибки: запустить
ssh-copy-idс путём к приватному** ключу (без.pub) — команда должна получить именно публичный ключ (.pub).
Возможные ошибки
- Ошибка:** ключевая аутентификация настроена, но SSH всё равно просит пароль.
Почему возникает: неправильные права доступа на папку ~/.ssh или файл authorized_keys на сервере (SSH намеренно игнорирует ключи с неправильными правами — это мера безопасности).
Как определить: запустить ssh -v user@host — в подробном выводе будет видно, что SSH пробует ключ, но сервер его отклоняет; проверить права на сервере: ls -la ~/.ssh/.
Как исправить: установить правильные права:
```bash
chmod 700 ~/.ssh
chmod 600 ~/.ssh/authorized_keys
```
Как избежать: использовать ssh-copy-id (она устанавливает правильные права автоматически) вместо ручного копирования ключа.
- Ошибка:** случайная перезапись существующего ключа командой
ssh-keygen.
Почему возникает: невнимательность при ответе на вопрос подтверждения перезаписи.
Как определить: после этой ошибки вы больше не можете войти на серверы, где был зарегистрирован старый ключ — только если у вас есть доступ по паролю или другой ключ.
Как исправить: если доступ по паролю сохранён — войти по паролю и добавить новый публичный ключ в authorized_keys; если доступ полностью утерян — потребуется «аварийный» доступ к серверу через консоль провайдера (это ситуация, которую важно предотвращать превентивно).
Как избежать: хранить резервные копии пары ключей в безопасном месте (например, зашифрованном хранилище паролей); никогда не генерировать новый ключ, не убедившись, что старый больше не нужен или уже сохранён.
Практические задания
- Создайте второй SSH-ключ, но уже RSA типа с длиной 4096 бит и нестандартным именем файла (
-f ~/.ssh/id_rsa_test). Сравните размер файлов приватных ключей Ed25519 и RSA командойls -la ~/.ssh/. - Вручную (без
ssh-copy-id) добавьте свой публичный ключ в файл~/.ssh/authorized_keysдля своего же пользователя (создайте файл, если он не существует), соблюдая правильные права доступа — и проверьте, что можете войтиssh localhostбез пароля. - Изучите содержимое приватного ключа
~/.ssh/id_ed25519— посмотрите его структуру (cat ~/.ssh/id_ed25519), убедитесь, что начинается с-----BEGIN OPENSSH PRIVATE KEY-----. Объясните в конспекте, почему этот файл нельзя передавать кому-либо ни при каких обстоятельствах.
Проверка знаний
Вопрос 1. Почему аутентификация по SSH-ключам считается безопаснее аутентификации по паролю?
Ответ: Потому что приватный ключ практически невозможно «угадать» перебором (его математическая сложность многократно превышает любой пароль), он никогда не передаётся по сети (только результат криптографической операции), и даже если злоумышленник перехватит весь трафик SSH-сессии — он не получит ничего полезного для воспроизведения аутентификации.
Вопрос 2. Зачем нужна passphrase для приватного ключа, если ключевая аутентификация и так безопаснее парольной?
Ответ: Passphrase шифрует сам файл приватного ключа на диске. Без неё, если злоумышленник физически получит доступ к вашему компьютеру и скопирует файл приватного ключа — он сможет использовать его для входа на все ваши серверы. С passphrase файл ключа без знания фразы бесполезен. Это дополнительный уровень защиты на случай компрометации вашего локального устройства.
Итоги урока
Вы изучили: принцип асимметричной криптографии применительно к SSH, типы ключей (Ed25519, RSA), назначение passphrase, структуру папки ~/.ssh/, файл authorized_keys.
Вы умеете: генерировать SSH-ключи командой ssh-keygen, копировать публичный ключ на сервер через ssh-copy-id, входить на сервер без пароля.
В следующем уроке потребуется: наличие рабочей пары SSH-ключей — в следующем уроке мы настроим удобный файл конфигурации, чтобы не вводить длинные команды подключения каждый раз.
Урок 13.4. Файл конфигурации `~/.ssh/config`
Научиться использовать файл ~/.ssh/config для создания коротких псевдонимов серверов, хранения параметров подключения и значительного упрощения повседневной работы с SSH.
Теория
Представьте, что вы администрируете несколько серверов. Каждый раз набирать что-то вроде:
```bash
ssh -p 2222 -i ~/.ssh/id_rsa_production admin@203.0.113.42
```
— утомительно и легко ошибиться. Именно для решения этой проблемы существует файл ~/.ssh/config.
~/.ssh/config — текстовый файл конфигурации SSH-клиента, находящийся в папке ~/.ssh/ в домашней папке текущего пользователя. В нём можно задать параметры подключения для конкретных серверов (или групп серверов) и назначить им короткие псевдонимы.
Базовая структура файла:
```
Host псевдоним
HostName адрес_или_имя_сервера
User имя_пользователя
Port порт
IdentityFile путь/к/приватному/ключу
```
После этого вместо длинной команды вы просто пишете:
```bash
ssh псевдоним
```
SSH-клиент сам подставит все нужные параметры из конфига.
Ключевые директивы файла конфигурации:
Host— псевдоним (или шаблон, см. ниже). Это то, что вы будете набирать после командыssh.HostName— реальный адрес или доменное имя сервера.User— имя пользователя для входа на этот сервер.Port— порт (если нестандартный; по умолчанию 22).IdentityFile— путь к приватному ключу для этого сервера.ServerAliveInterval— как часто (в секундах) SSH отправляет «пинг» серверу, чтобы соединение не разрывалось при долгом бездействии (очень полезная настройка).ServerAliveCountMax— сколько таких «пингов» подряд можно пропустить, прежде чем SSH решит, что соединение разорвано.
*Секция Host — настройки для всех подключений.* Если использовать Host (звёздочка — это шаблон, означающий «любой хост»), то настройки в этой секции применяются ко всем SSH-подключениям. Это удобно для глобальных настроек, например ServerAliveInterval.
Важно: порядок секций имеет значение. SSH-клиент читает конфиг сверху вниз и использует первое найденное значение для каждого параметра. Более специфичные правила (для конкретного хоста) должны стоять раньше более общих (например, Host *).
Права доступа к файлу конфигурации. Файл ~/.ssh/config должен иметь права 600 (только владелец может читать и писать) — в противном случае SSH откажется его использовать с ошибкой Bad owner or permissions on ~/.ssh/config.
Практика
Шаг 1. Убедитесь, что папка ~/.ssh/ существует (она должна была создаться в предыдущем уроке при генерации ключей):
```bash
ls -la ~/.ssh/
```
Шаг 2. Создайте файл конфигурации (или откройте существующий, если он есть) с помощью редактора nano (мы подробно изучали его в Блоке 7):
```bash
nano ~/.ssh/config
```
Шаг 3. Введите следующее содержимое (адаптируйте под свою систему):
```
Host local
HostName localhost
User ваш_пользователь
Port 22
IdentityFile ~/.ssh/id_ed25519
Host *
ServerAliveInterval 60
ServerAliveCountMax 3
```
Замените ваш_пользователь на ваше реальное имя пользователя в системе (результат команды whoami).
Сохраните файл: Ctrl+O, Enter, Ctrl+X.
Шаг 4. Установите правильные права доступа на файл конфигурации:
```bash
chmod 600 ~/.ssh/config
```
Проверьте:
```bash
ls -la ~/.ssh/config
```
Что вы увидите: -rw------- в начале строки — права 600.
[Скриншот терминала]
Шаг 5. Теперь подключитесь к localhost, используя только псевдоним из конфига:
```bash
ssh local
```
Что произойдёт: SSH прочитает конфиг, найдёт секцию Host local, подставит все параметры и подключится к localhost с нужным пользователем и ключом — всё автоматически.
```bash
whoami
hostname
exit
```
[Скриншот успешного подключения по псевдониму]
Шаг 6. Добавьте ещё одну секцию в конфиг — на этот раз с нестандартным портом (сымитируем ситуацию, когда SSH на сервере перенесён на порт 2222):
```bash
nano ~/.ssh/config
```
Добавьте перед секцией Host *:
```
Host localtest2222
HostName localhost
User ваш_пользователь
Port 2222
IdentityFile ~/.ssh/id_ed25519
```
Сохраните.
Шаг 7. Просмотрите итоговый файл конфигурации:
```bash
cat ~/.ssh/config
```
[Скриншот файла конфигурации]
Шаг 8. Попробуйте использовать функцию автодополнения Tab с псевдонимами из конфига — в современных системах bash дополняет имена хостов из ~/.ssh/config. Наберите ssh lo и нажмите Tab.
Разбор команд
Файл ~/.ssh/config — директивы
Это не команда, а конфигурационный файл. Рассмотрим основные директивы подробнее:
Host* — обязательная директива, начинает новую секцию. Всё, что ниже до следующей директивыHost, относится к этой секции. Поддерживает шаблоны:(любые символы),?(любой один символ). Пример:Host prod-*— применить настройки ко всем хостам, псевдоним которых начинается сprod-.HostName** — реальный адрес сервера. Может быть IP или доменным именем.User** — имя пользователя. Если не указано, используется имя локального пользователя.Port** — порт. Если не указан, используется 22.IdentityFile** — путь к файлу приватного ключа. Можно указать несколько строкIdentityFile— SSH попробует каждый по очереди.ServerAliveInterval N** — каждые N секунд SSH отправляет серверу пустой пакет, чтобы не дать соединению «упасть» из-за таймаута NAT или firewall. Рекомендуемое значение — 60 (раз в минуту).ServerAliveCountMax N** — сколько подряд неотвеченных пингов допустимо перед разрывом соединения. По умолчанию 3.ForwardAgent yes/no** — проброс SSH-агента (позволяет использовать ключи вашего локального компьютера на промежуточных серверах); нужно использовать аккуратно, только с доверенными серверами.StrictHostKeyChecking yes/no/ask** — поведение при проверке fingerprint. Значениеask(по умолчанию) — спрашивать при первом подключении.yes— никогда не подключаться к незнакомому серверу.no— никогда не проверять (небезопасно, использовать только для автоматизации в изолированных средах).
Приоритет настроек:
- Опции командной строки (высший приоритет).
- Файл
~/.ssh/config(пользовательский). - Файл
/etc/ssh/ssh_config(системный, для всех пользователей).
Возможные ошибки
- Ошибка:**
Bad owner or permissions on /home/user/.ssh/config— SSH отказывается использовать конфиг.
Почему возникает: права на файл ~/.ssh/config не равны 600 (например, 644 — читать могут другие пользователи, что SSH считает небезопасным).
Как определить: при попытке подключиться SSH выводит это сообщение.
Как исправить: chmod 600 ~/.ssh/config.
Как избежать: после создания файла конфигурации сразу выполнять chmod 600 ~/.ssh/config.
- Ошибка:** изменения в
~/.ssh/configне применяются.
Почему возникает: чаще всего — опечатка или неправильный отступ в файле (директивы внутри секции Host должны иметь отступ — пробел или Tab в начале строки; без отступа SSH воспринимает строку как начало новой «глобальной» директивы или нераспознанную строку).
Как определить: проверить файл внимательно, сравнить с примером выше. Можно запустить ssh -v псевдоним — в подробном выводе будет видно, какие параметры были применены из конфига.
Как исправить: исправить синтаксис файла (убедиться в наличии отступов у всех директив внутри секций Host).
- Ошибка:** псевдоним из конфига не работает через автодополнение Tab.
Почему возникает: некоторые версии bash или конфигурации системы не включают автодополнение для SSH-хостов по умолчанию.
Как исправить: это несущественная проблема, которую можно решить установкой дополнительных пакетов для автодополнения (bash-completion). Псевдоним при этом всё равно работает при полном наборе.
Практические задания
- Добавьте в файл
~/.ssh/configсекциюHost *с директивамиServerAliveInterval 60иServerAliveCountMax 3, если вы ещё не сделали этого в практике урока. Объясните в конспекте, что именно эти настройки делают. - Создайте в конфиге псевдоним для подключения к localhost под другим именем пользователя (сначала создайте тестового пользователя, добавьте свой публичный ключ в его
authorized_keys, опишите подключение в конфиге, проверьте что псевдоним работает, затем удалите тестового пользователя). - Изучите системный файл
/etc/ssh/ssh_config(это конфигурация клиента для всей системы, в отличие от пользовательского~/.ssh/config):cat /etc/ssh/ssh_config— запишите в конспект три директивы, которые там присутствуют, и объясните, что они означают.
Проверка знаний
Вопрос 1. Почему SSH отказывается использовать файл ~/.ssh/config с правами 644, но принимает тот же файл с правами 600?
Ответ: Права 644 означают, что файл могут читать другие пользователи системы. Файл конфигурации SSH может содержать пути к приватным ключам и другую чувствительную информацию — если другие пользователи смогут его прочитать, это нарушит безопасность. Права 600 гарантируют, что файл доступен только владельцу, что SSH считает минимально приемлемым уровнем безопасности.
Вопрос 2. Если в файле ~/.ssh/config две секции — Host myserver с Port 2222 и Host * с Port 22 — какой порт будет использован при подключении командой ssh myserver?
Ответ: Порт 2222, из секции Host myserver. SSH читает конфиг сверху вниз и использует первое найденное значение для каждого параметра. Секция Host myserver стоит раньше Host *, поэтому её значение Port 2222 будет найдено первым и применено.
Итоги урока
Вы изучили: структуру файла ~/.ssh/config, основные директивы (Host, HostName, User, Port, IdentityFile, ServerAliveInterval), порядок приоритета настроек.
Вы умеете: создавать псевдонимы для серверов в конфиге SSH, подключаться одним коротким словом вместо длинной команды, настраивать глобальные параметры для всех подключений.
В следующем уроке потребуется: всё, что вы знаете об SSH — теперь мы начнём использовать его не просто для входа в терминал, но и для передачи файлов.
Урок 13.5. Копирование файлов: `scp`
Освоить команду scp (Secure Copy) — простейший способ скопировать файл с одной машины на другую через SSH-соединение.
Теория
Войти на сервер через SSH — это хорошо, но часто нужно не только работать в терминале, но и перемещать файлы между машинами: загрузить конфигурационный файл на сервер, скачать с сервера лог-файл для анализа, скопировать резервную копию с одного сервера на другой.
scp (Secure Copy Protocol, «протокол защищённого копирования») — это команда, которая копирует файлы между локальным и удалённым компьютером (или между двумя удалёнными компьютерами) через уже знакомый нам зашифрованный SSH-протокол. Это, по сути, команда cp (которую мы изучали в уроке 5.5), расширенная для работы через сеть.
Синтаксис scp для основных случаев:
```
scp локальный_файл пользователь@хост:/путь/на/сервере/
scp пользователь@хост:/путь/на/сервере/файл /локальный/путь/
scp пользователь1@хост1:/путь/к/файлу пользователь2@хост2:/путь/назначения/
```
Запись пользователь@хост:/путь — это «адрес» файла на удалённой машине, аналогичный URL. Двоеточие : разделяет адрес сервера и путь на нём.
Важные особенности scp:
- Использует то же SSH-соединение (те же ключи, те же настройки из
~/.ssh/config). - Передаёт данные в зашифрованном виде — всё безопасно.
- Работает с паролями и с SSH-ключами — точно так же, как
ssh. - По умолчанию копирует только файлы. Для копирования папок нужен параметр
-r(рекурсивно) — как в знакомой нам командеcp -rиз урока 5.5. - Не может возобновить прерванную передачу (в отличие от
rsync, который мы изучим в уроке 13.7).
Когда использовать scp vs. другие способы:
scp— когда нужно быстро скопировать один-два файла, не думая о дополнительных настройках. Просто, какcp, только через сеть.sftp(урок 13.6) — когда нужна интерактивная работа с файлами на удалённой машине (просмотр папок, загрузка нескольких файлов).rsync(урок 13.7) — когда нужна эффективная синхронизация (только изменившиеся файлы), возобновление после обрыва, резервное копирование.
Заметка о будущем scp. В последних версиях OpenSSH (начиная с версии 9.0) scp по умолчанию использует протокол SFTP «под капотом», а не оригинальный SCP-протокол. Это техническая деталь, которая не меняет синтаксис и поведение команды для пользователя, но улучшает безопасность и совместимость.
Практика
Для практики создадим тестовые файлы и попрактикуемся в их копировании через localhost.
Шаг 1. Создайте несколько тестовых файлов для практики:
```bash
mkdir -p ~/scp_test/source
echo "Содержимое тестового файла 1" > ~/scp_test/source/file1.txt
echo "Содержимое тестового файла 2" > ~/scp_test/source/file2.txt
mkdir ~/scp_test/source/subdir
echo "Файл в подпапке" > ~/scp_test/source/subdir/file3.txt
ls -R ~/scp_test/source/
```
Шаг 2. Скопируйте один файл с «локальной» машины на «удалённую» (в нашем случае оба конца — localhost, но принцип тот же):
```bash
scp ~/scp_test/source/file1.txt ваш_пользователь@localhost:/tmp/
```
Что произойдёт: scp установит SSH-соединение (используя ключ из ~/.ssh/config или запросив пароль) и скопирует файл. Вы увидите прогресс: имя файла, прогресс-бар, скорость и время.
```
file1.txt 100% 32 0.5KB/s 00:00
```
[Скриншот терминала с выводом scp]
Шаг 3. Убедитесь, что файл появился на «сервере»:
```bash
ls -la /tmp/file1.txt
cat /tmp/file1.txt
```
Шаг 4. Скопируйте файл с «удалённой» машины на «локальную» (обратное направление) — скачайте файл с сервера:
```bash
mkdir ~/scp_test/destination
scp ваш_пользователь@localhost:/tmp/file1.txt ~/scp_test/destination/downloaded_file1.txt
```
Что произойдёт: файл /tmp/file1.txt с «сервера» скопируется в ~/scp_test/destination/downloaded_file1.txt на локальной машине с новым именем.
```bash
cat ~/scp_test/destination/downloaded_file1.txt
```
[Скриншот результата]
Шаг 5. Скопируйте папку целиком с помощью параметра -r:
```bash
scp -r ~/scp_test/source/ ваш_пользователь@localhost:/tmp/scp_source_copy/
```
Что произойдёт: скопируется вся папка source со всем содержимым, включая подпапки.
```bash
ls -R /tmp/scp_source_copy/
```
Шаг 6. Скопируйте сразу несколько файлов за один вызов:
```bash
scp ~/scp_test/source/file1.txt ~/scp_test/source/file2.txt ваш_пользователь@localhost:/tmp/
```
Шаг 7. Используйте псевдоним из ~/.ssh/config (если вы настроили его в предыдущем уроке):
```bash
scp ~/scp_test/source/file2.txt local:/tmp/
```
Что вы видите: scp поддерживает псевдонимы из ~/.ssh/config — так же как ssh.
Шаг 8. Очистите тестовые данные:
```bash
rm -r ~/scp_test
rm /tmp/file1.txt /tmp/file2.txt
rm -r /tmp/scp_source_copy/
```
Разбор команд
Команда scp
- Назначение:** копировать файлы между машинами по зашифрованному SSH-соединению.
- Синтаксис:**
scp [опции] источник назначение - Источник или назначение на удалённой машине:
[пользователь@]хост:[/путь] - Источник или назначение на локальной машине:
/обычный/путьили~/относительный/путь - Основные параметры:**
-r— рекурсивное копирование (для папок со всем содержимым).-P порт— нестандартный порт (внимание: заглавная-Pв отличие от строчной-pу командыssh; это историческая несовместимость).-i файл_ключа— указать конкретный приватный ключ.-v— подробный режим для диагностики.-C— включить сжатие данных при передаче (может ускорить передачу текстовых файлов на медленных каналах).-l ограничение— ограничить скорость передачи в Кбит/с (полезно, чтобы не перегружать канал при передаче больших файлов на боевом сервере).- Реальные примеры использования:**
scp backup.tar.gz admin@server.example.com:/var/backups/— загрузить резервную копию на сервер.scp -r admin@server.example.com:/var/log/nginx/ ~/logs/— скачать папку логов Nginx с сервера для анализа.scp -P 2222 config.txt user@server.com:/etc/myapp/— копирование на нестандартный порт.- Типичные ошибки:**
- Перепутать порядок «источник» и «назначение» — файл скопируется не туда, куда нужно.
- Забыть
-rпри копировании папки —scpвыдаст ошибкуnot a regular file. - Использовать строчную
-pвместо заглавной-Pдля указания порта — строчная-pвscpозначает сохранение временных меток файлов, а не порт.
Возможные ошибки
- Ошибка:**
scp: /путь/на/сервере: Permission denied— нет прав записи по указанному пути на сервере.
Почему возникает: пользователь, под которым установлено SSH-соединение, не имеет прав записи в указанную директорию.
Как определить: сообщение об ошибке явно содержит Permission denied.
Как исправить: выбрать другую директорию (например, /tmp/ или домашнюю папку пользователя), или войти по SSH на сервер и создать директорию с нужными правами.
Как избежать: проверять права доступа на директорию назначения перед копированием.
- Ошибка:**
No such file or directoryдля пути на сервере.
Почему возникает: неправильный путь, или промежуточные директории не существуют.
Как определить: сообщение явно говорит об отсутствии пути.
Как исправить: войти по SSH, создать необходимые директории командой mkdir -p.
Как избежать: убедиться в правильности пути, предварительно просмотрев его через SSH.
Практические задания
- Напишите команду
scp, которая скопирует весь каталог~/.ssh/с одного хоста на другой (подсказка: понадобится параметр для рекурсии), но не выполняйте её — просто запишите и объясните в конспекте, что именно она сделает и почему в реальной жизни копировать приватные ключи по сети было бы опасной практикой. - Ограничьте скорость передачи при копировании файла до 100 Кбит/с (
-l 100) и сравните время с копированием без ограничения — когда эта опция была бы полезна на практике? - Используя
scp, скопируйте системный файл/etc/hostsс «сервера» (localhost) в свою домашнюю папку под именемhosts_backup.txt. Изучите его содержимое и объясните в конспекте, что означают строки в этом файле (мы говорили о нём в уроке 12.4).
Проверка знаний
Вопрос 1. Чем scp принципиально отличается от обычной команды cp, изученной в уроке 5.5?
Ответ: cp копирует файлы в пределах одной машины. scp копирует файлы между разными машинами по сети, используя зашифрованное SSH-соединение. В остальном логика использования схожа: указываешь источник и назначение, для рекурсивного копирования папок добавляешь -r.
Вопрос 2. Почему при указании нестандартного порта в scp используется заглавная -P, а не строчная -p как в команде ssh?
Ответ: Это историческая несовместимость: в scp строчная -p уже была «занята» другим значением (preserve — сохранение временных меток и прав файлов). Когда добавляли опцию порта, пришлось использовать заглавную букву. Это частая ловушка при работе с инструментами SSH, которую важно запомнить.
Итоги урока
Вы изучили: синтаксис scp для копирования файлов в обоих направлениях (локальная→удалённая и удалённая→локальная), параметры -r, -P, -C, -l, особенность заглавной -P для порта.
Вы умеете: копировать файлы и папки через сеть одной командой, ограничивать скорость передачи, использовать псевдонимы из ~/.ssh/config.
В следующем уроке потребуется: понимание того, что SSH используется для передачи файлов — в следующем уроке рассмотрим более интерактивный способ работы с файлами на удалённой машине через SFTP.
Урок 13.6. Интерактивная работа с файлами: `sftp`
Освоить sftp — интерактивный файловый клиент для работы с удалённой машиной в режиме диалога, аналог FTP, но полностью безопасный.
Теория
sftp (SSH File Transfer Protocol, «протокол передачи файлов через SSH») — это интерактивный инструмент для работы с файлами на удалённой машине. В отличие от scp, который работает как одна команда (указал источник, назначение, нажал Enter — файл скопирован), sftp открывает интерактивный сеанс, в котором вы можете перемещаться по директориям, просматривать содержимое папок, скачивать и загружать несколько файлов по очереди — примерно так же, как файловый менеджер, но в терминале.
Аналогия с обычным FTP. Если вы когда-либо пользовались FTP-клиентами (FileZilla, WinSCP) — sftp работает по той же логике, но полностью зашифрован, используя SSH «под капотом». Буква «s» в начале означает именно это: Secure (защищённый) FTP. Важно не путать: SFTP — это совсем другой протокол, чем FTPS (FTP с SSL-шифрованием); они похожи по назначению, но технически устроены по-разному.
Команды внутри SFTP-сессии делятся на две группы:
- Команды для удалённой машины** — работают на сервере:
ls,cd,pwd,mkdir,rm,rename(переименовать),rmdir. - Команды для локальной машины** — те же команды, но с префиксом
l(local):lls(просмотреть содержимое текущей локальной папки),lcd(сменить локальную директорию),lpwd(показать текущую локальную папку). - Команды передачи файлов:**
get удалённый_файл [локальное_имя]— скачать файл с сервера.put локальный_файл [удалённое_имя]— загрузить файл на сервер.mget шаблон— скачать несколько файлов (по шаблону, напримерmget *.log).mput шаблон— загрузить несколько файлов.
Чтобы выйти из SFTP-сессии: exit или quit или Ctrl+D.
Когда sftp удобнее scp:
- Когда заранее не знаете точный путь к нужному файлу и хотите «поисследовать» файловую систему сервера перед скачиванием.
- Когда нужно загрузить или скачать несколько разных файлов из разных мест за один сеанс.
- Когда вы привыкли к интерактивному файловому менеджеру.
Когда scp или rsync лучше sftp:
- Когда путь известен заранее — одна команда
scpбыстрее и проще. - Когда нужна синхронизация (только изменившиеся файлы) —
rsync. - Когда нужно автоматизировать передачу файлов в скриптах —
scpилиrsyncудобнее, чем интерактивныйsftp.
Практика
Шаг 1. Создайте тестовые файлы для практики:
```bash
mkdir -p ~/sftp_test
echo "Файл для загрузки на сервер" > ~/sftp_test/upload_me.txt
echo "Ещё один файл" > ~/sftp_test/another.txt
```
Шаг 2. Запустите SFTP-сессию к localhost:
```bash
sftp ваш_пользователь@localhost
```
Что вы увидите: после успешного подключения появится приглашение sftp> вместо привычного $. Это означает, что вы внутри SFTP-сессии.
[Скриншот приглашения sftp>]
Шаг 3. Изучите состояние и навигацию по удалённой машине:
```
sftp> pwd
sftp> ls
sftp> ls -la
sftp> cd /tmp
sftp> pwd
sftp> ls
```
Что вы увидите: команды работают так же, как в обычном терминале, но выполняются на удалённой стороне. pwd покажет текущую директорию на сервере.
[Скриншот навигации]
Шаг 4. Проверьте текущую директорию на локальной машине (используем l-префикс):
```
sftp> lpwd
sftp> lls
sftp> lcd ~/sftp_test
sftp> lpwd
sftp> lls
```
Что вы увидите: lpwd и lls работают с вашей локальной машиной — вы видите локальные пути и файлы, не выходя из SFTP-сессии.
Шаг 5. Загрузите файл на удалённую машину (команда put):
```
sftp> cd /tmp
sftp> put upload_me.txt
sftp> ls
```
Что произойдёт: файл upload_me.txt из текущей локальной директории (мы перешли туда через lcd на шаге 4) загрузится в текущую удалённую директорию (/tmp).
[Скриншот загрузки файла]
Шаг 6. Скачайте файл с удалённой машины (команда get):
```
sftp> get /etc/os-release
sftp> lls
```
Что произойдёт: файл /etc/os-release с «сервера» скачается в текущую локальную директорию (~/sftp_test). Команда lls покажет, что он там появился.
Шаг 7. Загрузите несколько файлов сразу с помощью mput:
```
sftp> mput ~/sftp_test/*.txt
```
Что произойдёт: все файлы .txt из указанной локальной папки загрузятся на сервер в текущую удалённую директорию.
Шаг 8. Создайте папку на удалённой машине прямо из SFTP-сессии:
```
sftp> mkdir /tmp/sftp_uploads
sftp> ls /tmp/
```
Шаг 9. Выйдите из SFTP-сессии:
```
sftp> exit
```
Что вы увидите: возврат в обычную командную строку.
[Скриншот выхода из sftp]
Шаг 10. Очистите тестовые данные:
```bash
rm -r ~/sftp_test
rm /tmp/upload_me.txt /tmp/another.txt
rmdir /tmp/sftp_uploads
```
Разбор команд
Команда sftp
- Назначение:** запустить интерактивный сеанс передачи файлов по SSH.
- Синтаксис:**
sftp [опции] [пользователь@]хост - Основные параметры запуска:**
-P порт— нестандартный порт (заглавная P, как вscp).-i файл_ключа— конкретный приватный ключ.-b файл_скрипта— запустить SFTP в пакетном (не интерактивном) режиме, выполняя команды из файла-скрипта.
Команды внутри SFTP-сессии (полный список основных):
| Команда | Действие |
|---|---|
| pwd | Текущая директория на сервере |
| lpwd | Текущая директория на локальной машине |
| ls [путь] | Список файлов на сервере |
| lls [путь] | Список файлов локально |
| cd путь | Перейти в директорию на сервере |
| lcd путь | Перейти в директорию локально |
| mkdir путь | Создать директорию на сервере |
| rmdir путь | Удалить директорию на сервере |
| rm файл | Удалить файл на сервере |
| rename старое новое | Переименовать файл на сервере |
| get удал. [лок.] | Скачать файл с сервера |
| put лок. [удал.] | Загрузить файл на сервер |
| mget шаблон | Скачать несколько файлов |
| mput шаблон | Загрузить несколько файлов |
| exit / quit | Выйти из сессии |
| help | Показать справку по командам |
- Типичные ошибки: забыть префикс
lи написатьcd /tmpвместоlcd /tmpкогда хотите сменить локальную** директорию — в результате смените директорию на сервере, а не локально, и загрузите/скачаете файлы не туда.
Возможные ошибки
- Ошибка:**
get: /etc/shadow: Permission denied.
Почему возникает: попытка скачать файл, на чтение которого у вашего пользователя нет прав (вспомните урок 8.6 про права доступа и особый статус файла /etc/shadow).
Как определить: явное сообщение Permission denied.
Как исправить: скачать файл можно только если у вас достаточно прав (root или специальные права). Для большинства системных файлов это невозможно без sudo, а SFTP не поддерживает sudo внутри сессии. Если доступ нужен — войти по SSH и использовать sudo cp файл /tmp/, затем скачать через SFTP из /tmp/.
- Ошибка:*
mget.log — шаблон не раскрывается, скачивается буквально файл с именем*.log.
Почему возникает: в SFTP шаблоны раскрываются иначе, чем в bash — в некоторых ситуациях может потребоваться правильно экранировать или настроить поведение.
Как исправить: попробовать mget "*.log", или вручную указать нужные файлы через несколько команд get.
Практические задания
- Запустите SFTP-сессию к localhost и скачайте файл
/etc/hostnameна локальную машину. Затем прямо в SFTP-сессии создайте директорию/tmp/my_sftp_dirи загрузите в неё любой локальный файл из вашей домашней папки. Выйдите из сессии и проверьте результат. - Используя SFTP-команду
helpвнутри сессии, изучите полный список доступных команд. Найдите три команды, которые мы не рассматривали в уроке, и объясните в конспекте их назначение. - Объясните в конспекте сценарий, когда SFTP удобнее, чем
scp: например, вам нужно «обследовать» незнакомый сервер, найти нужные конфигурационные файлы и скачать несколько из них — опишите последовательность действий.
Проверка знаний
Вопрос 1. Как в SFTP-сессии узнать, в какой директории вы сейчас находитесь на локальной машине, не выходя из сессии?
Ответ: Командой lpwd (local pwd, «локальный pwd»). В SFTP-сессии команды с префиксом l выполняются на локальной машине: lpwd — текущая локальная директория, lls — список файлов в ней, lcd путь — сменить локальную директорию.
Вопрос 2. В чём принципиальное отличие sftp от scp с точки зрения использования?
Ответ: scp — это одна не-интерактивная команда: вы указываете источник и назначение, она копирует и завершается. sftp — это интерактивный сеанс, в котором вы можете «ходить» по директориям сервера командами cd/ls, просматривать файлы, и выполнять несколько операций загрузки/скачивания последовательно, не завершая сеанс между ними.
Итоги урока
Вы изучили: что такое SFTP, чем отличается от SCP и FTP, все основные команды внутри SFTP-сессии (включая l-префиксные команды для локальной машины), команды get/put/mget/mput.
Вы умеете: запускать SFTP-сессию, навигировать по удалённой и локальной файловой системе одновременно, скачивать и загружать файлы в интерактивном режиме.
В следующем уроке потребуется: понимание задачи «синхронизации» файлов между машинами — следующий инструмент, rsync, решает её намного эффективнее.
Урок 13.7. Эффективная синхронизация файлов: `rsync` через сеть
Освоить rsync — наиболее мощный инструмент синхронизации файлов, умеющий передавать только изменившиеся части файлов, возобновлять прерванные передачи и работать как по SSH, так и локально.
Теория
Представьте: у вас на сервере есть папка с проектом размером 10 ГБ. Вы изменили два небольших файла и хотите обновить локальную копию. scp -r скопирует все 10 ГБ заново. rsync скопирует только изменившиеся файлы, а если они большие — даже только изменившиеся блоки внутри файлов. Это может сократить время передачи с часов до секунд.
rsync (Remote Sync, «удалённая синхронизация») — утилита для эффективной синхронизации файлов и директорий. Главное, что отличает её от scp:
- Дельта-передача (delta transfer algorithm).
rsyncсравнивает файлы на источнике и на приёмнике и передаёт только изменения — отличающиеся блоки данных. Если файл почти не изменился, передаётся лишь небольшая «дельта» (разница), а не весь файл целиком. - Возобновление прерванных передач. Если соединение оборвалось посредине — при следующем запуске
rsyncпродолжит с того места, где остановился (а не начнёт с нуля). - Гибкие фильтры. Можно легко исключить определённые файлы или папки (
--exclude). - Работа и локально, и через сеть.
rsyncможно использовать и для синхронизации папок на одной машине (без сети), и через SSH (с указанием удалённого хоста). - Сохранение метаданных. С нужными параметрами
rsyncсохраняет права доступа, временные метки, символические ссылки и другие атрибуты файлов.
Синтаксис rsync через SSH:
```bash
rsync [опции] /локальная/папка/ пользователь@хост:/удалённая/папка/
rsync [опции] пользователь@хост:/удалённая/папка/ /локальная/папка/
```
Критично важный нюанс: слэш в конце пути!
Это одна из самых распространённых причин путаницы при работе с rsync:
rsync /source/dir/(со слэшем на конце) — синхронизировать содержимое папкиdir.rsync /source/dir(без слэша) — синхронизировать саму папкуdir(папка будет создана внутри назначения).
Пример:
```bash
rsync /source/dir/ user@host:/dest/ # → /dest/file1, /dest/file2 ...
rsync /source/dir user@host:/dest/ # → /dest/dir/file1, /dest/dir/file2 ...
```
Запомните это правило — оно сэкономит вам много времени и нервов.
Наиболее полезная комбинация параметров для реальной работы:
```bash
rsync -avz --progress источник назначение
```
-a(archive, «архивный режим») — сочетание нескольких опций сразу:-r(рекурсивно),-l(копировать символические ссылки),-p(сохранять права доступа),-t(сохранять временные метки),-g(сохранять группу),-o(сохранять владельца, если есть права),-D(копировать специальные файлы устройств). Обычно именно это и нужно для резервного копирования.-v(verbose) — подробный вывод: показывает, какие файлы передаются.-z(compress) — сжимать данные при передаче. Ускоряет работу на медленных каналах; на быстрых локальных сетях может замедлить из-за накладных расходов на сжатие.--progress— показывать прогресс для каждого файла.
Важный параметр --delete. По умолчанию rsync только добавляет и обновляет файлы в назначении, но не удаляет те, которых уже нет в источнике. Если вы хотите настоящую «зеркальную» синхронизацию (назначение должно стать точной копией источника), добавьте --delete — тогда файлы, удалённые в источнике, будут удалены и в назначении. Используйте этот параметр осторожно.
Проверка без выполнения (-n или --dry-run). Перед реальной синхронизацией (особенно с --delete) крайне рекомендуется сначала сделать «холостой прогон»: добавьте -n или --dry-run — rsync покажет, что собирается сделать, но ничего не изменит реально. Это позволяет проверить правильность команды без риска потерять данные.
Практика
Шаг 1. Убедитесь, что rsync установлен (в Ubuntu обычно предустановлен):
```bash
rsync --version
```
Если не найден: sudo apt install rsync.
Шаг 2. Создайте тестовую структуру директорий:
```bash
mkdir -p ~/rsync_source/{docs,images,configs}
echo "Документ 1" > ~/rsync_source/docs/doc1.txt
echo "Документ 2" > ~/rsync_source/docs/doc2.txt
echo "Конфиг приложения" > ~/rsync_source/configs/app.conf
echo "Данные" > ~/rsync_source/data.bin
ls -R ~/rsync_source/
```
Шаг 3. Выполните «холостой прогон» перед реальной синхронизацией:
```bash
rsync -avzn ~/rsync_source/ ваш_пользователь@localhost:/tmp/rsync_dest/
```
Что вы увидите: список файлов, которые rsync собирается скопировать, но ничего не изменится реально (флаг -n). Проверьте, что список соответствует ожиданиям.
[Скриншот dry-run]
Шаг 4. Выполните реальную синхронизацию:
```bash
rsync -avz --progress ~/rsync_source/ ваш_пользователь@localhost:/tmp/rsync_dest/
```
Что вы увидите: список передаваемых файлов с прогрессом и итоговую статистику (сколько файлов передано, сколько байт, скорость передачи).
[Скриншот реальной синхронизации с прогрессом]
Шаг 5. Проверьте результат:
```bash
ls -R /tmp/rsync_dest/
```
Шаг 6. Измените несколько файлов в источнике и добавьте новый:
```bash
echo "Обновлённый документ 1" > ~/rsync_source/docs/doc1.txt
echo "Новый документ 3" > ~/rsync_source/docs/doc3.txt
```
Шаг 7. Запустите rsync снова и посмотрите — он передаст только изменившееся:
```bash
rsync -avz --progress ~/rsync_source/ ваш_пользователь@localhost:/tmp/rsync_dest/
```
Что вы увидите: на этот раз будут переданы только docs/doc1.txt (изменён) и docs/doc3.txt (новый). Файлы doc2.txt, app.conf, data.bin не трогаются — они не изменились. Вот в чём сила rsync.
[Скриншот инкрементальной синхронизации]
Шаг 8. Попробуйте исключить определённые файлы при синхронизации:
```bash
rsync -avz --exclude='*.conf' ~/rsync_source/ ваш_пользователь@localhost:/tmp/rsync_dest2/
```
Что произойдёт: все файлы скопируются, кроме configs/app.conf (он соответствует шаблону *.conf).
```bash
ls -R /tmp/rsync_dest2/
```
Шаг 9. Используйте rsync для локальной синхронизации (без сети — просто чтобы увидеть, что это тоже работает):
```bash
rsync -av ~/rsync_source/ ~/rsync_local_backup/
```
Шаг 10. Очистите тестовые данные:
```bash
rm -r ~/rsync_source ~/rsync_local_backup
rm -r /tmp/rsync_dest /tmp/rsync_dest2
```
Разбор команд
Команда rsync
- Назначение:** эффективная синхронизация файлов и директорий (локально или через сеть по SSH).
- Синтаксис:**
rsync [опции] источник назначение - Для работы через SSH:
источникилиназначениев форме[пользователь@]хост:/путь. - Основные параметры:**
-a(archive) — сохранить все атрибуты файлов (права, метки, ссылки и т.д.). Почти всегда нужен.-v(verbose) — подробный вывод.-z(compress) — сжатие при передаче.-n/--dry-run— холостой прогон (показать что будет сделано, не делая ничего).--progress— показывать прогресс для каждого файла.--delete— удалять в назначении файлы, отсутствующие в источнике (зеркальная синхронизация).-e 'ssh -p 2222'— использовать SSH на нестандартном порту.--exclude='шаблон'— исключить файлы по шаблону.--include='шаблон'— явно включить файлы (используется вместе с--exclude).-u(update) — пропускать файлы, которые в назначении новее, чем в источнике.--bwlimit=КБИТ— ограничить скорость передачи.--checksum— сравнивать файлы по контрольной сумме, а не только по размеру и дате (медленнее, но точнее).- Реальные примеры использования:**
rsync -avz --delete ~/website/ admin@server.com:/var/www/html/— развернуть сайт на сервере (зеркальная синхронизация).rsync -avz --progress user@backup-server.com:/data/ /mnt/local_backup/— ежедневный бэкап данных с сервера.rsync -avz -e 'ssh -p 2222' source/ user@server.com:/dest/— синхронизация через нестандартный порт.rsync -avn --delete ~/docs/ server:/docs/— проверить, что удалится с--delete, без реального выполнения.
Итоговое сравнение инструментов передачи файлов:
| Инструмент | Лучше подходит для... |
|---|---|
| scp | Быстро скопировать один-два файла |
| sftp | Интерактивная работа с файлами (просмотр, загрузка/скачивание нескольких файлов) |
| rsync | Синхронизация папок, резервное копирование, повторяемые задачи, большие объёмы |
Возможные ошибки
- Ошибка:** случайное удаление важных файлов из-за
--delete.
Почему возникает: --delete удаляет из назначения файлы, которых нет в источнике — если перепутать источник и назначение местами, можно удалить «нужные» файлы и заменить «ненужными».
Как определить: данные пропали после rsync с --delete.
Как исправить: восстановить из резервной копии (если есть).
Как избежать: всегда использовать -n/--dry-run перед реальным запуском rsync с --delete. Никогда не запускать с --delete без предварительной проверки.
- Ошибка:** rsync передаёт все файлы каждый раз, не используя инкрементальность.
Почему возникает: отсутствует -a (или -t) — без сохранения временных меток rsync не может определить, изменился ли файл, и передаёт всё заново.
Как исправить: добавить флаг -a к команде rsync.
- Ошибка:** путаница со слэшем — файлы оказываются «не там».
Почему возникает: непонимание разницы rsync src/ и rsync src.
Как определить: в назначении появляется лишний уровень вложенности (или наоборот — содержимое «вываливается» туда, куда не ожидалось).
Как исправить: чётко запомнить правило слэша (разобрано в теории). При сомнениях — сначала -n dry-run.
Практические задания
- Создайте локальную папку-«источник» с несколькими файлами и папку-«назначение». Синхронизируйте их с помощью
rsync -av. Затем удалите один файл из источника и запуститеrsync -avn --delete(dry-run), чтобы увидеть, что будет удалено. Потом запустите без-nи убедитесь, что файл действительно удалился из назначения. - Синхронизируйте папку на localhost через SSH с флагами
-avz --progress, добавив исключение для файлов с расширением.log(--exclude='*.log'). Создайте несколько.log-файлов в источнике и убедитесь, что они не передаются. - Объясните в конспекте, почему команда
rsync -av ~/docs/ backup:~/docs/будет работать быстрее при повторном запуске, чемscp -r ~/docs/ backup:~/при тех же условиях.
Проверка знаний
Вопрос 1. Что такое «дельта-передача» в rsync и почему она важна для резервного копирования больших объёмов данных?
Ответ: Дельта-передача — это механизм, при котором rsync передаёт не весь файл, а только изменившиеся блоки. Если в файле размером 1 ГБ изменились только 10 МБ, будет передано лишь 10 МБ. Для резервного копирования больших объёмов это критически важно: вместо ежедневного копирования терабайт данных передаются лишь реально изменившиеся части, что экономит время, трафик и место.
Вопрос 2. Зачем использовать --dry-run перед реальным запуском rsync с --delete?
Ответ: --delete удаляет из назначения файлы, отсутствующие в источнике. Если источник и назначение перепутаны или шаблоны --exclude настроены неверно — можно уничтожить нужные данные. --dry-run позволяет увидеть, что именно rsync собирается удалить и скопировать, без реального выполнения. Это «страховка» перед потенциально разрушительной операцией.
Итоги урока
Вы изучили: принцип дельта-передачи, параметры -avz, --delete, --dry-run, --exclude, правило слэша, сравнение scp/sftp/rsync.
Вы умеете: синхронизировать файлы и папки через SSH с помощью rsync, делать инкрементальные резервные копии, безопасно проверять команды через dry-run.
В следующем уроке (первый урок Блока 14) потребуется: понимание, что SSH — это критически важный сервис с точки зрения безопасности, и его правильная настройка — основа защиты любого Linux-сервера.
Мини-проект блока
Задача: создать практическую систему, которая объединяет всё, что изучено в блоке: SSH-ключи, конфиг, и rsync для автоматического резервного копирования.
Что нужно сделать:
- Настройте SSH-ключи и конфиг (если ещё не сделано): убедитесь, что у вас есть пара ключей Ed25519, и создайте запись в
~/.ssh/configдля подключения к localhost под псевдонимомbackup-host(для учебных целей используем localhost как «сервер бэкапов»).
- Создайте структуру «важных данных» для резервного копирования:
```bash
mkdir -p ~/important/{documents,projects,configs}
echo "Важный документ" > ~/important/documents/report.txt
echo "Код проекта" > ~/important/projects/app.py
cp ~/.ssh/config ~/important/configs/ssh_config.bak
```
- Напишите команду rsync для резервного копирования папки
~/important/на «сервер» в директорию/tmp/backup/с параметрами-avz --progress --delete. Сначала выполните dry-run, затем реальную синхронизацию.
- Проверьте инкрементальность: измените один файл в
~/important/, добавьте один новый файл, удалите один файл. Запустите rsync снова и убедитесь, что он передал только изменения.
- Напишите bash-скрипт
~/backup.sh(мы изучим скрипты подробно в Блоке 15, но здесь попробуем самое простое):
```bash
#!/bin/bash
rsync -avz --delete ~/important/ backup-host:/tmp/backup/
echo "Резервное копирование завершено: $(date)"
```
Сделайте скрипт исполняемым: chmod +x ~/backup.sh.
Запустите и убедитесь, что он работает: ./backup.sh.
- Задокументируйте в конспекте: какие SSH-ключи используются, что означает каждый параметр rsync в скрипте, и почему эта связка (SSH-ключи + rsync) лучше ручного копирования.
Критерий готовности: скрипт ~/backup.sh запускается без ввода пароля (благодаря SSH-ключам) и корректно синхронизирует папку, передавая только изменившиеся файлы при повторном запуске.
Контрольные вопросы
- Объясните, что такое fingerprint SSH-сервера, где он хранится на стороне клиента и зачем SSH проверяет его при каждом подключении.
- В чём разница между приватным и публичным SSH-ключом? Какой из них кладётся на сервер, а какой остаётся у вас?
- Какой параметр команды
scpиспользуется для копирования директорий, и почему вscpпорт указывается через-P, а не-p? - Перечислите три команды с
l-префиксом, доступные внутри SFTP-сессии, и объясните, что они делают. - Что произойдёт при запуске
rsync -av ~/source/ user@host:/dest/если в/dest/уже есть файлы, которых нет в~/source/? - Объясните правило слэша в конце пути для rsync на конкретном примере.
- Какой файл нужно создать и настроить на стороне SSH-сервера, чтобы пользователь мог войти по ключу? Каковы правильные права доступа на этот файл?
Выводы по блоку
В этом блоке вы совершили качественный скачок: перешли от работы с одной машиной к управлению машинами через сеть. Это и есть суть профессии системного администратора — умение работать с серверами, находящимися в любой точке мира, из любого места, где есть интернет-соединение.
Вы разобрались в том, почему SSH вытеснил небезопасный Telnet, как работает криптография «под капотом» этого протокола, и почему SSH-ключи надёжнее паролей. Вы умеете не просто войти на сервер, но и удобно организовать работу через файл ~/.ssh/config, передавать файлы тремя разными инструментами под разные задачи, и синхронизировать данные инкрементально с помощью rsync.
Этот материал будет использоваться во всех следующих блоках: в Блоке 14 (безопасность SSH), в Блоке 15 (скрипты через SSH), в Блоке 16 (Git через SSH), в Блоке 20 (администрирование VPS).
Список изученных тем
- SSH: история, принцип шифрования, архитектура клиент-сервер, порт 22, пакеты
openssh-client/openssh-server. - Команда
ssh: синтаксис, параметры-p,-v,-i, файлknown_hosts, fingerprint. - SSH-ключи: асимметричная криптография, алгоритмы (Ed25519, RSA), passphrase, команды
ssh-keygenиssh-copy-id, файлauthorized_keys. - Файл
~/.ssh/config: директивыHost,HostName,User,Port,IdentityFile,ServerAliveInterval, порядок приоритета. scp: синтаксис, параметры-r,-P(заглавная!),-C,-l, направление копирования.sftp: интерактивная сессия, командыget/put/mget/mput,l-префикс для локальных команд.rsync: дельта-передача, параметры-avz,--delete,--dry-run,--exclude, правило слэша, сравнение сscpиsftp.
Рекомендации перед переходом
Убедитесь, что вы умеете:
- Подключиться по SSH к localhost по ключу (без ввода пароля).
- Объяснить, чем отличается приватный ключ от публичного и где каждый из них должен находиться.
- Скопировать файл на удалённую машину и обратно с помощью
scp. - Запустить
rsyncс параметрами-avz --dry-runи понять вывод.
В Блоке 14 мы будем работать непосредственно с безопасностью сервера, и SSH станет центральной темой — мы научимся отключать аутентификацию по паролю (оставив только ключи), менять порт SSH, настраивать Fail2Ban против перебора паролей. Всё это строится на фундаменте, заложенном в этом блоке.