Deployment guide

Mirth Connect

Overview

Mirth Connect, now published as NextGen Connect, is the most widely deployed open source healthcare integration engine. It is an interface engine: you build channels that receive, filter, transform and route clinical messages between disparate systems. It speaks the languages of healthcare interoperability out of the box, including HL7 v2 and v3, FHIR, X12, DICOM, XML, JSON and delimited text. It can move those messages over MLLP, TCP, HTTP, file, database, SFTP and more.

This SecureAnyCloud image installs Mirth Connect 4.5.2 (MPL 2.0) on OpenJDK 17, running as a dedicated mirth service user under systemd. nginx terminates TLS in front of the Mirth web admin and REST API, so the admin surface is never exposed in the clear.

What you get:

  • Mirth Connect 4.5.2 build b363 (NextGen Connect, MPL 2.0), verified by sha256 at build time
  • An OpenJDK 17 headless JRE, running Mirth as the mirth system service (mcserver.service)
  • The Mirth web admin and REST API, which are HTTPS native and bound to 127.0.0.1:8443 (loopback only)
  • nginx terminating TLS on :443 with a per-VM self-signed certificate and reverse proxying to the loopback listener
  • Port 80 serving an unauthenticated /healthz endpoint and redirecting all other traffic to HTTPS
  • The default admin / admin login rotated to a unique per-VM password on the first boot of every VM, recorded in a root-only file. The image is verified to have the shipped default disabled before it ships
  • A dedicated Azure data disk at /var/lib/mirthconnect that holds the embedded Apache Derby database, the auto-generated keystore and the configuration map
  • mcserver.service and nginx.service as enabled, active systemd units
  • 24/7 SecureAnyCloud support

Prerequisites

You need an active Azure subscription, an SSH key pair, and a VNet with a subnet in the target region.

Standard_B2ms (2 vCPU / 8 GiB RAM) is a reasonable starting size. Size up for higher message throughput and more concurrent channels.

Configure the network security group (NSG) to allow inbound 22/tcp from your management network, and 80/tcp plus 443/tcp for the web admin and REST API.

Mirth channels open their own inbound listener ports, for example an HL7 MLLP listener on TCP 6661. These are defined per channel, so open only the specific ports your channels use (see Step 13).

The appliance ships a self-signed certificate. For production, put your own domain and a trusted certificate in front of it (see Maintenance).

Step 1 - Deploy from the Azure Marketplace

Sign in to the Azure Portal, choose Create a resource, search the Marketplace for Mirth Connect by SecureAnyCloud, and select Create.

On the Basics tab, pick your subscription, resource group, region and size. Under Administrator account, choose SSH public key and paste your key. Under Inbound port rules, allow SSH (22), HTTP (80) and HTTPS (443).

Review the dedicated data disk on the Disks tab, then select Review + create and Create.

Step 2 - Deploy from the Azure CLI

Accept the Marketplace terms once per subscription, create the VM, then open ports 80 and 443.

# Accept the Marketplace terms once per subscription (required before the first CLI deploy)
az vm image terms accept --urn sac1647283583153:mirth-connect-ubuntu-24-04:default:latest
az vm create \
  --resource-group <your-rg> \
  --name mirth-connect \
  --image sac1647283583153:mirth-connect-ubuntu-24-04:default:latest \
  --size Standard_B2ms \
  --admin-username azureuser \
  --ssh-key-values ~/.ssh/id_ed25519.pub \
  --vnet-name <your-vnet> --subnet <your-subnet> \
  --public-ip-sku Standard
az vm open-port --resource-group <your-rg> --name mirth-connect --port 80 --priority 1010
az vm open-port --resource-group <your-rg> --name mirth-connect --port 443 --priority 1020

Step 3 - Connect to your VM

Connect over SSH with the key you supplied at deployment.

ssh azureuser@<vm-public-ip>

Step 4 - Confirm the services are running

Check that both services are active:

systemctl is-active mcserver.service nginx.service

Both report active. Mirth Connect runs as a Java service (the mcserver launcher). It is bound to the loopback address 127.0.0.1:8443 for HTTPS and 127.0.0.1:8080 for HTTP.

nginx fronts it with TLS on port 443, plus a port 80 health endpoint and HTTPS redirect. Mirth's embedded Derby database and keystore live on the dedicated Azure data disk mounted at /var/lib/mirthconnect.

Step 5 - Retrieve your admin password

The Mirth admin password is generated uniquely on the first boot of your VM and written to a root-only file:

sudo cat /root/mirthconnect-credentials.txt

This file contains MIRTH_USERNAME (always admin), MIRTH_PASSWORD, the web admin URL and the REST API base. Store the password somewhere safe.

The file is mode 0600 and owned by root, so only an administrator can read it. Step 12 shows where the Derby database, keystore and configuration map live on the data disk.

Step 6 - Confirm the health endpoint and the TLS edge

nginx serves an unauthenticated health endpoint for load balancers and probes, and terminates TLS in front of the loopback Mirth listener. Request all three entry points:

curl -s -o /dev/null -w 'healthz: HTTP %{http_code}\n' http://127.0.0.1/healthz
curl -s -o /dev/null -w 'port 80: HTTP %{http_code}\n' http://127.0.0.1/
curl -sk -o /dev/null -w 'web admin over TLS: HTTP %{http_code}\n' https://127.0.0.1/

/healthz returns HTTP 200 and never requires authentication, so it is safe for an Azure Load Balancer health probe. Port 80 returns HTTP 301 and redirects to HTTPS. The web admin at https://<vm>/ returns HTTP 200 over TLS.

