Back

How to Deploy a Django Project with CI/CD Using GitHub Actions and DigitalOcean

Oct, 27 2024

Django & Github Actions - Coding for Entrepreneurs

 

Table of content

  1. Why Use CI/CD with GitHub Actions and a VPS?
  2. Creating a basic Django project
  3. Setting up the CI/CD workflows
  4. Deploying and Final thoughts

 

Why Use CI/CD with GitHub Actions and a VPS?

Setting up a robust CI/CD (Continuous Integration/Continuous Deployment) pipeline is essential for ensuring smooth, automated tests and deployments. In this blog, I'll walk you through how I used GitHub Actions to automate the deployment of a Django project on a DigitalOcean vps. This setup saves time and keeps the code secure, as all changes are tested and deployed automatically.

 

Creating a basic Django project

# 1. Install Python and Django: Make sure Python is installed on your machine. Install Django using pip:

pip install django
# 2. Create a Django Project: In your terminal, create a new directory for your project, 
#     navigate into it, and start a new Django project:

django-admin startproject myproject
cd myproject
# 3. Start a Django App: Django uses apps to organize code. Create a basic app, like main:

python manage.py startapp main
# 4. Configure Installed Apps: Open settings.py in your project folder and add main to the INSTALLED_APPS list:
#     myproject/settings.py

INSTALLED_APPS = [
    ...
    'main',
]
# 5. Set Up Database Migrations: Initialize the database by running migrations, which set up the default tables:

python manage.py migrate
# 6. Run the Development Server: To make sure everything is working, start the development server:
#     Visit http://127.0.0.1:8000 in your browser, and you should see Django’s welcome page, 
#     confirming that your project is set up successfully.

python manage.py runserver

# 7. Create a .gitignore File: To prevent sensitive files from being pushed to GitHub, 
#     create a .gitignore file in your project folder and add common patterns for Django projects:

*.pyc
__pycache__/
db.sqlite3
.env
# 8. Initialize Git and Commit the Project: Initialize Git, add your files, and commit your initial project:

git init
git add .
git commit -m "Initial Django project setup"
# 9. Finally create a .github/workflows folder at the project root the same level as manage.py
#    the final project structure should look like this:

myproject/                     # Root project directory
├── main/                      # Django app directory
│   ├── migrations/            # Directory for database migrations
│   │   └── __init__.py
│   ├── __init__.py            # App initialization
│   ├── admin.py               # Admin panel configuration
│   ├── apps.py                # App configuration
│   ├── models.py              # Models for the app
│   ├── tests.py               # Tests for the app
│   ├── views.py               # Views for the app
│   └── ...                    # Additional app files as needed
├── myproject/                 # Main project configuration directory
│   ├── __init__.py            # Project initialization
│   ├── asgi.py                # ASGI configuration
│   ├── settings.py            # Project settings, including INSTALLED_APPS
│   ├── urls.py                # URL routing configuration
│   └── wsgi.py                # WSGI configuration
├── .gitignore                 # Ignored files for Git
├── db.sqlite3                 # SQLite database file (created after migrations)
├── manage.py                  # Django management script
└── .github/                   # GitHub folder for workflows
    └── workflows/             # Directory for CI/CD workflow files

 

Setting up the CI/CD workflows

With our basic Django project set up and committed to GitHub, we’re ready to create an automated workflow that deploys updates to our Django website whenever changes are pushed to the main branch. Before proceeding, you'll need to store your server host, username, and password as secrets in your project repository to ensure secure access during deployment. This blog will focus on setting up the CI/CD pipeline rather than configuring the VPS itself. For a thorough, beginner-friendly guide to preparing your VPS for production, check out this official tutorial by DigitalOcean.

  1. Inside .github/workflows/ create a file deploy.yml and add the following configuration:
    name: CI/CD Pipeline
    
    on:
      push:
        branches:
          - main
    
    jobs:
      deploy:
        runs-on: ubuntu-latest
    
        steps:
        - name: Check out the repository
          uses: actions/checkout@v2
    
        - name: Deploy to Production Server
          env:
            HOST: ${{ secrets.PRODUCTION_HOST }}
            USERNAME: ${{ secrets.PRODUCTION_USER }}
            PASSWORD: ${{ secrets.PRODUCTION_PASSWORD }}
    
          run: |
            sshpass -p "$PASSWORD" ssh -o StrictHostKeyChecking=no $USERNAME@$HOST "
            cd /home/portfolio_website &&
            git pull origin main &&
            pip install -r requirements.txt &&
            python manage.py collectstatic --noinput &&
            python manage.py migrate &&
            sudo systemctl restart gunicorn
            "
    Explanation of above workflow: 
    • Define Workflow Trigger: Set the workflow to trigger on pushes to the main branch.
    • Set the job to run on ubuntu-latest.
    • Use the actions/checkout@v2 action to pull the latest code from the repository.
    • Use env variables from repo secrets (host, username, and password) to connect to the server.
    • Connect to VPS: Use sshpass with the password secret to connect to the server over SSH.
    • Move into the project directory on the VPS where the code resides.
    • Run git pull origin main  to pull the latest changes from the main branch.
    • Run pip install -r requirements.txt to install any new or updated dependencies.
    • Run Tests: Use python manage.py test to run Django tests,
    • Run python manage.py collectstatic --noinput to gather static files for deployment.
    • Run python manage.py migrate to apply any new database schema changes.
    • Restart the Gunicorn service using sudo systemctl restart gunicorn to serve the updated code.

 

Deploying and Final thoughts

Now that you've set up your CI/CD pipeline using GitHub Actions, deploying your Django application to your VPS becomes a seamless process. With each push to the main branch, your updates are automatically deployed, ensuring that your website remains up-to-date without the hassle of manual intervention. This automation not only saves time but also minimizes the risk of human error during deployment, allowing you to focus more on developing features rather than worrying about the deployment process.

As you continue to develop your application, remember to regularly test your CI/CD pipeline. This practice will help you catch any issues early, ensuring a smooth deployment every time. Consider expanding your pipeline to include additional steps, such as running automated tests, monitoring application performance, and integrating other services as your project grows.

If you found this guide helpful, I encourage you to share it with fellow developers who might benefit from setting up their own CI/CD workflows. Additionally, feel free to check out my linksdown bellow and my GitHub repository for code examples and further resources. Your feedback is invaluable, so don’t hesitate to reach out with any questions or suggestions for future topics! Happy coding!