WordPress on an ARM VPS with Docker

Server racks in a data center used as a hero image for a WordPress on ARM VPS with Docker guide

WordPress on an ARM VPS with Docker is a practical way to run a personal website on ARM64 hardware. This guide covers Docker Compose, WordPress, MySQL, private networking, a reverse proxy, DNS, HTTPS, and backups.

This WordPress on an ARM VPS with Docker setup uses safe placeholders rather than production values. Replace YOUR_DOMAIN, YOUR_DB_PASSWORD, and YOUR_PROXY_NETWORK with your own values. If you have questions, do not include real credentials in the comments; use placeholders instead.

WordPress on an ARM VPS with Docker: requirements

  • An ARM64 VPS running a supported Linux distribution.
  • A domain name and SSH access.
  • Docker Engine and Docker Compose.
  • A reverse proxy such as Nginx Proxy Manager connected to the application network.
  • A separate location for tested backups.

Prepare the ARM VPS

Connect over SSH, apply security updates, and check the architecture:

uname -m
docker --version
docker compose version

An ARM64 server normally reports aarch64. Confirm that the selected images support ARM64. Do not expose a database port to the Internet.

Create a shared Docker network

If the reverse proxy and WordPress stack use separate Compose projects, create a shared external network:

docker network create YOUR_PROXY_NETWORK

If the network already exists, keep it. Do not remove it while other services depend on it.

Configure WordPress with Docker Compose

Create a new directory and save this as compose.yaml. WordPress and MySQL are not published on host ports; the reverse proxy reaches WordPress through Docker networking.

services:
  db:
    image: mysql:8.4
    restart: unless-stopped
    command: --default-authentication-plugin=mysql_native_password
    environment:
      MYSQL_DATABASE: YOUR_DB_NAME
      MYSQL_USER: YOUR_DB_USER
      MYSQL_PASSWORD: YOUR_DB_PASSWORD
      MYSQL_ROOT_PASSWORD: YOUR_DB_ROOT_PASSWORD
    volumes:
      - project_db_storage:/var/lib/mysql
    networks:
      - wordpress_private

  wordpress:
    image: wordpress:php8.3-apache
    restart: unless-stopped
    depends_on:
      - db
    environment:
      WORDPRESS_DB_HOST: db:3306
      WORDPRESS_DB_USER: YOUR_DB_USER
      WORDPRESS_DB_PASSWORD: YOUR_DB_PASSWORD
      WORDPRESS_DB_NAME: YOUR_DB_NAME
    volumes:
      - project_wordpress_storage:/var/www/html
    networks:
      - wordpress_private
      - proxy_network

volumes:
  project_db_storage:
  project_wordpress_storage:

networks:
  wordpress_private:
    internal: true
  proxy_network:
    external: true
    name: YOUR_PROXY_NETWORK

Important: project_db_storage and project_wordpress_storage are Docker volume labels, not passwords, usernames, or public ports. Knowing these labels alone does not provide access. You may rename them, but the names must match in the service and top-level volumes sections.

Protect the actual database values, especially MYSQL_PASSWORD, MYSQL_ROOT_PASSWORD, and the matching WordPress variables. Use long, unique secrets and store them securely.

Start and verify the containers

docker compose up -d
docker compose ps
docker compose logs --tail=100 wordpress
docker compose logs --tail=100 db

Wait for database initialization and confirm WordPress is attached to both the private and shared proxy networks.

Proxy manager interface

Create a proxy host with these placeholder values:

  • Domain Names: YOUR_DOMAIN
  • Scheme: http
  • Forward Hostname / IP: wordpress
  • Forward Port: 80
  • Block Common Exploits: enabled
  • Cache Assets: normally disabled unless tested
  • Websockets Support: enable only when required
Nginx Proxy Manager WordPress example for WordPress on an ARM VPS with Docker
Example proxy-host settings using safe placeholder values.

The upstream hostname is the Compose service name wordpress, not a server IP or arbitrary host port. The proxy must be connected to YOUR_PROXY_NETWORK.

File-based Nginx configuration

server {
    listen 80;
    server_name YOUR_DOMAIN;

    location / {
        proxy_pass http://wordpress:80;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
    }
}

Configure DNS

In your DNS provider’s dashboard, add an A record: use @ for the root domain and set the value to your VPS public IPv4 address. Add an AAAA record only when IPv6 and the firewall are correctly configured.

Cloudflare DNS example for WordPress on an ARM VPS with Docker
Example DNS records using placeholders and documentation-only IP addresses.

For www, you can use a CNAME pointing to YOUR_DOMAIN. Remove conflicting old records for the same hostname. Do not add a DNS record for the private Docker service name.

nslookup YOUR_DOMAIN

Before requesting a certificate, confirm that the result points to the intended VPS and that public HTTP and HTTPS traffic reaches the reverse proxy.

Enable HTTPS

Open the proxy host’s SSL settings, select or request a certificate for YOUR_DOMAIN, and enable HTTPS redirection after the certificate is issued. Requests can fail when DNS is incorrect, ports 80 or 443 are blocked, or another service answers for the hostname.

Nginx Proxy Manager SSL settings for WordPress on an ARM VPS with Docker
Example SSL settings with a certificate selected.

Enable Force SSL after HTTPS works correctly. Enable HSTS carefully because browsers remember HTTPS-only behavior. Enable HSTS subdomains only when every relevant subdomain supports HTTPS.

If WordPress reports mixed content or redirect loops, check the forwarded protocol headers and the WordPress site URL. Change one setting at a time and test in a private browser window.

Verify and back up

  • Open https://YOUR_DOMAIN and confirm the certificate is valid.
  • Run docker compose ps.
  • Confirm MySQL has no public host port.
  • Check that the proxy resolves wordpress.
  • Back up the WordPress volume and database to separate storage.
docker compose exec -T db mysqldump   -uYOUR_DB_USER -pYOUR_DB_PASSWORD YOUR_DB_NAME > wordpress-backup.sql

Avoid placing real passwords in shell history. Test restoration before relying on a backup.

Common problems

502 Bad Gateway

Check shared network membership, the exact upstream name wordpress, and container port 80.

Certificate request fails

Check DNS, public reachability, firewall rules, and whether another service uses the public listeners.

Database connection errors

Check the service name, credentials, database name, and initialization logs. WORDPRESS_DB_HOST should use db:3306.

References

See the Guides category and Docker guides.

Leave a Comment

Your email address will not be published. Required fields are marked *

Scroll to Top