Skip to content

Commit 848485a

Browse files
committed
Refactor environment configuration and enhance NGINX setup for Keycloak integration
1 parent a92dbca commit 848485a

File tree

10 files changed

+151
-54
lines changed

10 files changed

+151
-54
lines changed

.env.example

Lines changed: 4 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -5,42 +5,8 @@ COMPOSE_PROJECT_NAME=people
55
ENVIRONMENT=production
66

77
# ----------------------------------------------------------------------------
8-
# API DB
8+
# POSTGRES ADMIN
9+
# For compose file variable substitution like ${POSTGRES_USER} and ${POSTGRES_DB}
910
# ----------------------------------------------------------------------------
10-
POSTGRES_DB=people
11-
POSTGRES_USER=postgres
12-
POSTGRES_PASSWORD_FILE=/run/secrets/db-password
13-
PGDATA=/var/lib/postgresql/data/pgdata
14-
POSTGRES_INITDB_ARGS=--encoding=UTF-8 --lc-collate=C --lc-ctype=C
15-
16-
# ----------------------------------------------------------------------------
17-
# KEYCLOAK ADMIN (Web UI credentials)
18-
# ----------------------------------------------------------------------------
19-
KC_DB=postgres
20-
KC_DB_URL=jdbc:postgresql://db:5432/keycloak
21-
KC_DB_USERNAME=keycloak
22-
KC_DB_PASSWORD=keycloak
23-
KC_HOSTNAME=keycloak.example.com
24-
KC_PROXY_HEADERS=xforwarded
25-
KC_BOOTSTRAP_ADMIN_USERNAME=username
26-
KC_BOOTSTRAP_ADMIN_PASSWORD=password
27-
KC_HEALTH_ENABLED=true
28-
KC_METRICS_ENABLED=true
29-
30-
# ----------------------------------------------------------------------------
31-
# SPRING
32-
# ----------------------------------------------------------------------------
33-
SPRING_PROFILES_ACTIVE=docker
34-
SPRING_DATASOURCE_URL=jdbc:postgresql://db:5432/people
35-
SPRING_DATASOURCE_USERNAME=username
36-
SPRING_DATASOURCE_PASSWORD=password
37-
#JAVA_OPTS="-XX:+UseG1GC -Xms256m -Xmx512m"
38-
JAVA_OPTS="-XX:+UseG1GC -XX:MaxRAMPercentage=75"
39-
KEYCLOAK_ISSUER_URI=http://keycloak.example.com/realms/people-realm
40-
KEYCLOAK_JWK_SET_URI=http://keycloak.example.com/realms/people-realm/protocol/openid-connect/certs
41-
42-
# ----------------------------------------------------------------------------
43-
# NGINX
44-
# ----------------------------------------------------------------------------
45-
NGINX_PORT=80
46-
NGINX_SSL_PORT=443
11+
POSTGRES_DB=postgres
12+
POSTGRES_USER=postgres

.gitignore

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,8 +34,13 @@ build/
3434

