Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
node_modules
.env
.env.*
!**/.env.example
!env/.env.shared.example
env/.env.shared
dist
Expand Down
13 changes: 13 additions & 0 deletions apps/router-worker/.env.example
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
REDIS_URL=redis://localhost:6379
DATABASE_URL=postgres://postgres:postgres@localhost:5432/tracking_base
ROUTER_QUEUE_NAME=router-deliveries
ROUTER_WORKER_NAME=router-delivery-worker
ROUTER_WORKER_CONCURRENCY=5
META_CONVERSIONS_ENDPOINT_URL=
META_PIXEL_ID=
META_ACCESS_TOKEN=
META_TEST_EVENT_CODE=
GOOGLE_CONVERSIONS_ENDPOINT_URL=
GOOGLE_CONVERSIONS_API_KEY=
TIKTOK_EVENTS_ENDPOINT_URL=
TIKTOK_ACCESS_TOKEN=
22 changes: 22 additions & 0 deletions apps/tracking-api/.env.example
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
PORT=3000
DATABASE_URL=postgres://postgres:postgres@localhost:5432/tracking_base
TEST_DATABASE_URL=postgres://postgres:postgres@localhost:5432/tracking_base
# Router worker and queue
REDIS_URL=redis://localhost:6379/0
ROUTER_QUEUE_NAME=router-deliveries
ROUTER_WORKER_NAME=router-delivery-worker
ROUTER_WORKER_CONCURRENCY=5
REDIS_HOST=
REDIS_PORT=6379
REDIS_DB=0
REDIS_USERNAME=
REDIS_PASSWORD=
NODE_ENV=development
METRICS_ENABLED=true
TRACKING_API_AUTH_MODE=off
TRACKING_API_SECRET=
TRACKING_SIGNATURE_SKEW_SECONDS=300
TRACKING_RATE_LIMIT_ENABLED=false
TRACKING_RATE_LIMIT_WINDOW_MS=60000
TRACKING_RATE_LIMIT_MAX_REQUESTS=120
TRACKING_CORS_ALLOW_ORIGINS=http://localhost:5173,https://prankbook.com
7 changes: 6 additions & 1 deletion deploy/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ This folder separates deploy concerns:

- `deploy/app`: application containers (`tracking-console`, `tracking-api`, `router-worker`).
- `deploy/infra`: shared infrastructure containers (`redis`).
- `deploy/vps`: upload-first guide and host Nginx template for VPS rollout.

## Is this model correct for current repo flow?

Expand All @@ -18,6 +19,7 @@ Yes, this matches the current architecture:
## Prerequisites

