Deployment guide

BHIMA

Overview

BHIMA (Basic Hospital Information Management Application) is an open-source hospital information system built for health facilities in low-resource settings. It pairs a full double-entry accounting ledger with the daily operations of a clinic or hospital: patient registration and billing, debtors and cash management, medical stock and inventory across depots, employees and payroll, and the financial and operational reports that a facility needs.

This SecureAnyCloud image installs BHIMA 1.39 from the official upstream release alongside Node.js 24 LTS, MySQL 8 and Redis. nginx reverse-proxies the stack, and all components are wired together for predictable single-VM behaviour.

What you get:

  • BHIMA 1.39.0 (the official upstream release build) at /opt/bhima/bin, run by the bhima system user
  • Node.js 24 LTS from NodeSource
  • MySQL 8 from Ubuntu 24.04 main, tuned with BHIMA's required sql_mode (STRICT_ALL_TABLES,NO_UNSIGNED_SUBTRACTION)
  • Redis from Ubuntu 24.04 main as the express-session store
  • nginx reverse-proxying TCP 80 to the app on 127.0.0.1:8080
  • bhima.service (Node app) and bhima-firstboot.service (one-shot per-VM credential rotation)
  • A populated demonstration dataset (Test Enterprise, chart of accounts, patients and posted transactions), so every module has content on first boot
  • Per-VM admin, database and session secrets generated at first boot. The upstream superuser/superuser demo login is rejected
  • 24/7 SecureAnyCloud support

Prerequisites

You need an active Azure subscription, an SSH key, and a VNet with a subnet.

Configure a network security group (NSG) that exposes TCP 22 to your management CIDR and TCP 80 to your users. You can instead expose TCP 80 to your CDN, Front Door or Application Gateway, with TLS terminated upstream.

Standard_B2s (2 vCPU, 4 GB RAM) is comfortable for a single-facility deployment. For busy multi-department hospitals, choose a D-series VM.

1

Deploy from the SecureAnyCloud gallery

In the Azure Portal, create a new VM from sacGallery/bhima-ubuntu-24-04. Choose Standard_B2s, attach your SSH key, and place the VM in a subnet whose NSG allows inbound TCP 22 (SSH) and TCP 80 (HTTP).

Wait for provisioning to finish, then copy the public IP address from the VM Overview blade.

2

SSH to the VM

ssh azureuser@<vm-ip>
3

Confirm the stack is running

systemctl is-active bhima.service mysql.service redis-server.service nginx.service node --version ss -ltn | grep -E ':(80|8080|3306|6379) ' curl -sI http://127.0.0.1/ | head -4

Expected output:

active active active active v24.19.0 LISTEN 0 511 0.0.0.0:80 0.0.0.0:* LISTEN 0 151 127.0.0.1:3306 0.0.0.0:* LISTEN 0 511 127.0.0.1:6379 0.0.0.0:* LISTEN 0 511 *:8080 *:* HTTP/1.1 200 OK Server: nginx/1.24.0 (Ubuntu)

Port 80 is nginx (public). Port 8080 is the BHIMA Node process. Port 3306 is MySQL and port 6379 is Redis, and both are bound to localhost.

4

Explore the demonstration dataset

The image ships a populated demonstration dataset, so you can explore every module immediately. Confirm the row counts:

RP=$(sudo grep '^MYSQL_ROOT_PASSWORD=' /stage/scripts/bhima-credentials.log | cut -d= -f2-) sudo mysql -uroot -p"$RP" bhima -N -e "SELECT 'enterprises', COUNT(*) FROM enterprise UNION ALL SELECT 'projects', COUNT(*) FROM project UNION ALL SELECT 'users', COUNT(*) FROM user UNION ALL SELECT 'accounts', COUNT(*) FROM account UNION ALL SELECT 'patients', COUNT(*) FROM patient UNION ALL SELECT 'journal rows', COUNT(*) FROM posting_journal;"

Expected output:

enterprises 1 projects 3 users 4 accounts 307 patients 265 journal rows 52
5

Read the per-VM credentials

Each VM generates its own admin, database and session secrets at first boot and writes them to a root-only file. Read the file:

sudo cat /stage/scripts/bhima-credentials.log