3535
### Docker ###
3636
.env
37+
.env.api
38+
.env.db
39+
.env.keycloak
40+
.env.nginx
3741
secrets/*.txt
3842

43+
3944
### Kubernetes ###
4045
values.y*ml
4146
secret.y*ml

compose.yaml

Lines changed: 35 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -138,6 +138,22 @@ volumes:
138138
labels:
139139
description: "Spring Boot application logs"
140140

141+
# Volume for Keycloak data (build configuration and cache)
142+
keycloak-conf:
143+
driver: local
144+
labels:
145+
description: "Keycloak build configuration"
146+
backup: "recommended"
147+
critical: "false"
148+
149+
# Volume for Keycloak runtime data (cache, temporary files)
150+
keycloak-lib:
151+
driver: local
152+
labels:
153+
description: "Keycloak runtime data"
154+
backup: "recommended"
155+
critical: "false"
156+
141157
# ============================================================================
142158
# SECRETS
143159
# ============================================================================
@@ -170,7 +186,7 @@ services:
170186
nginx:
171187
image: nginx:1.29-alpine
172188
container_name: nginx
173-
189+
174190
# Drop all capabilities (principle of least privilege)
175191
cap_drop:
176192
- ALL
@@ -184,6 +200,9 @@ services:
184200
security_opt:
185201
- no-new-privileges:true # Prevent escalation
186202

203+
env_file:
204+
- env_files/.env.nginx
205+
187206
# Restart policy
188207
restart: unless-stopped
189208

@@ -268,6 +287,9 @@ services:
268287
networks:
269288
- backend
270289

290+
extra_hosts:
291+
- "mcqueide.local:172.21.0.1"
292+
271293
# Ports: DO NOT expose externally in production
272294
# ports:
273295
# - "8081:8080" # ❌ For debug only, remove in production
@@ -276,9 +298,8 @@ services:
276298
expose:
277299
- "8080"
278300

279-
# Not required, docker uses .env by default
280301
env_file:
281-
- .env
302+
- env_files/.env.api
282303

283304
secrets:
284305
- api-db-password
@@ -383,7 +404,7 @@ services:
383404

384405
# Not required, docker uses .env by default
385406
env_file:
386-
- .env
407+
- env_files/.env.db
387408

388409
# OPTIMIZATION: Use tmpfs for temporary data (improves performance)
389410
# Sockets and temp files don't require persistence
@@ -393,7 +414,7 @@ services:
393414

394415
# Healthcheck
395416
healthcheck:
396-
test: [ "CMD-SHELL", "pg_isready -U ${POSTGRES_USER} -d ${POSTGRES_DB}" ]
417+
test: [ "CMD-SHELL", "pg_isready -U ${POSTGRES_USER:-postgres} -d ${POSTGRES_DB:-postgres}" ]
397418
interval: 10s
398419
timeout: 5s
399420
retries: 5
@@ -455,11 +476,15 @@ services:
455476
- keycloak-admin-password
456477

457478
env_file:
458-
- .env
479+
- env_files/.env.keycloak
459480

460481
volumes:
482+
- keycloak-conf:/opt/keycloak/conf
483+
- keycloak-lib:/opt/keycloak/lib/quarkus/
461484
- ./keycloak/export:/opt/keycloak/data/import
462485

486+
# NOTE: Use 'start' for production (builds automatically on first run)
487+
# After first successful build, you can optionally use 'start --optimized' for faster restarts
463488
command: start-dev
464489

465490
# Run import
@@ -470,7 +495,7 @@ services:
470495
condition: service_healthy
471496

472497
healthcheck:
473-
test: ["CMD-SHELL", "exec 3<>/dev/tcp/keycloak/9000 && echo -e 'GET /health/ready HTTP/1.1\r\nHost: keycloak\r\nConnection: close\r\n\r\n' >&3 && cat <&3 | grep -q '200 OK'"]
498+
test: ["CMD-SHELL", "exec 3<>/dev/tcp/keycloak/9000 && echo -e 'GET /auth/health/ready HTTP/1.1\r\nHost: keycloak\r\nConnection: close\r\n\r\n' >&3 && cat <&3 | grep -q '200 OK'"]
474499
interval: 30s
475500
timeout: 10s
476501
retries: 5
@@ -480,10 +505,10 @@ services:
480505
resources:
481506
limits:
482507
cpus: '0.5'
483-
memory: 512M
508+
memory: 768M
484509
reservations:
485510
cpus: '0.25'
486-
memory: 256M
511+
memory: 512M
487512

488513
logging:
489514
driver: "json-file"
@@ -513,7 +538,7 @@ services:
513538
- keycloak-admin-password
514539

515540
env_file:
516-
- .env
541+
- env_files/.env.keycloak
517542

518543
volumes:
519544
- ./keycloak/export:/opt/keycloak/data/import:rw
@@ -543,10 +568,6 @@ services:
543568
# Deploy with minimal downtime:
544569
# docker compose up -d --no-deps --build app
545570
#
546-
# Check service health:
547-
# docker compose ps
548-
# docker compose exec app node healthcheck.js
549-
#
550571
# Logs:
551572
# docker compose logs -f app
552573
# docker compose logs --tail=100 postgres

env_files/.env.api.example

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
# ----------------------------------------------------------------------------
2+
# SPRING
3+
# ----------------------------------------------------------------------------
4+
SPRING_PROFILES_ACTIVE=docker
5+
SPRING_DATASOURCE_URL=jdbc:postgresql://db:5432/people
6+
SPRING_DATASOURCE_USERNAME=people
7+
SPRING_DATASOURCE_PASSWORD=people
8+
#JAVA_OPTS="-XX:+UseG1GC -Xms256m -Xmx512m"
9+
JAVA_OPTS="-XX:+UseG1GC -XX:MaxRAMPercentage=75"
10+
CORS_ALLOWED_ORIGINS=http://localhost:3000,http://localhost:4200,http://app:3000,http://keycloak:8080
11+
CORS_ALLOWCREDENTIALS=true
12+
KEYCLOAK_ISSUER_URI=http://keycloak:8080/auth/realms/people-realm
13+
KEYCLOAK_CLIENT_SECRET= # Empty for public client with PKCE

env_files/.env.db.example

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
# ----------------------------------------------------------------------------
2+
# POSTGRES ADMIN
3+
# ----------------------------------------------------------------------------
4+
POSTGRES_DB=postgres
5+
POSTGRES_USER=postgres
6+
POSTGRES_PASSWORD_FILE=/run/secrets/db-password

env_files/.env.keycloak.example

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
# ----------------------------------------------------------------------------
2+
# KEYCLOAK ADMIN (Web UI credentials)
3+
# ----------------------------------------------------------------------------
4+
KC_DB=postgres
5+
KC_DB_URL=jdbc:postgresql://db:5432/keycloak
6+
KC_DB_USERNAME=keycloak
7+
KC_DB_PASSWORD=keycloak
8+
KC_HOSTNAME=keycloak
9+
#KC_HOSTNAME=localhost # If Keycloak is accessed only locally
10+
# KC_PROXY=edge # Deprecated
11+
KC_PROXY_HEADERS=xforwarded
12+
KC_HOSTNAME_STRICT=false # To allow access via HTTP instead of HTTPS, not recommended for production.
13+
KC_HTTP_ENABLED=true
14+
KC_BOOTSTRAP_ADMIN_USERNAME=admin
15+
KC_BOOTSTRAP_ADMIN_PASSWORD=admin
16+
KC_HEALTH_ENABLED=true
17+
KC_METRICS_ENABLED=true
18+
KC_LOG_LEVEL=info
19+
KC_HTTP_RELATIVE_PATH=/auth

env_files/.env.nginx.example

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
# ----------------------------------------------------------------------------
2+
# NGINX
3+
# ----------------------------------------------------------------------------
4+
NGINX_PORT=80
5+
NGINX_SSL_PORT=443

nginx/conf.d/default.conf

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,9 +32,58 @@ server {
3232
add_header Content-Type text/plain;
3333
}
3434

35+
# ========================================================================
36+
# KEYCLOAK - Identity and Access Management
37+
# ========================================================================
38+
location ^~ /auth/ {
39+
limit_req zone=general burst=30 nodelay;
40+
limit_conn addr 15;
41+
42+
proxy_pass http://keycloak;
43+
proxy_http_version 1.1;
44+
45+
# Essential headers for Keycloak behind reverse proxy
46+
proxy_set_header Host $host;
47+
proxy_set_header X-Real-IP $remote_addr;
48+
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
49+
proxy_set_header X-Forwarded-Proto $scheme;
50+
proxy_set_header X-Forwarded-Host $host;
51+
proxy_set_header X-Forwarded-Port $server_port;
52+
53+
# Buffer settings for Keycloak admin console
54+
proxy_buffering on;
55+
proxy_buffer_size 8k;
56+
proxy_buffers 8 8k;
57+
58+
# Timeouts (Keycloak can be slow on first start)
59+
proxy_connect_timeout 60s;
60+
proxy_send_timeout 60s;
61+
proxy_read_timeout 60s;
62+
63+
proxy_set_header Connection "";
64+
}
65+
3566
# ========================================================================
3667
# BACKEND API ROUTES
3768
# ========================================================================
69+
location /swagger-ui.html {
70+
limit_req zone=general burst=20 nodelay;
71+
limit_conn addr 10;
72+
73+
proxy_pass http://backend;
74+
proxy_http_version 1.1;
75+
76+
proxy_set_header Host $host;
77+
proxy_set_header X-Real-IP $remote_addr;
78+
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
79+
proxy_set_header X-Forwarded-Proto $scheme;
80+
81+
proxy_connect_timeout 30s;
82+
proxy_send_timeout 30s;
83+
proxy_read_timeout 30s;
84+
proxy_set_header Connection "";
85+
}
86+
3887
location /swagger-ui/ {
3988
limit_req zone=general burst=20 nodelay;
4089
limit_conn addr 10;

nginx/nginx.conf

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,19 @@ http {
9797
keepalive_timeout 60s;
9898
}
9999

100+
# ========================================================================
101+
# UPSTREAM - Keycloak
102+
# ========================================================================
103+
upstream keycloak {
104+
least_conn;
105+
106+
server keycloak:8080 max_fails=3 fail_timeout=30s weight=1;
107+
108+
keepalive 32;
109+
keepalive_requests 100;
110+
keepalive_timeout 60s;
111+
}
112+
100113
# ========================================================================
101114
# UPSTREAM - Frontend App (Node.js)
102115
# ========================================================================

src/main/resources/application.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,7 @@ spring:
4343
jwk-set-uri: ${issuer-uri}/protocol/openid-connect/certs
4444
user-name-attribute: preferred_username
4545

46-
issuer-uri: ${KEYCLOAK_ISSUER_URI:http://localhost:8080/realms/people-realm}
46+
issuer-uri: ${KEYCLOAK_ISSUER_URI:http://localhost:8080/auth/realms/people-realm}
4747

4848
# CORS Configuration
4949
cors:
@@ -94,4 +94,4 @@ spring:
9494
server:
9595
port: 8080
9696

97-
issuer-uri: ${KEYCLOAK_ISSUER_URI:http://keycloak:8080/realms/people-realm}
97+
issuer-uri: ${KEYCLOAK_ISSUER_URI:http://keycloak:8080/auth/realms/people-realm}

0 commit comments

Comments
 (0)