GitHub Actions CI/CD Pipeline for a Python Project
In modern software development, manually running test suites, checking code formatting, and deploying releases is inefficient and error-prone. **Continuous Integration and Continuous Deployment (CI/CD)** automate these repetitive steps, ensuring that every git commit is tested, verified, and safely pushed to production.
With **GitHub Actions** built directly into GitHub repositories, setting up powerful CI/CD workflows no longer requires third-party platforms like Jenkins or Travis CI. This comprehensive guide walks you through building a robust GitHub Actions workflow for a Python project that runs lint checks, executes pytest test suites, and automates package publishing.
1. Understanding GitHub Actions Architecture
GitHub Actions workflows are defined in YAML files located inside `.github/workflows/`. Key components include:
- Workflows: Automated procedures defined by `.yml` files that run one or more jobs.
- Events: Specific triggers that initiate workflow execution (e.g., `push` to `main`, pull requests, or scheduled cron triggers).
- Jobs: Sets of steps executed on the same virtual runner machine (e.g., `ubuntu-latest`).
- Steps: Individual tasks or shell commands executed within a job, such as checking out code or running test scripts.
2. Writing the CI/CD Pipeline Configuration
Create a file named `ci-cd.yml` inside your repository's `.github/workflows/` directory to orchestrate linting, testing, and building.
name: Python CI/CD Pipeline
on:
push:
branches: [ "main" ]
pull_request:
branches: [ "main" ]
jobs:
test:
runs-on: ubuntu-latest
strategy:
matrix:
python-version: ["3.9", "3.10", "3.11", "3.12"]
steps:
- name: Checkout Repository
uses: actions/checkout@v4
- name: Set up Python ${ { matrix.python-version } }
uses: actions/setup-python@v5
with:
python-version: '${ { matrix.python-version } }'
cache: 'pip'
- name: Install Dependencies
run: |
python -m pip install --upgrade pip
pip install flake8 pytest
if [ -f requirements.txt ]; then pip install -r requirements.txt; fi
- name: Lint with Flake8
run: |
# Stop the build if there are Python syntax errors or undefined names
flake8 . --count --select=E9,F63,F7,F82 --show-source --statistics
# Exit-zero treats all errors as warnings
flake8 . --count --exit-zero --max-complexity=10 --max-line-length=127 --statistics
- name: Test with Pytest
run: |
pytest
Conclusion
Automating Python testing and code quality checks with GitHub Actions gives engineering teams instant feedback on pull requests and guarantees that only verified code reaches production. By leveraging matrix builds across multiple Python versions, developers can ensure complete cross-version compatibility effortlessly.