DevGang
Авторизоваться

Поддерживайте чистый код Python с помощью Black и GitHub Actions

Написать код достаточно сложно, но обеспечить его хороший формат и легкость чтения может быть еще более сложной задачей.

За десять лет наши навыки кодирования значительно улучшились. Но большинство из них - это не какое-то причудливое использование API или что-то в этом роде. Это то, как мы форматируем код.

В свои ранние годы мы кодировали результат. Конечно, это конечная цель каждого программиста. Но по мере продвижения становилось понятным, что хорошее кодирование — это гораздо больше, чем просто выполнение задач.

Было нелегко поделиться своими кодами с другими и не получить кучу вопросов, чтобы объяснить их. Другим программистам было очень сложно переварить наши коды, даже с помощью вспомогательных документов и встроенных комментариев.

Работа программиста не заканчивается на рабочем коде.

Помимо документации, есть кое-что, что делает хороший код отличным. И сообщество программистов не преминуло выяснить, что это такое.

Это то, как мы форматируем наш код.

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

По этой причине у нас есть руководство по стилю, известное как PEP 8. Этот стандарт позволяет каждому программисту кодировать в одном стиле. Если все сделано правильно, начинающий программист может потратить меньше времени на выяснение, какая строка к чему относится.

Вот пример кода. Первый - это то, как я бы закодировал его в начале своей карьеры. Это делает свою работу. Он считывает файл и обучает модель.

Неформатированный код Python
Неформатированный код Python

На приведенном выше изображении вы можете видеть, что только половина нашего кода помещается на экране. Нам пришлось бы прокручивать вправо и влево, чтобы прочитать и понять код. Везде есть нежелательные пустые строки и пробелы, в то время как там, где они должны быть, нет пустой строки.

И вот как это будет выглядеть после внедрения руководства по стилю. Этот вариант легче понять, не так ли?

Отформатированный код Python
Отформатированный код Python

Но есть одна проблема. Запомнить руководство по стилю и заставить себя закодировать его таким образом требует много работы. Мы все еще хотели потратить больше времени на выполнение этой работы.

Было бы полезно, если бы кто-то другой позаботился о форматировании кода. Вот тут-то и появляется черный цвет. Black - это пакет Python для форматирования вашего кода в соответствии с предопределенным руководством по стилю в одной команде. Это руководство может быть PEP 8, или вы можете настроить его под свою организационную версию.

Современные редакторы кода обычно поставляются с поддержкой форматирования документов. Например, в VS Code вы можете щелкнуть правой кнопкой мыши на редакторе и выбрать форматирование кода. Если установлен Black, он сразу же отформатирует ваш код.

Все эти улучшения на этом не остановились. Вы можете автоматизировать форматирование кода с помощью крючков предварительной фиксации и не беспокоиться об этом во время кодирования. Когда вы вносите изменения, они форматируют все ваши файлы python.

Последний недостающий кусочек головоломки - это вот что. Даже крючки предварительной фиксации запускаются на компьютерах разработчиков. Работая в команде, вы по-прежнему полагаетесь на них при форматировании.

Что, если вы можете сделать это централизованно, независимо от того, кто является разработчиком и как они это сделали?

На этом и сосредоточен этот пост. Для этого мы используем действия GitHub.

Когда разработчики регистрируются в центральном репозитории, их код автоматически приводится в соответствие со стандартами организации. Действия GitHub запускают рабочий процесс всякий раз, когда мы вносим изменения в репозиторий. Мы можем настроить его для выполнения команды форматирования блока.

Настройте действия Black на GitHub для автоматического форматирования кода Python

Чтобы использовать black для форматирования вашего кода Python при внесении изменений с помощью GitHub Actions, вы можете выполнить следующие действия:

Во-первых, убедитесь, что в вашем проекте установлен black. Вы можете сделать это, добавив black к requirements.txt файл в вашем проекте или запустив pip install black в виртуальной среде вашего проекта.

Затем создайте новый файл в каталоге .github/workflows вашего проекта под названием format.yml. Этот файл будет содержать конфигурацию для вашего рабочего процесса GitHub Actions.

В файле format.yml вы можете определить рабочий процесс, который выполняется черным цветом в вашем коде всякий раз, когда вы вносите изменения в свой репозиторий. Вот пример рабочего процесса, который делает это:

name: Format code

on:
  push:
    branches: [ master ]

jobs:
  format:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v2
      - name: Format code with black
        run: |
          pip install black
          black .
      - name: Commit changes
        uses: EndBug/add-and-commit@v4
        with:
          author_name: ${{ github.actor }}
          author_email: ${{ github.actor }}@users.noreply.github.com
          message: "Format code with black"
          add: "."
          branch: ${{ github.ref }}

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

Он устанавливает black, а затем запускает команду black для всего проекта (. в конце black команды указывается текущий каталог). Наконец, он фиксирует новые изменения в той же ветке.

После того как вы определили свой рабочий процесс, вы можете зафиксировать изменения в своем репозитории и отправить их на GitHub. Когда вы это сделаете, рабочий процесс запустится автоматически, отформатировав ваш с black.

Исключение и включение файлов и папок для форматирования

Существует проблема с вышеуказанной конфигурацией. Он просматривает все файлы и папки в нашем репозитории и пытается их отформатировать. Иногда мы хотим избежать этого для определенных файлов.

У black есть опции для настройки его поведения при форматировании.

В следующем примере мы настроили black так, чтобы он игнорировал любые файлы внутри папки ref.