Step 7 - Verify the per-VM admin password over the REST API

Mirth ships the default login admin / admin. On the first boot of your VM, that default is rotated to your unique per-VM password using the Mirth REST API, and the default is then verified as disabled. You can confirm the same from the command line.

The Mirth REST API requires an X-Requested-With header on every call. Because the command embeds your unique password, run it interactively rather than from a script. Substitute the value of MIRTH_PASSWORD from Step 5 for <MIRTH_PASSWORD>:

mirth_login() { curl -sk -H 'X-Requested-With: sac' -H 'Accept: application/json' \
  --data-urlencode username=admin --data-urlencode "password=$1" \
  https://127.0.0.1/api/users/_login | tr -d ' \n' | grep -oE '"status":"[A-Z_]+"' | head -1; } echo -n "default admin/admin -> "; mirth_login 'admin' echo -n "your per-VM password -> "; mirth_login '<MIRTH_PASSWORD>'

The default admin / admin prints "status":"FAIL", which confirms that the shipped default has been disabled. Your per-VM password prints "status":"SUCCESS". A FAIL status means the credentials were rejected, and SUCCESS means the session authenticated.

Mirth's own password policy is left at its defaults. You can tighten it in conf/mirth.properties.

Step 8 - Sign in to the web admin

Browse to https://<vm-public-ip>/. The appliance uses a self-signed certificate, so accept the browser warning. For production, put your own domain and certificate in front (see Maintenance). Mirth Connect shows its landing page.

Sign in to the Web Dashboard with the username admin and the password from Step 5. Alternatively, select Launch Mirth Connect Administrator to download and run the full desktop Administrator, where you design and deploy channels.

Step 9 - Explore the REST API

Everything the Administrator does is also available over the REST API. The appliance ships an interactive Swagger explorer at https://<vm-public-ip>/api/.

This is the NextGen Connect Client API, grouped by area: Channels, Channel Deployment Operations, Channel Statistics, Messages, Users, Server Configuration and more. Use it to script deployments, integrate with CI, or drive Mirth from your own tooling.

Step 10 - Build and manage channels via the API

Expand the Channels group in the API explorer to see the full channel lifecycle:

  • GET /channels lists channels.
  • POST /channels creates a channel.
  • PUT /channels/{channelId} updates a channel.
  • DELETE /channels/{channelId} removes a channel.

The group also offers deploy, undeploy, enable and summary operations.

A channel defines a source connector (for example an HL7 MLLP listener), a set of transformers and filters, and one or more destination connectors. Design channels in the desktop Administrator, then use these endpoints to deploy and manage them at scale.

Step 11 - Manage users

The Users group exposes the user management endpoints, including GET /users to list users and POST /users to create one. It also includes the POST /users/_login and PUT /users/{id}/password calls that this appliance uses on first boot to rotate the admin password.

As the administrator, you can add operators, assign them channels and manage passwords entirely over the API.

Step 12 - Confirm data lives on the dedicated disk

Mirth's data is stored under /var/lib/mirthconnect on the dedicated Azure data disk. That includes the embedded Derby database (channels, message history, users), the auto-generated keystore and the configuration map. The data therefore survives OS changes and can be resized independently. Confirm the mount:

findmnt /var/lib/mirthconnect ls -1 /var/lib/mirthconnect/appdata

The mount is backed by a separate Azure data disk that is captured into the image and re-provisioned on every VM. The mirthdb directory is the Derby database, and keystore.jks is the server keystore.

Step 13 - Open channel listener ports

Mirth channels receive messages on ports you choose per channel. For example, an HL7 v2 MLLP listener commonly uses TCP 6661, and a channel might listen for HTTP on another port. The image deliberately does not pre-open a wide range.

When you deploy a channel with a TCP or HTTP listener, open exactly that port in the Azure network security group:

az vm open-port --resource-group <your-rg> --name mirth-connect --port 6661 --priority 1030

Bind channel listeners only to the interfaces you need, and prefer TLS-enabled connectors for any traffic that leaves the host.

Maintenance

  • Password. The admin password is set on first boot and recorded in /root/mirthconnect-credentials.txt. To change it, sign in to the Administrator and use the user settings, or call PUT /api/users/1/password over the REST API.
  • TLS and your own domain. The appliance ships a per-VM self-signed certificate on port 443. For production, point a DNS name at the VM and install a trusted certificate, for example with certbot and Let's Encrypt. Then reference it in the nginx site at /etc/nginx/sites-available/sac-mirth-connect and reload nginx.
  • Channels. Design and deploy channels in the desktop Administrator, which you launch from the landing page. You can also manage them over the REST API under /api/channels.
  • Upgrades. Mirth Connect is installed under /opt/mirthconnect. Your data under /var/lib/mirthconnect is preserved across restarts. Test upgrades against a copy of your data disk first.
  • Storage. All Mirth state lives under /var/lib/mirthconnect on the data disk. Back up that volume to protect your channels and message history.
  • Security patches. unattended-upgrades remains enabled, so the OS continues to receive security updates automatically.
  • Compliance. This image ships as infrastructure only. You are responsible for all HIPAA and PHI controls, including encryption in transit and at rest, network isolation, access control and audit. SecureAnyCloud does not imply certified compliance.

Support

SecureAnyCloud provides 24/7 expert support for this image. Contact sales@secureanycloud.com.

Deploy on Azure

Launch Mirth Connect (NextGen Connect) 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