Skip to content

Commit 20bd1ed

Browse files
authored
Merge pull request #48 from codersforcauses/issue/45-impl
Issue/45 Deployment Setup and Continuous Deployment
2 parents 63caa9d + 245993f commit 20bd1ed

4 files changed

Lines changed: 224 additions & 0 deletions

File tree

.env.production.example

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
2+
# FRONTEND
3+
APP_ENV=PRODUCTION
4+
NEXT_PUBLIC_BACKEND_URL="https://robodrone.codersforcauses.com/api"
5+
6+
7+
# BACKEND
8+
APP_NAME=DjangoAPI
9+
API_SECRET_KEY= CHANGE THIS TO A RANDOM STRING
10+
API_ALLOWED_HOSTS=".localhost 127.0.0.1 [::1]"
11+
12+
POSTGRES_HOST=localhost
13+
POSTGRES_NAME=postgres
14+
POSTGRES_USER=postgres
15+
POSTGRES_PASSWORD=password
16+
POSTGRES_PORT=5432
17+
18+
DJANGO_SUPERUSER_PASSWORD= CHANGE THIS TO A RANDOM STRING
19+
DJANGO_SUPERUSER_EMAIL= CHANGE THIS TO A VALID EMAIL
20+
DJANGO_SUPERUSER_USERNAME= CHANGE THIS TO A VALID USERNAME
21+
22+
FRONTEND_URL="https://robodrone.codersforcauses.com/"

.github/workflows/cd-pipeline.yml

Lines changed: 86 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,86 @@
1+
name: Build and Push Docker Images
2+
3+
on:
4+
push:
5+
branches: [main]
6+
7+
env:
8+
REGISTRY: ghcr.io
9+
IMAGE_NAME: ${{ github.repository }}
10+
11+
jobs:
12+
build-and-push-client:
13+
runs-on: ubuntu-latest
14+
permissions:
15+
contents: read
16+
packages: write
17+
18+
steps:
19+
- name: Checkout repository
20+
uses: actions/checkout@v4
21+
22+
- name: Set up Docker Buildx
23+
uses: docker/setup-buildx-action@v3
24+
25+
- name: Log in to Container Registry
26+
uses: docker/login-action@v3
27+
with:
28+
registry: ${{ env.REGISTRY }}
29+
username: ${{ github.actor }}
30+
password: ${{ secrets.GITHUB_TOKEN }}
31+
32+
- name: Build and push client image
33+
uses: docker/build-push-action@v5
34+
with:
35+
context: .
36+
file: ./docker/client/Dockerfile
37+
push: ${{ github.event_name != 'pull_request' }}
38+
tags: |
39+
${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}-prod-client:latest
40+
${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}-prod-client:${{ github.sha }}
41+
cache-from: type=gha
42+
cache-to: type=gha,mode=max
43+
platforms: linux/amd64,linux/arm64
44+
45+
- name: Output client image name
46+
if: github.event_name != 'pull_request'
47+
run: |
48+
echo "Client image: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}-prod-client:latest"
49+
50+
build-and-push-server:
51+
runs-on: ubuntu-latest
52+
permissions:
53+
contents: read
54+
packages: write
55+
56+
steps:
57+
- name: Checkout repository
58+
uses: actions/checkout@v4
59+
60+
- name: Set up Docker Buildx
61+
uses: docker/setup-buildx-action@v3
62+
63+
- name: Log in to Container Registry
64+
uses: docker/login-action@v3
65+
with:
66+
registry: ${{ env.REGISTRY }}
67+
username: ${{ github.actor }}
68+
password: ${{ secrets.GITHUB_TOKEN }}
69+
70+
- name: Build and push server image
71+
uses: docker/build-push-action@v5
72+
with:
73+
context: .
74+
file: ./docker/server/Dockerfile
75+
push: ${{ github.event_name != 'pull_request' }}
76+
tags: |
77+
${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}-prod-server:latest
78+
${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}-prod-server:${{ github.sha }}
79+
cache-from: type=gha
80+
cache-to: type=gha,mode=max
81+
platforms: linux/amd64,linux/arm64
82+
83+
- name: Output server image name
84+
if: github.event_name != 'pull_request'
85+
run: |
86+
echo "Server image: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}-prod-server:latest"

docker-compose.prod.yml

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,62 @@
1+
services:
2+
db:
3+
image: postgres:16.4
4+
restart: unless-stopped
5+
volumes:
6+
- ./data/db:/var/lib/postgresql/data
7+
env_file: ./.env.prod
8+
healthcheck:
9+
test: ["CMD-SHELL", "pg_isready -U postgres"]
10+
interval: 3s
11+
timeout: 3s
12+
retries: 5
13+
14+
server:
15+
image: ghcr.io/codersforcauses/robodrone-prod-server:latest
16+
container_name: robodrone_server
17+
restart: unless-stopped
18+
env_file: ./.env.prod
19+
ports:
20+
- 8081:8081
21+
entrypoint: /entrypoint.sh
22+
volumes:
23+
- ./opt/accesslogs/:/var/log/accesslogs/
24+
- ./opt/static_files:/opt/static_files
25+
environment:
26+
- DJANGO_SETTINGS_MODULE=api.settings
27+
depends_on:
28+
- db
29+
30+
client:
31+
image: ghcr.io/codersforcauses/robodrone-prod-client:latest
32+
container_name: robodrone_client
33+
restart: unless-stopped
34+
env_file: ./.env.prod
35+
ports:
36+
- 3000:3000
37+
entrypoint: /entrypoint.sh
38+
depends_on:
39+
- server
40+
41+
nginx:
42+
image: nginx:stable-alpine3.21
43+
container_name: robodrone_nginx
44+
restart: unless-stopped
45+
ports:
46+
- 80:80
47+
- 443:443
48+
49+
volumes:
50+
- ./docker/nginx/custom.conf:/etc/nginx/nginx.conf
51+
- ./opt/static_files:/opt/static_files
52+
depends_on:
53+
- server
54+
- client
55+
56+
watchtower:
57+
image: containrrr/watchtower:latest
58+
container_name: robodrone_watchtower
59+
restart: unless-stopped
60+
volumes:
61+
- /var/run/docker.sock:/var/run/docker.sock
62+
command: --interval 30

docker/nginx/custom.conf

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
user nginx;
2+
worker_processes 1;
3+
error_log /var/log/nginx/error.log warn;
4+
pid /var/run/nginx.pid;
5+
6+
events {
7+
worker_connections 1024;
8+
}
9+
10+
http {
11+
include /etc/nginx/mime.types;
12+
default_type application/octet-stream;
13+
14+
# upstream to the server container
15+
upstream backend {
16+
server server:8081; #name of container:port exposed
17+
}
18+
19+
# upstream to the server container
20+
upstream frontend {
21+
server client:3000; #name of container:port exposed
22+
}
23+
24+
server {
25+
listen 80;
26+
server_name _;
27+
28+
# proxy to api
29+
location /api/ {
30+
proxy_pass http://backend;
31+
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
32+
proxy_set_header Host $host;
33+
proxy_redirect off;
34+
}
35+
# proxy to django admin
36+
location /admin/ {
37+
proxy_pass http://backend;
38+
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
39+
proxy_set_header Host $host;
40+
proxy_redirect off;
41+
}
42+
# serve django static files
43+
location /static/ {
44+
alias /server/staticfiles/;
45+
}
46+
# proxy to client
47+
location / {
48+
proxy_pass http://frontend;
49+
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
50+
proxy_set_header Host $host;
51+
proxy_redirect off;
52+
}
53+
}
54+
}

0 commit comments

Comments
 (0)