Хранить пароли в текстовом файле — плохая идея. Даже если файл спрятан в папке, от кражи это не спасёт. Но что делать, если хочется простой инструмент под себя, без облаков и подписок?
Собрать собственный менеджер паролей на Python — задача на вечер. Заодно разберётесь, как работает симметричное шифрование и почему не стоит доверять браузерному сохранению. Итог — рабочий CLI-инструмент, который шифрует данные через Fernet и сам копирует пароль в буфер обмена.
Почему шифрование — не опция, а обязательное условие
Многие «туториалы» по менеджерам паролей пропускают главное: шифрование. Если просто сохранять пароли в .txt, то при утечке файла все аккаунты окажутся в чужих руках. Браузеры тоже не панацея — их хранилища часто ломают.
Fernet — симметричный протокол из библиотеки cryptography. Он одновременно шифрует и аутентифицирует данные: файл невозможно незаметно изменить, расшифровка просто не сработает.
| Что даёт Fernet | Что было бы без него |
|---|---|
| Пароли нечитаемы без ключа | Любой открывает файл и читает всё |
| Изменение файла ломает расшифровку | Злоумышленник может подменить запись незаметно |
| Один скрипт — вся логика | Нужна база данных и куча кода |
Шаг 1. Устанавливаем зависимости
Нужен Python 3.11 или новее. Затем:
pip install cryptography pyperclip- cryptography — модуль Fernet;
- pyperclip — автоматическое копирование пароля в буфер.
Шаг 2. Проектируем класс
Основная логика зашита в класс PasswordManager. Методы:
- generate_key() — создаёт мастер-ключ;
- create_password_file() — инициализирует пустой зашифрованный файл;
- add_password(site, password) — шифрует и сохраняет запись;
- get_password(site) — возвращает пароль по имени сайта;
- list_passwords() — показывает все сохранённые сайты.
Шаг 3. Пишем код
Полный скрипт сохраните как password_manager.py:
import os from cryptography.fernet import Fernet from pyperclip import copy MASTER_KEY_FILE = "master.key" PASSWORD_FILE = "passwords.encrypted" class PasswordManager: def __init__(self): self.key = self._load_or_generate_key() self.cipher = Fernet(self.key) def _load_or_generate_key(self): if os.path.exists(MASTER_KEY_FILE): with open(MASTER_KEY_FILE, "rb") as f: return f.read() else: key = Fernet.generate_key() with open(MASTER_KEY_FILE, "wb") as f: f.write(key) print("Master key generated and saved to master.key") return key def create_password_file(self): if not os.path.exists(PASSWORD_FILE): with open(PASSWORD_FILE, "wb") as f: f.write(self.cipher.encrypt(b"")) print("Password file created.") def add_password(self, site, password): if not os.path.exists(PASSWORD_FILE): self.create_password_file() with open(PASSWORD_FILE, "rb") as f: encrypted_data = f.read() decrypted_data = self.cipher.decrypt(encrypted_data).decode() entries = {} if decrypted_data: for line in decrypted_data.splitlines(): if ":" in line: s, p = line.split(":", 1) entries[s] = p entries[site] = password new_data = "\n".join(f"{s}:{p}" for s, p in entries.items()) with open(PASSWORD_FILE, "wb") as f: f.write(self.cipher.encrypt(new_data.encode())) print(f"Password for {site} added successfully.") def get_password(self, site): if not os.path.exists(PASSWORD_FILE): self.create_password_file() with open(PASSWORD_FILE, "rb") as f: encrypted_data = f.read() decrypted_data = self.cipher.decrypt(encrypted_data).decode() entries = {} if decrypted_data: for line in decrypted_data.splitlines(): if ":" in line: s, p = line.split(":", 1) entries[s] = p return entries.get(site) def list_passwords(self): if not os.path.exists(PASSWORD_FILE): return [] with open(PASSWORD_FILE, "rb") as f: encrypted_data = f.read() decrypted_data = self.cipher.decrypt(encrypted_data).decode() sites = [] if decrypted_data: for line in decrypted_data.splitlines(): if ":" in line: sites.append(line.split(":", 1)[0]) return sitesЧтобы использовать менеджер, создайте экземпляр класса и вызывайте методы. Например:
pm = PasswordManager() pm.add_password("github", "my-secret-password") print(pm.get_password("github")) print(pm.list_passwords())Типичные ошибки
- Хранить файл с ключом и файл с паролями в одной папке. Если злоумышленник получит оба — все пароли расшифрованы.
- Использовать мастер-пароль, который легко подобрать. Лучше длинную фразу, а не «password123».
- Забыть про резервную копию. Потеряете ключ — потеряете доступ ко всем паролям.
Свой менеджер паролей — это не только способ защитить данные, но и отличный тренажёр по работе с шифрованием. Возьмите за основу этот код, добавьте интерфейс командной строки или графическую оболочку — и пользуйтесь каждый день.
Комментарии (0)
Войдите, чтобы комментировать.
Пока нет комментариев. Будьте первым.