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
2 changes: 1 addition & 1 deletion .env.example
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# Docker compose setting
COMPOSE_PATH_SEPARATOR=:
COMPOSE_DEV=docker-compose-dev.yaml
COMPOSE_DEV=docker-compose.yaml
COMPOSE_PROD=docker-compose-prod.yaml
COMPOSE_FILE=${COMPOSE_DEV}

Expand Down
11 changes: 2 additions & 9 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -35,21 +35,14 @@ This project is a ready-to-use fullstack template that leverages Docker Compose

#### 3. **Configure environment variables**

Copy `.env.example` to `.env` and edit as needed.

```bash
cp .env.example .env
```
If you want to customize settings, copy `.env.example` to `.env` and edit as needed.

> Set the `COMPOSE_FILE` environment variable to switch between development and production modes.

#### 4. **Set up Nginx IP whitelist and SSL certificates**

- Copy `whitelist.conf.example` to `whitelist.conf` and edit as needed.
If you need to restrict the range of allowed IP addresses, edit this file.

```bash
cp nginx/whitelist.conf.example nginx/whitelist.conf
```

- To enable SSL (HTTPS), you need to configure SSL settings in your `.env` file and place your SSL certificates in the `nginx/ssl` directory.
- Env setting:
Expand Down
132 changes: 66 additions & 66 deletions docker-compose-dev.yaml → docker-compose.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -13,28 +13,28 @@ services:
- ./nginx/docker-entrypoint.sh:/docker-entrypoint.sh
environment:
- NODE_ENV=development
- TZ=${TIMEZONE}
- HOSTNAME=${HOSTNAME}
- TZ=${TIMEZONE:-UTC}
- HOSTNAME=${HOSTNAME:-localhost}
# SSL settings
- SSL_ENABLE=${SSL_ENABLE}
- SSL_CERT_FILE=${SSL_CERT_FILE}
- SSL_KEY_FILE=${SSL_KEY_FILE}
- SSL_ENABLE=${SSL_ENABLE:-false}
- SSL_CERT_FILE=${SSL_CERT_FILE:-cert.pem}
- SSL_KEY_FILE=${SSL_KEY_FILE:-privkey.pem}
# Port settings
- FRONTEND_PORT=${FRONTEND_PORT}
- BACKEND_PORT=${BACKEND_PORT}
- PMA_PORT=${PMA_PORT}
- GRAFANA_PORT=${GRAFANA_PORT}
- REDIS_INSIGHT_PORT=${REDIS_INSIGHT_PORT}
- FRONTEND_PORT=${FRONTEND_PORT:-3000}
- BACKEND_PORT=${BACKEND_PORT:-5000}
- PMA_PORT=${PMA_PORT:-8080}
- GRAFANA_PORT=${GRAFANA_PORT:-3001}
- REDIS_INSIGHT_PORT=${REDIS_INSIGHT_PORT:-5540}
# Redis Insight authentication
- REDIS_INSIGHT_USER=${REDIS_INSIGHT_USER}
- REDIS_INSIGHT_PASSWORD=${REDIS_INSIGHT_PASSWORD}
- REDIS_INSIGHT_USER=${REDIS_INSIGHT_USER:-}
- REDIS_INSIGHT_PASSWORD=${REDIS_INSIGHT_PASSWORD:-}
entrypoint: ["/docker-entrypoint.sh"]
ports:
- "${FRONTEND_PORT}:${FRONTEND_PORT}"
- "${BACKEND_PORT}:${BACKEND_PORT}"
- "${PMA_PORT}:${PMA_PORT}"
- "${GRAFANA_PORT}:${GRAFANA_PORT}"
- "${REDIS_INSIGHT_PORT}:${REDIS_INSIGHT_PORT}"
- "${FRONTEND_PORT:-3000}:${FRONTEND_PORT:-3000}"
- "${BACKEND_PORT:-5000}:${BACKEND_PORT:-5000}"
- "${PMA_PORT:-8080}:${PMA_PORT:-8080}"
- "${GRAFANA_PORT:-3001}:${GRAFANA_PORT:-3001}"
- "${REDIS_INSIGHT_PORT:-5540}:${REDIS_INSIGHT_PORT:-5540}"
depends_on:
frontend:
condition: service_healthy
Expand All @@ -57,15 +57,15 @@ services:
- ./frontend:/app
environment:
- NODE_ENV=development
- TZ=${TIMEZONE}
- SITE_URL=${SITE_URL}
- VITE_SSL_ENABLE=${SSL_ENABLE}
- VITE_PROJECT_NAME=${PROJECT_NAME}
- VITE_PROJECT_VERSION=${PROJECT_VERSION}
- VITE_PROJECT_DESCRIPTION=${PROJECT_DESCRIPTION}
- TZ=${TIMEZONE:-UTC}
- SITE_URL=${SITE_URL:-http://localhost}
- VITE_SSL_ENABLE=${SSL_ENABLE:-false}
- VITE_PROJECT_NAME=${PROJECT_NAME:-docker-fullstack-template}
- VITE_PROJECT_VERSION=${PROJECT_VERSION:-1.0.0}
- VITE_PROJECT_DESCRIPTION=${PROJECT_DESCRIPTION:-Docker fullstack template}
# API settings
- VITE_API_HOST=${API_HOST}
- VITE_API_PORT=${API_PORT}
- VITE_API_HOST=${API_HOST:-localhost}
- VITE_API_PORT=${API_PORT:-5000}
command: ["sh", "./init-dev.sh"]
depends_on:
backend:
Expand All @@ -85,30 +85,30 @@ services:
volumes:
- ./backend:/app
environment:
- TZ=${TIMEZONE}
- TZ=${TIMEZONE:-UTC}
- DEBUG_MODE=true
- LOG_LEVEL=${LOG_LEVEL}
- SSL_ENABLE=${SSL_ENABLE}
- SECRET_KEY=${SECRET_KEY}
- PROJECT_NAME=${PROJECT_NAME}
- PROJECT_VERSION=${PROJECT_VERSION}
- PROJECT_DESCRIPTION=${PROJECT_DESCRIPTION}
- LOG_LEVEL=${LOG_LEVEL:-INFO}
- SSL_ENABLE=${SSL_ENABLE:-false}
- SECRET_KEY=${SECRET_KEY:-change-me}
- PROJECT_NAME=${PROJECT_NAME:-docker-fullstack-template}
- PROJECT_VERSION=${PROJECT_VERSION:-0.1.0}
- PROJECT_DESCRIPTION=${PROJECT_DESCRIPTION:-Docker fullstack template}
# CORS settings
- HOSTNAME=${HOSTNAME}
- BACKEND_PORT=${BACKEND_PORT}
- FRONTEND_PORT=${FRONTEND_PORT}
- HOSTNAME=${HOSTNAME:-localhost}
- BACKEND_PORT=${BACKEND_PORT:-5000}
- FRONTEND_PORT=${FRONTEND_PORT:-3000}
# Database settings
- DATABASE_URL=mysql+pymysql://${DB_USER}:${DB_PASSWORD}@mariadb/${DB_DATABASE}
- DATABASE_URL_TEST=mysql+pymysql://${DB_USER}:${DB_PASSWORD}@mariadb/test_${DB_DATABASE}
- DB_POOL_SIZE=${DB_POOL_SIZE}
- DB_POOL_TIMEOUT=${DB_POOL_TIMEOUT}
- DB_POOL_RECYCLE=${DB_POOL_RECYCLE}
- DB_MAX_OVERFLOW=${DB_MAX_OVERFLOW}
- DB_CONNECT_TIMEOUT=${DB_CONNECT_TIMEOUT}
- DB_READ_TIMEOUT=${DB_READ_TIMEOUT}
- DB_WRITE_TIMEOUT=${DB_WRITE_TIMEOUT}
- DATABASE_URL=mysql+pymysql://${DB_USER:-app}:${DB_PASSWORD:-app}@mariadb/${DB_DATABASE:-app}
- DATABASE_URL_TEST=mysql+pymysql://${DB_USER:-app}:${DB_PASSWORD:-app}@mariadb/test_${DB_DATABASE:-app}
- DB_POOL_SIZE=${DB_POOL_SIZE:-10}
- DB_POOL_TIMEOUT=${DB_POOL_TIMEOUT:-30}
- DB_POOL_RECYCLE=${DB_POOL_RECYCLE:-3600}
- DB_MAX_OVERFLOW=${DB_MAX_OVERFLOW:-20}
- DB_CONNECT_TIMEOUT=${DB_CONNECT_TIMEOUT:-10}
- DB_READ_TIMEOUT=${DB_READ_TIMEOUT:-30}
- DB_WRITE_TIMEOUT=${DB_WRITE_TIMEOUT:-30}
# Redis settings
- REDIS_URL=redis://:${REDIS_PASSWORD}@redis:6379/0
- REDIS_URL=redis://:${REDIS_PASSWORD:-redis}@redis:6379/0
command: ["sh", "./init-dev.sh"]
depends_on:
mariadb:
Expand All @@ -127,11 +127,11 @@ services:
mariadb:
image: mariadb:11.3
environment:
- TZ=${TIMEZONE}
- MYSQL_DATABASE=${DB_DATABASE}
- MYSQL_USER=${DB_USER}
- MYSQL_PASSWORD=${DB_PASSWORD}
- MYSQL_ROOT_PASSWORD=${DB_ROOT_PASSWORD}
- TZ=${TIMEZONE:-UTC}
- MYSQL_DATABASE=${DB_DATABASE:-app}
- MYSQL_USER=${DB_USER:-app}
- MYSQL_PASSWORD=${DB_PASSWORD:-app}
- MYSQL_ROOT_PASSWORD=${DB_ROOT_PASSWORD:-root}
volumes:
- db-data:/var/lib/mysql
- ./db/custom.cnf:/etc/mysql/conf.d/custom.cnf
Expand All @@ -149,10 +149,10 @@ services:
phpmyadmin:
image: phpmyadmin/phpmyadmin:5.2.2
environment:
- TZ=${TIMEZONE}
- TZ=${TIMEZONE:-UTC}
- PMA_HOST=mariadb
- PMA_USER=root
- PMA_PASSWORD=${DB_ROOT_PASSWORD}
- PMA_PASSWORD=${DB_ROOT_PASSWORD:-root}
volumes:
- ./phpmyadmin/config.user.inc.php:/etc/phpmyadmin/config.user.inc.php
depends_on:
Expand All @@ -165,8 +165,8 @@ services:
redis:
image: redis:8.4.0
environment:
- TZ=${TIMEZONE}
- REDIS_PASSWORD=${REDIS_PASSWORD}
- TZ=${TIMEZONE:-UTC}
- REDIS_PASSWORD=${REDIS_PASSWORD:-redis}
volumes:
- redis-data:/data
- ./redis/redis.conf:/usr/local/etc/redis/redis.conf
Expand All @@ -180,7 +180,7 @@ services:
- backend-network
restart: always
healthcheck:
test: ["CMD-SHELL", "redis-cli -a ${REDIS_PASSWORD} ping | grep -q PONG"]
test: ["CMD-SHELL", "redis-cli -a ${REDIS_PASSWORD:-redis} ping | grep -q PONG"]
start_period: 30s
interval: 10s
timeout: 5s
Expand All @@ -189,12 +189,12 @@ services:
redis-insight:
image: redis/redisinsight:2.70
environment:
- TZ=${TIMEZONE}
- TZ=${TIMEZONE:-UTC}
- RI_REDIS_HOST=redis
- RI_REDIS_PORT=6379
- RI_REDIS_ALIAS=${PROJECT_NAME}
- RI_REDIS_ALIAS=${PROJECT_NAME:-docker-fullstack-template}
- RI_REDIS_USERNAME=default
- RI_REDIS_PASSWORD=${REDIS_PASSWORD}
- RI_REDIS_PASSWORD=${REDIS_PASSWORD:-redis}
volumes:
- redis-insight-data:/data
depends_on:
Expand All @@ -213,7 +213,7 @@ services:
loki:
image: grafana/loki:3.5.3
environment:
- TZ=${TIMEZONE}
- TZ=${TIMEZONE:-UTC}
volumes:
- loki-data:/loki
- loki-wal-data:/wal
Expand All @@ -236,7 +236,7 @@ services:
alloy:
image: grafana/alloy:v1.10.0
environment:
- TZ=${TIMEZONE}
- TZ=${TIMEZONE:-UTC}
volumes:
- alloy-data:/data
- ./backend/logs:/var/log/backend
Expand All @@ -252,12 +252,12 @@ services:
grafana:
image: grafana/grafana:12.2.0-16557133545
environment:
- TZ=${TIMEZONE}
- SSL_ENABLE=${SSL_ENABLE}
- GRAFANA_HOST=${GRAFANA_HOST}
- GRAFANA_PORT=${GRAFANA_PORT}
- GF_SECURITY_ADMIN_USER=${GRAFANA_USER}
- GF_SECURITY_ADMIN_PASSWORD=${GRAFANA_PASSWORD}
- TZ=${TIMEZONE:-UTC}
- SSL_ENABLE=${SSL_ENABLE:-false}
- GRAFANA_HOST=${GRAFANA_HOST:-localhost}
- GRAFANA_PORT=${GRAFANA_PORT:-3001}
- GF_SECURITY_ADMIN_USER=${GRAFANA_USER:-admin}
- GF_SECURITY_ADMIN_PASSWORD=${GRAFANA_PASSWORD:-admin}
- GF_PANELS_DISABLE_SANITIZE_HTML=true
- GF_PLUGINS_ALLOW_LOADING_UNSIGNED_PLUGINS=*
- GF_USERS_ALLOW_SIGN_UP=false
Expand Down
3 changes: 0 additions & 3 deletions nginx/.gitignore
Original file line number Diff line number Diff line change
@@ -1,6 +1,3 @@
# Whitelist
whitelist.conf

# SSL
*.pem
*.key
Expand Down
2 changes: 1 addition & 1 deletion nginx/nginx.conf
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ http {

# IP whitelist configuration
geo $allowed {
default 0; # 0 - blocked, 1 - allowed
default 1; # 0 - blocked, 1 - allowed
include /etc/nginx/whitelist.conf;
}

Expand Down
20 changes: 20 additions & 0 deletions nginx/whitelist.conf
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
# IP whitelist for `geo $allowed`
#
# Default behavior:
# - `nginx.conf` uses `default 1;` => allow all requests
#
# Enable whitelist mode:
# - Change `nginx.conf` to `default 0;`
# - Then uncomment/add allowed IPs/subnets below (use `1;` to allow)
#
# Examples:
# - Allow localhost
# 127.0.0.1/32 1;
#
# - Allow private networks
# 10.0.0.0/8 1;
# 172.16.0.0/12 1;
# 192.168.0.0/16 1;
#
# - Optional
# 100.64.0.0/10 1;
7 changes: 0 additions & 7 deletions nginx/whitelist.conf.example

This file was deleted.