1. GHCR images exist for both services:
- `tracking-console`
- `tracking-api`
- `router-worker`
2. Postgres is reachable (Railway/Supabase/self-hosted).
Expand All @@ -39,7 +41,8 @@ docker compose up -d
cd deploy/app
cp .env.example .env
# edit .env values first
docker compose up -d
docker compose pull
docker compose up -d --no-build
```

### 3) Smoke check
Expand All @@ -63,10 +66,12 @@ curl -fsS http://127.0.0.1:13001/ready

This repository workflow publishes images to:

- `ghcr.io/<github-owner>/<repo>/tracking-console:{latest|staging-<sha>}`
- `ghcr.io/<github-owner>/<repo>/tracking-api:{latest|staging-<sha>}`
- `ghcr.io/<github-owner>/<repo>/router-worker:{latest|staging-<sha>}`

Example if your repo is `CongThienDev/Tracking_Base_System`:

- `ghcr.io/congthiendev/tracking_base_system/tracking-console:latest`
- `ghcr.io/congthiendev/tracking_base_system/tracking-api:latest`
- `ghcr.io/congthiendev/tracking_base_system/router-worker:latest`
36 changes: 36 additions & 0 deletions deploy/app/.env.example
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
# GHCR images (must exist)
TRACKING_CONSOLE_IMAGE=ghcr.io/congthiendev/tracking_base_system/tracking-console:latest
TRACKING_API_IMAGE=ghcr.io/congthiendev/tracking_base_system/tracking-api:latest
ROUTER_WORKER_IMAGE=ghcr.io/congthiendev/tracking_base_system/router-worker:latest

# API runtime
TRACKING_CONSOLE_PORT=18081
TRACKING_API_PORT=13001
DATABASE_URL=postgresql://<user>:<password>@<host>:<port>/<db>?sslmode=require
ADMIN_API_TOKEN=replace-with-strong-token

# Queue runtime (shared by API + worker)
REDIS_URL=redis://redis:6379/0
ROUTER_QUEUE_NAME=router-deliveries
ROUTER_WORKER_NAME=router-delivery-worker
ROUTER_WORKER_CONCURRENCY=5

# Security (recommended for internet-facing API)
TRACKING_API_AUTH_MODE=shared-secret
TRACKING_API_SECRET=replace-with-strong-secret
TRACKING_SIGNATURE_SKEW_SECONDS=300
TRACKING_RATE_LIMIT_ENABLED=true
TRACKING_RATE_LIMIT_WINDOW_MS=60000
TRACKING_RATE_LIMIT_MAX_REQUESTS=120
TRACKING_CORS_ALLOW_ORIGINS=http://localhost:5173,https://prankbook.com
METRICS_ENABLED=true

# Destination adapters (optional, enable when ready)
META_CONVERSIONS_ENDPOINT_URL=
META_PIXEL_ID=
META_ACCESS_TOKEN=
META_TEST_EVENT_CODE=
GOOGLE_CONVERSIONS_ENDPOINT_URL=
GOOGLE_CONVERSIONS_API_KEY=
TIKTOK_EVENTS_ENDPOINT_URL=
TIKTOK_ACCESS_TOKEN=
5 changes: 1 addition & 4 deletions deploy/app/docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,7 @@ name: tracking-base-app

services:
tracking-console:
image: ${TRACKING_CONSOLE_IMAGE:-tracking-console:local}
build:
context: ../..
dockerfile: apps/tracking-console/Dockerfile
image: ${TRACKING_CONSOLE_IMAGE:-ghcr.io/congthiendev/tracking_base_system/tracking-console:latest}
container_name: tracking-console
restart: unless-stopped
depends_on:
Expand Down
1 change: 1 addition & 0 deletions deploy/infra/.env.example
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
REDIS_PORT=6379
70 changes: 70 additions & 0 deletions deploy/vps/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
# VPS Deploy (Upload-Only)

Use this guide when you do **not** clone the full repository on VPS.

## Files to upload to VPS

Create folder `/opt/tracking-base` on VPS and upload:

1. `deploy/infra/docker-compose.yml` -> `/opt/tracking-base/infra.compose.yml`
2. `deploy/infra/.env.example` -> `/opt/tracking-base/.env.infra.example`
3. `deploy/app/docker-compose.yml` -> `/opt/tracking-base/app.compose.yml`
4. `deploy/app/.env.example` -> `/opt/tracking-base/.env.app.example`
5. `deploy/vps/nginx.tracking-base.conf.example` -> `/opt/tracking-base/nginx.tracking-base.conf.example`

## Prepare env files

```bash
cd /opt/tracking-base
cp .env.infra.example .env.infra
cp .env.app.example .env.app
```

Edit `.env.app` with production values:

- `TRACKING_CONSOLE_IMAGE=ghcr.io/congthiendev/tracking_base_system/tracking-console:latest`
- `TRACKING_API_IMAGE=ghcr.io/congthiendev/tracking_base_system/tracking-api:latest`
- `ROUTER_WORKER_IMAGE=ghcr.io/congthiendev/tracking_base_system/router-worker:latest`
- `TRACKING_CONSOLE_PORT=18081`
- `TRACKING_API_PORT=13001`
- `DATABASE_URL=...`
- `REDIS_URL=redis://redis:6379/0`
- `ADMIN_API_TOKEN=...`
- `TRACKING_API_SECRET=...`

## Run containers

```bash
docker login ghcr.io

docker compose -f infra.compose.yml --env-file .env.infra up -d
docker compose -f app.compose.yml --env-file .env.app pull
docker compose -f app.compose.yml --env-file .env.app up -d --no-build
```

## Verify

```bash
docker compose -f app.compose.yml --env-file .env.app ps
curl -I http://127.0.0.1:18081
curl -fsS http://127.0.0.1:13001/health
curl -fsS http://127.0.0.1:13001/ready
```

## Host Nginx

1. Copy `nginx.tracking-base.conf.example` to `/etc/nginx/sites-available/tracking-base.conf`
2. Replace `console.example.com` and `track.example.com`
3. Enable site and reload Nginx:

```bash
sudo ln -s /etc/nginx/sites-available/tracking-base.conf /etc/nginx/sites-enabled/tracking-base.conf
sudo nginx -t
sudo systemctl reload nginx
```

4. Issue SSL cert:

```bash
sudo certbot --nginx -d console.example.com -d track.example.com
```
27 changes: 27 additions & 0 deletions deploy/vps/nginx.tracking-base.conf.example
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
server {
listen 80;
server_name console.example.com;

location / {
proxy_pass http://127.0.0.1:18081;
proxy_http_version 1.1;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}

server {
listen 80;
server_name track.example.com;

location / {
proxy_pass http://127.0.0.1:13001;
proxy_http_version 1.1;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}
2 changes: 1 addition & 1 deletion env/.env.shared.example
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ TIKTOK_ACCESS_TOKEN=


# --- Deploy app stack ---
TRACKING_CONSOLE_IMAGE=tracking-console:local
TRACKING_CONSOLE_IMAGE=ghcr.io/congthiendev/tracking_base_system/tracking-console:latest
TRACKING_API_IMAGE=ghcr.io/congthiendev/tracking_base_system/tracking-api:latest
ROUTER_WORKER_IMAGE=ghcr.io/congthiendev/tracking_base_system/router-worker:latest
TRACKING_CONSOLE_PORT=18081
Expand Down
Loading