Прежде чем перейти к статье, хочу вам представить, экономическую онлайн игру Brave Knights, в которой вы можете играть и зарабатывать. Регистируйтесь, играйте и зарабатывайте!
В эпоху цифровых технологий безопасность играет ключевую роль в защите ваших данных и систем. Особенно это актуально для серверов и систем, доступ к которым осуществляется через SSH. Даже если вы используете сложные пароли и надежные методы шифрования, одной аутентификации может быть недостаточно для полноценной защиты вашего сервера от несанкционированного доступа.
Двухфакторная аутентификация (2FA) – это мощный инструмент, который значительно повышает уровень безопасности, требуя подтверждения вашей личности с помощью второго фактора. В этом контексте, двухфакторная аутентификация через Telegram является достаточно эффективным решеним, которое можно легко интегрировать в процесс SSH-подключения.
Зачем это может пригодиться? Во-первых, это значительно усложняет жизнь потенциальным злоумышленникам. Даже если пароль окажется скомпрометирован, доступ к вашему серверу будет возможен только после подтверждения входа через Telegram, что практически исключает риск несанкционированного доступа. Во-вторых, Telegram предоставляет удобный интерфейс и высокий уровень безопасности для отправки уведомлений и запросов на подтверждение, что делает процесс аутентификации простым и доступным.
В этой статье мы шаг за шагом рассмотрим, как настроить двухфакторную авторизацию для SSH с использованием Telegram-бота. Разберем все необходимые шаги – от создания бота до интеграции с вашим сервером, чтобы вы могли обеспечить дополнительный уровень безопасности для вашего окружения.
Ее величество, настройка
Создание бота в Telegram и получение необходимых реквизитов:
Все давно описано, но на всякий подробная инструкция для получения токена и chat id ниже:
Создаем бота через @BotFather. Для чего нужно ввести команду /newbot , далее нужно вести имя и ник бота. В результате нужно получить токен, для доступа к боту.
Далее необходимо запустить созданного бота через команду /start и что-то в него написать, например, "Привет, Хабр!"
Сообщение нужно для того, чтобы впоследствии узнать ваш Chat ID. Сделать это можно при помощи следующей команды (не забываем указать токен вашего бота):
curl -s https://api.telegram.org/bot{BOT_TOKEN}/getUpdates | grep -o '"id":[0-9]*' | head -1 | awk -F: '{print $2}'
Пример того, как это выглядит:
На этом часть настройки Telegram бота заканчивается.
Настройка на машине с Linux
Все шаги выполняются на системе Linux Debian 12. Но адаптировать их под вашу точно не составит труда ;)
Для начала, необходимо установить Python, если вдруг его нет.
sudo apt update && sudo apt install -y python3 python3-pip
И несколько pip пакетов, которые нам пригодятся:
pip3 install python-telegram-bot aiofiles requests --break-system-packages
Создадим сам python-скрипт, которые реализуют логику двухфакторной аутентификации.
Не забудьте изменить TOKEN и CHAT_ID на ваши.
cat > telegram_auth.py <<EOF
import telegram
from telegram import InlineKeyboardButton, InlineKeyboardMarkup
import sys
import os
import asyncio
from datetime import datetime
import requests # Для получения информации о городе и провайдере
import subprocess # Для выполнения системных команд
# Конфигурация
TOKEN = '7449414805:AAGuDLfYOeC1ylwooYkt1xEEbpGxRKOXc8I' # Токен вашего Telegram-бота
CHAT_ID = '9414805' # ID чата в Telegram, куда будут отправляться сообщения
IP_INFO_URL = 'http://ipinfo.io/{}/json' # URL для получения информации о IP-адресе (город, провайдер и т.д.)
# Создаем объект бота с использованием токена
bot = telegram.Bot(token=TOKEN)
# Словарь для хранения запросов на подтверждение
requests = {}
def get_local_ip():
"""
Функция для получения локального IP-адреса машины, на которой выполняется скрипт.
Использует команду 'hostname -I' для получения IP-адресов и возвращает первый из них.
"""
try:
result = subprocess.run(['hostname', '-I'], capture_output=True, text=True)
return result.stdout.strip().split()[0] # Возвращаем первый IP из списка
except Exception:
return 'Неизвестен' # Возвращаем 'Неизвестен' в случае ошибки
def get_hostname():
"""
Функция для получения имени хоста машины, на которой выполняется скрипт.
Использует команду 'hostname' для получения имени хоста.
"""
try:
result = subprocess.run(['hostname'], capture_output=True, text=True)
return result.stdout.strip() # Возвращаем имя хоста
except Exception:
return 'Неизвестен' # Возвращаем 'Неизвестен' в случае ошибки
async def send_telegram_message(username, remote_ip, request_id):
"""
Асинхронная функция для отправки сообщения в Telegram с информацией о попытке входа.
Сообщение включает время входа, IP-адрес, информацию о городе и провайдере,
локальный IP и имя хоста.
"""
# Получаем информацию о IP
ip_info = {}
try:
response = requests.get(IP_INFO_URL.format(remote_ip))
ip_info = response.json() # Преобразуем ответ в формат JSON
except Exception:
ip_info = {} # Если возникла ошибка, оставляем словарь пустым
# Извлекаем информацию из ответа
city = ip_info.get('city', 'Неизвестно')
provider = ip_info.get('org', 'Неизвестно')
login_time = datetime.now().strftime('%Y-%m-%d %H:%M:%S') # Текущее время в нужном формате
local_ip = get_local_ip() # Получаем локальный IP
hostname = get_hostname() # Получаем имя хоста
# Формируем текст сообщения
message = (f"