В 2024 году Python исполняется 33 года. За это время он прошел невероятный путь – от пет-проекта до одного из самых универсальных и популярных языков. Все начинающие питонисты знают, что первую версию языка разработал голландский программист Гвидо ван Россум, а назван он в честь британского комедийного шоу, а не прожорливой змеи. Как развивались основные концепции языка, почему крупные ИТ-компании боялись, что автобус может переехать Гвидо, и когда на логотипе Python все-таки появились змеи – расскажет публикация на Хабре.
🏆 Лучшие практики разработки на Python
Знание и правильное применение лучших практик – один из самых важных навыков профессионального разработчика. Следование общепринятым правилам позволяет:
Повысить качество кода. Лучшие практики основаны на многолетнем опыте обширного сообщества разработчиков и направлены на минимизацию ошибок, улучшение читаемости и поддерживаемости кода. Это помогает создавать более надежные и долговечные системы.
Ускорить процесс разработки. Применение многократно опробованных шаблонов и подходов помогает быстрее писать типовой код и решать распространенные проблемы.
Упростить совместную работу, ревью кода и интеграцию изменений. Особенно в больших командах и опенсорсных проектах.
Обеспечить гибкость и масштабируемость проекта. Правильно организованный код легче адаптировать под новые требования и масштабы. Это снижает риск технического долга — ситуации, в которой изменения становятся слишком дорогостоящими или сложными для реализации.
Привет!
Всю неделю мы мониторим интернет, чтобы в воскресенье прислать тебе интересное письмо. Наша цель – держать читателей в курсе последних открытий и тенденций в мире Python. В еженедельных письмах ты найдешь:
Новые возможности в последних версиях Python
Работа с базами данных и SQL в Python.
Веб-разработка на Django и Flask.
Машинное обучение и анализ данных с помощью Python.
Автоматизация и работа с API на Python.
Тестирование и отладка кода на Python.
Задачи для новичков с решениями.
Устанавливайте Python с поддержкой нескольких версий. Используйте mise или pyenv для установки Python – они дают возможность переключаться между разными версиями языка и позволяют обновлять интерпретатор без влияния на другие инструменты и проекты. Еще один отличный вариант – Development Containers.
Используйте последнюю версию Python. Для новых проектов выбирайте самую последнюю стабильную версию Python 3. Это обеспечивает наличие последних исправлений безопасности и максимальную производительность. Обязательно обновляйте проекты по мере выхода новых версий языка и забудьте про Python 2.
Используйте pipx для запуска приложений в среде разработки. Вместо установки пакетов с помощью pip или другого аналогичного метода используйте pipx для запуска инструментов в отдельной виртуальной среде.
Не используйте Poetry для новых проектов – в нем нестандартно реализованы некоторые ключевые функции. Лучше пользоваться PDM или Hatch.
Создавайте файл pyproject.toml в корневой директории каждого проекта – для хранения информации о конфигурации и используемых инструментах.
Используйте src-структуру для каталогов. Это требует использования редактируемых установок, но PDM и Hatch упрощают задачу.
Используйте виртуальные среды для разработки. Виртуальная среда изолирует проекты и наборы установленных для них пакетов – не будет никаких конфликтов.
Применяйте файлы requirements.txt для установки пакетов в среду – вместо использования команды pip. Либо используйте PDM или Hatch для управления пакетами.
Используйте инструмент для форматирования кода и линтер для проверки на ошибки. Самый популярный форматер Python-кода – Black, а самый известный линтер – flake8. Однако их с успехом можно заменить одним мощным и быстрым инструментом – Ruff.
Применяйте pytest для тестирования, а в ситуациях, где это невозможно – используйте стандартный модуль unittest.
Используйте PyInstaller для упаковки приложений в исполняемый файл. А свои пакеты публикуйте в виде wheel, чтобы другие разработчики могли загружать их с помощью pipx и pip-sync.
Используйте аннотации типов – особенно в важных приложениях и библиотеках. Для проверки вам пригодится mypy, а для интеграции этого инструмента с Pydantic – плагин.
Форматируйте строки с помощью f-строк, а не с использованием %, str.format() или str.Template().
Всегда используйте объекты datetime, которые знают о временных зонах. По умолчанию Python создает объекты datetime, которые не включают временную зону.
Применяйте enum или collections.namedtuple() для неизменяемых наборов пар «ключ-значение».
Создавайте классы данных для пользовательских объектов. Среди прочего это позволяет сократить количество кода, необходимого для определения классов, предназначенных для хранения значений. Экземпляры таких классов можно замораживать.
Используйте collections.abc для пользовательских типов коллекций. Абстрактные базовые классы в collections.abc реализованы на C и работают очень быстро.
Применяйте breakpoint() для отладки. Эта функция создает точки останова, которые могут использовать и встроенный отладчик, и внешние инструменты отладки.
Используйте журналирование для диагностических сообщений. Команда print() удобна для вывода отладочной информации, но в скрипты и приложения нужно включать логирование.
Применяйте формат TOML для конфигурационных файлов – если они предназначены для людей. Используйте формат JSON для данных, которые передаются между компонентами приложения.
Используйте async только там, где это необходимо. Асинхронные возможности Python позволяют одному процессу избегать блокировки на операциях ввода-вывода. Для запуска нескольких процессов нужно использовать контейнеры или сервер Gunicorn. Чтобы создать собственное приложения для управления многочисленными процессами, воспользуйтесь этим стандартным пакетом.
Обрабатывайте ввод из командной строки с argparse. Модуль argparse теперь является рекомендуемым способом обработки ввода вместо устаревших optparse и getopt.
Для указания путей к файлам и каталогам используйте pathlib, а не строки.
Используйте os.scandir() вместо os.listdir(). Функция os.scandir() значительно быстрее и эффективнее, чем os.listdir().
Запускайте внешние команды с subprocess. Модуль subprocess предоставляет безопасный способ запуска внешних команд. Используйте его вместо spawn, popen2 и popen3.
Используйте httpx для клиентских приложений. Пакет httpx поддерживает HTTP/2 и async и заменяет requests, который работает только с HTTP 1.1.
📒 Google Colab или Jupyter Notebook: что лучше подойдет для новичка
Jupyter Notebook обладает массой очевидных достоинств:
Позволяет выполнять код по частям и мгновенно видеть результаты.
Поддерживает большинство популярных библиотек.
В блокнотах легко визуализировать данные и форматировать текст.
Устанавливается локально, работает без подключения к сети.
Облачный сервис Google Colab предоставляет похожую функциональность – код можно писать и выполнять в браузере – и несколько дополнительных преимуществ:
Использование GPU/TPU.
Удобное меню навигации по файлу.
Возможность совместной работы над проектом – настойка доступа и синхронизация работают точно так же, как в документах Google.
Подробнее о преимуществах и начале работы в Google Colab – в этой статье на Хабре
🕸️ Веб-разработка
«Как настроить уведомления в Django с помощью сигналов: пошаговое руководство» рассказывает обо всех тонкостях работы с сигналами, которые запускают выполнение нужных действий после совершения определенных манипуляций с моделями. Например, сигнал может:
Запустить автоматическое создание профиля пользователя после регистрации.
Отправить уведомление о заполнении формы, появлении нового отзыва, получении сообщения.
Обновить данные в связанных моделях.
Сделать запись об изменении статуса объекта.
API предоставляет данные о студентах
«Безопасность в Django: защита от распространенных угроз веб-приложений» – рассказывает о самых распространенных типах атак (SQL-инъекциях, межсайтовой подделке запросов, кросс-сайтовом скриптинге, DoS и DDoS) и очень подробно разбирает способы защиты от них.
Настройка nginx для защиты от DDoS
📈 Как улучшить производительность Python
Беспрецедентное развитие ИИ сделало Python суперпопулярным языком – и поставило исключительно сложную задачу перед ведущими инженерами: как увеличить скорость работы Питона, не жертвуя его простотой и гибкостью. Одним из решений проблемы стал перенос критически важных для производительности частей кода на более быстрые языки – C, C++ и Rust. Для упрощения совместного использования Python и Rust разработчик Дэвид Хьюитт создал PyO3. В этом интервью он подробно рассказал о сложностях разработки такого проекта и его впечатляющих возможностях.
Как преодолеть разрыв
Интеграция Python и Rust – нетривиальная задача, поскольку эти два языка имеют принципиально разные подходы к управлению памятью, потоками и обработке ошибок. Однако PyO3 решает эти проблемы, используя мощные возможности Rust и C-образную архитектуру интерпретатора Python.
В основе PyO3 лежит концепция сопоставления функций и структур Rust их аналогам в Python. Используя процедурные макросы, PyO3 генерирует необходимый код для создания совместимых с Python объектов и функций, позволяя разработчикам Python легко взаимодействовать с компонентами на базе Rust. Этот подход позволяет программистам на Python воспользоваться преимуществами производительности и безопасности Rust без необходимости глубоко погружаться в тонкости языка.
Безопасность памяти и время жизни объектов
Одна из ключевых задач при объединении Python и Rust – обеспечение безопасности памяти. Система проверки заимствований и времени жизни объектов в Rust играет в этом отношении важную роль. PyO3 использует аннотации времени жизни Rust для управления владением и временем жизни объектов Python, гарантируя, что ссылки на объекты Python являются действительными, а доступ к памяти не осуществляется после ее освобождения. Это внимание к безопасности памяти является существенным преимуществом использования Rust в контексте оптимизации производительности Python. Обеспечивая эти гарантии во время компиляции, PyO3 помогает разработчикам избежать распространенных ошибок и уязвимостей, связанных с памятью, которые могут возникать при использовании привязок C/C++.
Обработка ошибок и производительность
Это одно из самых мощных преимуществ PyO3. Сопоставляя механизмы обработки ошибок Rust с системой исключений Python, PyO3 обеспечивает бесшовную интеграцию для программистов, работающих с обоими языками. Эта интеграция гарантирует правильную передачу ошибок, позволяя коду Python элегантно обрабатывать исключения, созданные в Rust. Что касается производительности, PyO3 стремится обеспечить производительность, близкую к нативной, за счет использования абстракций Rust. Хотя на границе между Python и Rust могут быть некоторые накладные расходы, прирост производительности, достигаемый внутри кода Rust, часто с лихвой компенсирует их. По мере развития проекта PyO3 команда активно работает над оптимизацией этих пограничных случаев для дальнейшего снижения влияния на производительность.
Потоки и асинхронность
Одна из самых сложных областей интеграции Python и Rust – обработка потоков и асинхронности. Асинхронная модель Rust с async/await и глобальная блокировка интерпретатора (GIL) Python представляют собой уникальные проблемы, которые команда PyO3 активно решает. Разработчики исследуют различные подходы к преодолению разрыва между моделями параллелизма Rust и Python, в том числе использование типов Rust Send и Sync для обеспечения безопасного обмена данными между потоками, а также обеспечение бесшовной совместимости между асинхронными средами выполнения Rust и циклами событий Python.
Автор рассылки: Наталья Кайда