- name: Format code with black
  run: |
    pip install black
    black . --exclude="env/*"

Это приведет к запуску команды black для всех файлов в текущем каталоге, за исключением файлов в папке env.

По умолчанию black отформатирует все файлы .py, .pyi и .ipynb. В качестве альтернативы вы можете указать список файлов для включения напрямую, используя флаг --include, например:

- name: Format code with black
  run: |
    pip install black
    black --include="\.py" .

Это приведет к запуску команды black только для файлов с расширением .py в текущем каталоге.

Да, вы можете использовать оба флага --include и --exclude вместе, чтобы указать более сложный шаблон файлов для включения или исключения.

- name: Format code with black
  run: |
    pip install black
    black --include="\.py" --exclude="env/*" .

Это приведет к запуску команды black для всех файлов с расширением .py в текущем каталоге, за исключением файлов в папке env.

Обратите внимание, что флаг --include имеет приоритет над флагом --exclude, поэтому, если файл соответствует обоим шаблонам, он будет включен. Таким образом, будьте особенно осторожны, когда включаете шаблоны. Слепое включение шаблонов, как в приведенном выше примере, приведет к тому, что black также отформатирует файлы в вашей папке env.

Вы можете указать несколько шаблонов как для --include, так и для --exclude, разделив их запятой, например:

- name: Format code with black
  run: |
    pip install black
    black --include="\.py,\.pyi" --exclude="env/*,tests/*" .

Это приведет к запуску команды black для всех файлов с расширением .py или .pyi в текущем каталоге, за исключением файлов в папках env или tests.

Еще один полезный способ управления файлами, подлежащими исключению, - это ваш файл .gitignore. Возможно, у вас уже есть один в вашем проекте. Если файл соответствует каким-либо шаблонам в .gitignore, эти файлы будут проигнорированы при форматировании.

Если вам нужно использовать оба варианта поведения .gitignore и exclude, согласно официальным документам, вам нужно использовать --extend-exclude вместо --exclude.

Расширение рабочего процесса с помощью более чистых инструментов кода

Black - один из важнейших инструментов для форматирования кода Python. Это заботится о многих вещах. Но у нас есть и другие важные вещи.

Одним из аспектов чистого кодирования является логическая сортировка импорта. Но еще раз, вам не нужно беспокоиться об этом. Вы можете использовать вставку пакета с вашим рабочим процессом GitHub для автоматической обработки этого.

Удаление избыточных или неиспользуемых переменных - еще одно качество хорошей кодовой базы. Многие идеи в настоящее время автоматически выделяют такие новые переменные. Но autoflake8 также может автоматически удалять их.

Вот готовая конфигурация действий на GitHub:

name: Format code

on:
  push:
    branches: [ master ]

jobs:
  format:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v2
      - name: Format code with black
        run: |
          pip install black
          black .
      - name: Sort imports with isort
        run: |
          pip install isort
          isort .
      - name: Remove unused imports with autoflake
        run: |
          pip install autoflake
          autoflake --in-place --remove-all-unused-imports --remove-unused-variables --recursive .
      - name: Commit changes
        uses: EndBug/add-and-commit@v4
        with:
          author_name: ${{ github.actor }}
          author_email: ${{ github.actor }}@users.noreply.github.com
          message: "Format code with black"
          add: "."
          branch: ${{ github.ref }}

Когда все идет не так, как мы хотим

Независимо от всех наших усилий, могут быть случаи, когда этот автоматический рефакторинг кода может завершиться неудачей.

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

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

Из-за этого такие проблемы, как опечатки и другие незначительные вещи, обычно приводящие к сбою рефакторинга кода, не будут проблемой. Но когда они случаются, мы должны быть готовы.

Приведенная ниже конфигурация будет отправлять уведомление по электронной почте всякий раз, когда наш рефакторинг кода завершается неудачей.

- name: Notify errors
  if: failure()
  uses: dawidd6/action-send-mail@v2
  with:
    server_address: smtp.gmail.com
    server_port: 465
    username: ${{ secrets.EMAIL_USERNAME }}
    password: ${{ secrets.EMAIL_PASSWORD }}
    subject: "Format code with black"
    body: "Format code with black failed"
    to: ${{ secrets.EMAIL_TO }}
    from: ${{ secrets.EMAIL_FROM }}
    content_type: text/plain

Вышеупомянутое расширение конфигурации использует пользовательское действие GitHub, созданное Дэвидом Дзирлой.

Заключение

Никому не нужен беспорядочный код, но у некоторых хватает терпения его почистить.

У каждого сообщества программистов есть руководство по стилю, обеспечивающее читаемость кода. Но это первое препятствие в решении проблемы. Нам нужно сделать форматирование кода легким, чтобы каждый разработчик мог часто им пользоваться. Пакеты, подобные Black, делают это.

Но то, что это делается без усилий, не означает, что им пользуются все. Крючки предварительной фиксации автоматизируют процесс, но по-прежнему полагаются на разработчика. В этом посте представлен способ централизованного автоматического форматирования.

Black с помощью GitHub Actions может гарантировать, что код всегда отформатирован. Вы можете централизованно диктовать руководство по стилю. Это может быть PEP 8 или ваш собственный. И когда они по какой-либо причине выходят из строя, вы также можете получить уведомление.

#Python #Data Science
Комментарии
Чтобы оставить комментарий, необходимо авторизоваться

Присоединяйся в тусовку

В этом месте могла бы быть ваша реклама

Разместить рекламу