Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add proof-of-concept high availability cluster config #28

Draft
wants to merge 6 commits into
base: master
Choose a base branch
from
Draft
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
3 changes: 3 additions & 0 deletions cluster-ha/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
.apps
config/DHIS2_home/files
config/DHIS2_home/logs
3 changes: 3 additions & 0 deletions cluster-ha/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# Clustered DHIS2 server

This Docker Compose configuration which presents a proof-of-concept high-availability configuration using 3x DHIS2 tomcat containers and a redis instance for sharing state. See [the DHIS2 cluster docs](https://docs.dhis2.org/en/manage/performing-system-administration/dhis-core-version-239/installation.html?h=cluster+2.39#install_cluster_configuration_introduction) for more info.
24 changes: 24 additions & 0 deletions cluster-ha/config/DHIS2_home/dhis.conf
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
connection.dialect = org.hibernate.dialect.PostgreSQLDialect
connection.driver_class = org.postgresql.Driver
connection.url = jdbc:postgresql://db/dhis2
connection.username = dhis
connection.password = dhis
# Database schema behavior, can be validate, update, create, create-drop
connection.schema = update

encryption.password = xxxx
metadata.audit.persist = on

# URLs for specifying a custom app hub, these are the defaults
#apphub.base.url = https://apps.dhis2.org
#apphub.api.url = https://apps.dhis2.org/api

redis.enabled = on
redis.host = redis
redis.port = 6379
# redis.password = <your password>
redis.use.ssl = false
redis.cache.invalidation.enabled = on

# Optional, defaults to 2 minutes
# leader.time.to.live.minutes=4
50 changes: 50 additions & 0 deletions cluster-ha/config/nginx.conf
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
worker_processes 1;

events {
worker_connections 1024;
}

http {
upstream core {
server core:8080 max_fails=3 fail_timeout=60s;
}

gzip on; # Enables compression, incl Web API content-types
gzip_types
"application/json;charset=utf-8" application/json
"application/javascript;charset=utf-8" application/javascript text/javascript
"application/xml;charset=utf-8" application/xml text/xml
"text/css;charset=utf-8" text/css
"text/plain;charset=utf-8" text/plain;

server {
listen 80;
port_in_redirect off;

root /data/apps;

client_max_body_size 25m;

# Redirect required to prevent 403 error on / access
rewrite ^/$ $scheme://$http_host/dhis-web-dashboard redirect;

location / {
include mime.types;
try_files $uri $uri/ $uri/index.html @core;
}

# location /screenshot {
# proxy_set_header Host $http_host;
# proxy_set_header X-Real-IP $remote_addr;
# proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
# proxy_pass http://screenshot:9000;
# }

location @core {
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_pass http://core;
}
}
}
54 changes: 54 additions & 0 deletions cluster-ha/config/server.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
<?xml version="1.0" encoding="UTF-8"?>
<Server shutdown="-1">
<Listener className="org.apache.catalina.startup.VersionLoggerListener" />
<Listener className="org.apache.catalina.core.AprLifecycleListener" SSLEngine="on" />
<Listener className="org.apache.catalina.core.JreMemoryLeakPreventionListener" />
<Listener className="org.apache.catalina.mbeans.GlobalResourcesLifecycleListener" />
<Listener className="org.apache.catalina.core.ThreadLocalLeakPreventionListener" />

<GlobalNamingResources>
<Resource
name="UserDatabase"
auth="Container"
type="org.apache.catalina.UserDatabase"
description="User database that can be updated and saved"
factory="org.apache.catalina.users.MemoryUserDatabaseFactory"
pathname="conf/tomcat-users.xml"
/>
</GlobalNamingResources>

<Service name="Catalina">
<Connector port="8080" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443"
URIEncoding="UTF-8"
relaxedQueryChars='\ { } | [ ]'
/>

<Engine name="Catalina" defaultHost="localhost">
<Realm className="org.apache.catalina.realm.LockOutRealm">
<Realm
className="org.apache.catalina.realm.UserDatabaseRealm"
resourceName="UserDatabase"
/>
</Realm>

<Host
name="localhost"
appBase="webapps"
unpackWARs="true"
autoDeploy="false"
deployOnStartup="false"
>
<Context path="${context.path}" docBase="ROOT/" />

<Valve
className="org.apache.catalina.valves.AccessLogValve"
directory="logs"
prefix="localhost_access_log" suffix=".txt"
pattern="%h %l %u %t &quot;%r&quot; %s %b"
/>
</Host>
</Engine>
</Service>
</Server>
42 changes: 42 additions & 0 deletions cluster-ha/docker-compose.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
version: '3'
services:
core:
image: "dhis2/core-dev:local-tons-final"
restart: always
volumes:
- ./config/DHIS2_home/dhis.conf:/DHIS2_home/dhis.conf
- ./config/server.xml:/usr/local/tomcat/conf/server.xml
- ./config/DHIS2_home:/DHIS2_home
environment:
DHIS2_HOME: /DHIS2_home
# CATALINA_OPTS: "-Dcontext.path='${DHIS2_CORE_CONTEXT_PATH:-}'"
depends_on:
- "db"
- "redis"
scale: 3
db:
image: "ghcr.io/baosystems/postgis:12-3.3"
restart: always
volumes:
- datadb:/var/lib/postgresql/data
environment:
POSTGRES_DB: dhis2
POSTGRES_USER: dhis
POSTGRES_PASSWORD: dhis

redis:
image: redis
restart: always

gateway:
image: "jwilder/nginx-proxy:alpine"
restart: always
ports:
- "8080:80"
volumes:
- ./config/nginx.conf:/etc/nginx/nginx.conf:ro
- ./.apps:/data/apps:ro
- /var/run/docker.sock:/tmp/docker.sock:ro
volumes:
datadb:
home: