Skip to content

Juro Core Banking — Administrator Guide

Purpose

This guide is for platform engineers, DevOps engineers, and system administrators responsible for deploying, configuring, and operating Juro Core Banking in any environment.

Use this guide together with:

  • README.md — quick-start reference and Docker/Kubernetes commands
  • docs/USER_MANUAL.md — system configuration for banking administrators
  • JURO_CORE_BANKING_PRODUCTION_FASTTRACK_PLAN.md — production readiness gates
  • JURO_CORE_BANKING_BLOCKER_BOARD.md — live blocker tracking

1. System Overview

Juro Core Banking is a Spring Boot Java application built on Juro Core Banking providing a REST API for all core banking operations. It is the backend for Juro X Web App (_push_jurox) and integrates with the Digitalia blockchain layer.

Key characteristics:

  • Self-contained Spring Boot JAR embedding a servlet container (no external Tomcat required)
  • Multi-tenant architecture: a jurocore_tenants database tracks tenant configurations; each tenant has its own schema
  • REST API on HTTPS port 8443 (default); authenticated via Basic Auth or OAuth2
  • Stateless application tier — all state is in the database
  • Supports MariaDB ≥ 12.2 or PostgreSQL ≥ 18.0
  • Java 21+ required

Runtime dependencies:

Dependency Purpose
MariaDB or PostgreSQL Tenant registry and all banking data
ActiveMQ or Kafka (optional) External business events and COB batch partitioning
Juro X Web App Browser-based UI; not required for API-only deployments

2. System Requirements

Resource Minimum
RAM 16 GB
CPU 8 cores
Database MariaDB ≥ 12.2 or PostgreSQL ≥ 18.0
Java 21+ (Azul Zulu recommended)
Disk Sufficient for database growth, logs, and document storage

For production: provision the database on a dedicated host or managed service with backups, replication, and monitoring separate from the application tier.


3. Deployment

3.1 Local development (quick start)

# Create required databases
./gradlew createDB -PdbName=jurocore_tenants
./gradlew createDB -PdbName=jurocore_default

# Build and run
./gradlew devRun

# Confirm health
curl --insecure https://localhost:8443/juro-core-provider/actuator/health
# Expected: {"status":"UP"}

3.2 JAR deployment

# Build
./gradlew clean bootJar
# Output: juro-core-provider/build/libs/juro-core-provider.jar

# Download JDBC driver (example: MariaDB)
wget https://dlm.mariadb.com/4174416/Connectors/java/connector-java-3.5.2/mariadb-java-client-3.5.2.jar

# Start (with JDBC driver on classpath)
export JUROCORE_HIKARI_PASSWORD=verysecret
# ... set all required env vars
java -Dloader.path=. -jar juro-core-provider/build/libs/juro-core-provider.jar

3.3 Docker Compose deployment

Multiple compose variants are provided. Choose based on database and message broker requirements:

File Use case
docker-compose.yml Default (MariaDB)
docker-compose-development.yml Development with Loki logging
docker-compose-postgresql.yml PostgreSQL backend
docker-compose-postgresql-activemq.yml PostgreSQL + ActiveMQ + batch workers

Standard startup:

# Install Loki log driver (once)
docker plugin install grafana/loki-docker-driver:latest \
  --alias loki --grant-all-permissions

# Start
docker compose -f docker-compose-development.yml up -d

# Confirm health (allow 60–90 seconds for startup)
curl --insecure https://localhost:8443/juro-core-provider/actuator/health
# Expected: {"status":"UP"}

Accept the self-signed SSL certificate in your browser at https://localhost:8443 the first time.

3.4 Kubernetes deployment

General cluster (GKE or equivalent):

git clone https://github.com/cosimoglobal/Juro.git
cd Juro/kubernetes
./kubectl-startup.sh

# Monitor pod readiness
kubectl get pods -w

# Tear down
./kubectl-shutdown.sh

Minikube (local):

cd kubernetes
minikube start
./kubectl-startup.sh
kubectl get pods -w

# Access web UI
minikube service mifos-community

# Direct API access
minikube service jurocore-server --url --https

Check logs:

kubectl logs deployment/jurocore-server
kubectl logs deployment/mifos-community

Shut down:

./kubectl-shutdown.sh

4. Configuration

Juro Core Banking is configured via environment variables. These are set in your Docker Compose env file, Kubernetes Secrets/ConfigMaps, or shell environment for JAR deployments.

4.1 Database connection

Variable Description
JUROCORE_HIKARI_DRIVER_SOURCE_CLASS_NAME JDBC driver class
JUROCORE_HIKARI_JDBC_URL JDBC URL for the tenants database
JUROCORE_HIKARI_USERNAME Database username
JUROCORE_HIKARI_PASSWORD Database password

Consult docker-compose.yml for the full set of HikariCP connection pool variables.

4.2 Tenant configuration

Juro Core Banking uses a two-database model:

  • jurocore_tenants — tenant registry; maps tenant IDs to connection details
  • fineract_<tenantname> — one schema per tenant containing all banking data

The default tenant schema is jurocore_default with tenant ID default. Additional tenants are registered in jurocore_tenants.

4.3 TLS / SSL

The development configuration uses a self-signed certificate. For production:

  1. Mount a valid TLS certificate and private key into the container.
  2. Configure Spring Boot's server.ssl.* properties.
  3. Remove the --insecure flag from all health check commands.

4.4 Docker file permissions

If containers fail with permission errors on startup:

id -u ${USER}
id -g ${GROUP}

Set the JUROCORE_USER and JUROCORE_GROUP variables in config/docker/env/jurocore-common.env to match. Do not commit these changes.

4.5 Message broker (optional)

For environments using ActiveMQ or Kafka for external business events or COB batch partitioning:

ActiveMQ:

JUROCORE_REMOTE_JOB_MESSAGE_HANDLER_JMS_ENABLED=true
JUROCORE_REMOTE_JOB_MESSAGE_HANDLER_SPRING_EVENTS_ENABLED=false
JUROCORE_REMOTE_JOB_MESSAGE_HANDLER_JMS_BROKER_URL=tcp://activemq:61616

Refer to docker-compose-postgresql-activemq.yml for the full multi-worker pattern with Manager + Worker Spring Batch nodes.

Kafka:

Refer to application.properties for supported Kafka configuration parameters and their defaults.


5. Health Checks and Monitoring

5.1 Actuator health endpoint

curl --insecure https://localhost:8443/juro-core-provider/actuator/health
# Expected: {"status":"UP"}

# Readiness probe (used in CI and Kubernetes)
curl --insecure https://localhost:8443/juro-core-provider/actuator/health/readiness
# Expected: {"status":"UP"}

5.2 Authenticated API probe

curl --location \
  https://localhost:8443/juro-core-provider/api/v1/clients \
  --header 'Jurocore-Platform-TenantId: default' \
  --header 'Authorization: Basic bWlmb3M6cGFzc3dvcmQ='
# Expected: HTTP 200 with client list JSON

The default Basic Auth value (bWlmb3M6cGFzc3dvcmQ=) decodes to mifos:password. Replace with production credentials.

5.3 Database connectivity

# MariaDB
docker exec <mariadb-container> mysqladmin -uroot -p"${DB_ROOT_PASSWORD}" status

# PostgreSQL
docker exec <postgres-container> pg_isready -U fineract

5.4 Log access

Environment Command
Docker Compose docker compose logs -f fineract
Kubernetes kubectl logs deployment/jurocore-server
JAR tail -f logs/fineract.log
Java Flight Recorder PROJECT_ROOT/build/fineract/logs/*.jfr (open with Azul Mission Control or IntelliJ)

6. Build and CI

6.1 Build JAR

./gradlew clean bootJar

6.2 Build WAR (Tomcat deployment)

./gradlew :juro-core-war:clean :juro-core-war:war

6.3 Run tests

# All tests
./gradlew test

# Integration tests
./gradlew integrationTest

# Skip tests during build
./gradlew clean bootJar -x test

6.4 Build Docker image (Jib)

./gradlew :juro-core-provider:jibDockerBuild -x test

6.5 CI triage checklist

When a CI workflow fails around Cargo/Tomcat startup:

  1. Check runtime preflightscripts/ci/preflight-jurocore-runtime.sh checks readiness endpoint, DB TCP reachability, and tenant-authenticated API access.
  2. Check pre-test baseline probe — confirms whether port 8443 was already bound before tests started (stale listener = previous failure leaked a process).
  3. Check fallback diagnostics — captured in the Fallback cargo diagnostics on failure workflow step: HTTPS readiness result, socket status for 8443, tail of **/build/cargo/*.log.
  4. Download workflow artifactsserver-logs-* (Cargo output) and test-results-* (per-module reports).

Typical patterns:

Symptom Likely cause
Port baseline busy + startup timeout Stale listener or leaked process in runner
Readiness fails, no listener on 8443 Startup failure before Tomcat bind
Readiness UP but tests fail Endpoint/bootstrap sequencing or test data issue

7. Updates and Image Management

7.1 Standard update (Docker)

docker pull cosimousa/juro-core-banking:latest
docker compose -f docker-compose.yml up -d --no-deps fineract

7.2 Versioned releases

Tag releases explicitly:

docker buildx build \
  --platform linux/amd64,linux/arm64 \
  -t cosimousa/juro-core-banking:vYYYYMMDD \
  -t cosimousa/juro-core-banking:latest \
  --push .

Record the deployed tag in the ops log. Do not rely solely on latest in production.

7.3 Schema migrations

Juro Core Banking manages database migrations automatically on startup using Flyway. After a code update:

  1. Pull or build the new image.
  2. Start the container; Flyway applies pending migrations automatically.
  3. Monitor startup logs for migration errors before routing traffic.
  4. If migration fails, do not retry blindly — review the Flyway output, consult the change log, and restore from backup if needed.

8. Incident Response

Application returns no response or connection refused

  1. Confirm the container or process is running.
  2. Confirm port 8443 is bound: ss -tlnp | grep 8443 or lsof -i :8443.
  3. Check startup logs for JVM errors or database connection failures.
  4. Run the actuator health check and compare to expected {"status":"UP"}.

Health endpoint returns {"status":"DOWN"} or non-200

  1. Check the database container is running and accepting connections.
  2. Check that jurocore_tenants and jurocore_default databases exist and are reachable.
  3. Review application logs for specific subsystem failures (DB, Redis, message broker).
  4. Restart the application container after confirming the dependency is healthy.

Startup failure: database not found

# Re-create databases if missing (development/staging only)
./gradlew createDB -PdbName=jurocore_tenants
./gradlew createDB -PdbName=jurocore_default

Do not drop and recreate databases in production without a backup and explicit change approval.

Flyway migration failure on startup

  1. Review the Flyway error message in application logs.
  2. Identify the failing migration script version.
  3. Do not delete or skip the migration without understanding the impact.
  4. Restore from a pre-migration backup if the migration is not recoverable.
  5. Escalate to the engineering team.

Performance degradation or slow API responses

  1. Check database query performance; COB batch jobs can impact query latency.
  2. Check JVM heap usage (Java Flight Recorder or Actuator /metrics).
  3. If COB jobs are running, monitor via the batch job status API.
  4. Consider enabling ActiveMQ or Kafka for COB partitioning in large deployments.

9. Rollback

  1. Identify the last-known-good image tag.
  2. Update the Compose or Kubernetes spec to use that tag.
  3. If the rollback crosses a schema migration boundary, restore the database from a pre-upgrade backup.
  4. Start the container.
  5. Verify the health endpoint and an authenticated API call.
  6. Record the rollback in the ops log.

10. Close of Business (COB) Operations

The COB job runs daily processing for all active loans and accounts.

  • COB is a Spring Batch job. In the default configuration it runs on a single node.
  • For large deployments, enable remote partitioning via ActiveMQ or Kafka so sub-tasks are distributed across multiple worker nodes.
  • Monitor COB progress via the batch job status API or application logs.
  • If COB is stuck or overrunning, check worker health, message broker connectivity, and database locks.

11. Security

  • Default credentials (mifos / password) must be changed before any non-local deployment.
  • Use HTTPS with a valid certificate in production; never expose the HTTP port publicly.
  • Rotate JUROCORE_HIKARI_PASSWORD and any application secrets on a regular schedule and after any exposure event.
  • Run Trivy or equivalent container and dependency scans before each production release.
  • Report new vulnerabilities privately to admin@juro.net.
  • For known upstream vulnerabilities, refer to Juro Core Banking Security Reports.

12. Documentation Map

  • README.md — quick-start commands and environment variable reference
  • docs/ADMINISTRATOR_GUIDE.md — this file
  • docs/USER_MANUAL.md — system configuration for banking administrators
  • JURO_CORE_BANKING_PRODUCTION_FASTTRACK_PLAN.md — production readiness plan
  • JURO_CORE_BANKING_BLOCKER_BOARD.md — active production blockers
  • PHASE_3_BOOTSTRAP_HARDENING.md — tenant and admin bootstrap hardening (in progress)
  • PHASE_2_DURABLE_STORAGE.md — document storage hardening (complete)
  • STATIC_WEAVING.md — JPA static weaving configuration
  • DOCUMENT_STORAGE_EXPLORATION.md — file storage backend reference