The file is mode 0600 and owned by root. It contains BHIMA_ADMIN_USERNAME / BHIMA_ADMIN_PASSWORD (the application administrator), BHIMA_DB_PASSWORD, MYSQL_ROOT_PASSWORD and the URL for this VM. Copy these values into your secrets manager and keep the file off the VM.

6

Verify the credential rotation

The image is hardened so that no two VMs share a login. The per-VM superuser password authenticates, and the upstream superuser/superuser demo default is rejected. Run the check:

AP=$(sudo grep '^BHIMA_ADMIN_PASSWORD=' /stage/scripts/bhima-credentials.log | cut -d= -f2-)
curl -s -o /dev/null -w 'per-VM password -> HTTP %{http_code}\n' -X POST \
  -H 'Content-Type: application/json' \
  --data "{\"username\":\"superuser\",\"password\":\"$AP\",\"project\":1}" http://127.0.0.1/auth/login
curl -s -o /dev/null -w 'upstream default -> HTTP %{http_code}\n' -X POST \
  -H 'Content-Type: application/json' \
  --data '{"username":"superuser","password":"superuser","project":1}' http://127.0.0.1/auth/login

Expected output:

per-VM password -> HTTP 200 upstream default -> HTTP 401
7

Sign in

Browse to http://<vm-ip>/ from your laptop. BHIMA shows its sign-in form. Enter the username superuser and the BHIMA_ADMIN_PASSWORD from Step 5, then choose the project Test Project A. To switch between English and French, use the language dropdown at the top of the form.

8

The enterprise dashboard

After you sign in, BHIMA opens the enterprise dashboard. It shows the active project, the enterprise currency and exchange rates, and the current fiscal year.

9

Chart of accounts

Open Finance > Account Management to see the chart of accounts that ships with the demonstration dataset. It is a structured, multi-level account tree that you can edit, extend or replace with your own.

10

The posting journal

Open Finance > Journal to see BHIMA's double-entry accounting in action. Every transaction is recorded with matching debit and credit lines against real accounts, and the journal totals balance.

11

Components

Component Path

BHIMA app /opt/bhima/bin/

App version file /opt/bhima/package.json

Runtime config /opt/bhima/bin/.env

Node.js 24 LTS /usr/bin/node

systemd unit (app) /etc/systemd/system/bhima.service

systemd unit (firstboot) /etc/systemd/system/bhima-firstboot.service

Firstboot script /usr/local/sbin/bhima-firstboot.sh

Firstboot sentinel /var/lib/sac/data/bhima-firstboot.done

MySQL config /etc/mysql/mysql.conf.d/zz-bhima.cnf

MySQL data /var/lib/mysql/

nginx site /etc/nginx/sites-enabled/bhima-sac

Credentials /stage/scripts/bhima-credentials.log (mode 0600 root:root)

12

Production hardening

  • Front the VM with TLS. Terminate HTTPS at Azure Application Gateway or Front Door, or run certbot --nginx on the VM after you point your DNS at the public IP address.
  • Replace the demonstration dataset. The shipped Test Enterprise data is for evaluation. When you are ready to run a real facility, create your own enterprise, fiscal year and chart of accounts inside BHIMA. The upstream documentation at https://docs.bhi.ma explains how to start a clean production database.
  • Rotate or add users. Sign in as superuser, then create your own named administrator and staff accounts under Administration > Users and disable the demo accounts.
  • Back up MySQL. Schedule mysqldump bhima and copy /opt/bhima/bin/client/upload to Azure Blob Storage or AWS S3.
  • Restrict the NSG. Lock TCP 22 to your management CIDR, and front TCP 80/443 with your CDN only.
  • Patch monthly. Run sudo apt-get update && sudo apt-get -y upgrade && sudo reboot. Watch https://github.com/Third-Culture-Software/bhima/releases for BHIMA releases.

Licensing

BHIMA is licensed under the GNU General Public License v2.0 (GPL-2.0) and is free to use. SecureAnyCloud provides commercial support separately. Contact sales@secureanycloud.com.

Deploy on Azure

Launch BHIMA 1.39 on Ubuntu 24.04 LTS on Azure with 24/7 support from SecureAnyCloud.

View this image

Need Help?

Our support team is available 24/7.

sales@secureanycloud.com

Deploy on Azure