Skip to content
+1 (813) 212-3723 support@layeronecloud.com
Self-hosting VPS guides

How to host Nextcloud All-in-One on a VPS

Deploy Nextcloud AIO on an Ubuntu VPS, size CPU and storage honestly, restrict its management interface, and configure encrypted off-server backups.

7 min read

Nextcloud combines file sync, sharing, calendars, contacts, collaborative editing, chat, and a large app ecosystem. The supported All-in-One (AIO) stack also runs PostgreSQL, Redis, a web server, and optional services. It therefore needs more planning than a single PHP container.

This guide uses Nextcloud's official AIO master container. The public service gets normal HTTPS on TCP 443, while the self-signed AIO management interface on 8080 is bound to loopback and reached through SSH.

VPS size, CPU, storage, and price

Nextcloud says memory depends heavily on users, apps, files, and activity. AIO's interface calculates additional requirements for optional containers. The values here are a practical small-production plan, not universal upstream limits.

Item Planning value
Minimum RAM 4 GB for a small core AIO stack without heavy optional containers
Recommended RAM 8 GB for a small household or team with preview generation and update headroom
Expected CPU usage Roughly 0.05–0.25 vCPU idle; 1–4 vCPU while generating previews, syncing many files, indexing, scanning, or serving active users
Storage requirement Reserve 20–30 GB for Ubuntu, images, database, cache, and logs, plus all user files, file versions, trash, and temporary upload space
Exact LayerOne SKU gc.medium — slug layerone-pro, 4 vCPU, 8 GB RAM, 160 GB disk
Expected monthly cost $0.0205 per active hour; about $14.97 per 730 hours against the advertised $15.00 730-hour equivalent

A 744-hour month is about $0.0205 × 744 = $15.25. The 160 GB disk is not 160 GB of usable file capacity: the OS, container images, database, versions, trash, previews, and working space all share it. Existing data sets near 100 GB deserve a larger SKU and a measured migration plan.

User activity, preview formats, versions, optional apps, transfer, and storage growth vary, and LayerOne bills the allocated VPS hourly. CPU figures are planning estimates, not performance guarantees. Office, Talk, antivirus, full-text search, and large active teams can require substantially more RAM and CPU.

Assumptions

  • Ubuntu 24.04 LTS on an x86-64 LayerOne KVM VPS
  • A public IPv4 address and a dedicated DNS name such as cloud.example.com
  • Docker Engine from Docker's apt repository, not the Ubuntu Snap package; see Running Docker
  • DNS already resolves the hostname to this VPS
  • A sudo user using SSH keys; replace ADMIN_IP below with its fixed source address
  • Host ports 80 and 443 are unused; this guide uses AIO's integrated HTTPS path rather than an external reverse proxy

AIO supports a dedicated hostname, not a URL subdirectory. Do not plan to serve it as example.com/nextcloud.

1. Open only the required ports

In the LayerOne cloud firewall, use inbound default DROP and allow:

Source Protocol Port Purpose
ADMIN_IP/32 TCP 22 SSH and the management tunnel
0.0.0.0/0 TCP 80 Certificate validation and redirect
0.0.0.0/0 TCP 443 Nextcloud HTTPS

TCP/UDP 3478 is needed only if you later enable Nextcloud Talk's TURN server. UDP 443 is optional for HTTP/3. This guide does not publish AIO management ports 8080 or 8443.

sudo ufw default deny incoming
sudo ufw default allow outgoing
sudo ufw allow from ADMIN_IP to any port 22 proto tcp
sudo ufw allow 80/tcp
sudo ufw allow 443/tcp
sudo ufw enable
sudo ufw status verbose

Docker can bypass UFW for published ports, so keep the same restrictions in the LayerOne cloud firewall.

2. Check Docker and start AIO with its official Compose file

Confirm this is a standard Docker installation and not Docker Snap:

sudo docker info | grep 'Docker Root Dir'
docker compose version

If the root path begins /var/snap/docker, migrate to the supported Docker Engine installation before continuing.

Nextcloud recommends its example Compose file for production because it makes the master-container configuration reviewable and repeatable. Download the current upstream file into a dedicated project directory:

sudo install -d -m 0750 /opt/nextcloud-aio
sudo chown "$USER":"$USER" /opt/nextcloud-aio
cd /opt/nextcloud-aio
curl -fsSLo compose.yaml   https://raw.githubusercontent.com/nextcloud/all-in-one/main/compose.yaml
cp compose.yaml compose.yaml.upstream

Edit the ports list for nextcloud-aio-mastercontainer: change "8080:8080" to "127.0.0.1:8080:8080", and remove the optional "8443:8443" line. Keep "80:80". Do not rename the master container or its configuration volume; AIO depends on those names.

The resulting part of the service must read:

ports:
  - "80:80"
  - "127.0.0.1:8080:8080"

Do not add port 443 to the master-container service. After setup, AIO creates the sibling nextcloud-aio-apache container, which claims host TCP 443 for the actual Nextcloud site even though that port does not appear in this Compose service. Port 8080 is only the AIO control interface. If another web server already owns 443, stop here and follow the upstream reverse-proxy mode instead; that mode sets APACHE_PORT and APACHE_IP_BINDING and proxies to that Apache port, never to the management interface on 8080.

Validate the entire upstream file and start it:

cd /opt/nextcloud-aio
sudo docker compose config >/dev/null
sudo docker compose pull
sudo docker compose up -d

Although the socket is mounted read-only, the master container is designed to control sibling containers. Treat access to its interface as privileged host access. Keep compose.yaml.upstream only as a review reference; your edited compose.yaml is the active configuration.

Check startup:

sudo docker ps --filter name=nextcloud-aio-mastercontainer
sudo docker logs --tail=100 nextcloud-aio-mastercontainer
curl -kI https://127.0.0.1:8080

3. Complete setup through an SSH tunnel

On your workstation:

ssh -L 8080:127.0.0.1:8080 admin@SERVER_IP

Browse to https://127.0.0.1:8080, accept the expected self-signed certificate, and save the AIO passphrase in a password manager. Upstream specifically says to use an IP address, not the eventual Nextcloud domain, on port 8080 because HSTS can otherwise make the management URL inaccessible later.

Enter cloud.example.com when AIO asks for the Nextcloud domain. Start with the core containers. Add Collabora, Talk, ClamAV, Imaginary, full-text search, or other optional services one at a time only after reading the RAM estimate AIO shows for each.

4. Verify the finished service

After AIO reports the containers healthy, open https://cloud.example.com, create the Nextcloud administrator, then create a separate non-admin daily account.

sudo docker ps --format 'table {{.Names}}   {{.Status}}'
sudo docker exec --user www-data nextcloud-aio-nextcloud php occ status
curl -I https://cloud.example.com/status.php

Upload a small file, sync it to a second client, rename it, delete it, and restore it from trash. Confirm background jobs run and the Administration Overview has no unresolved configuration warnings. Test one file larger than your reverse-proxy or client defaults before migrating a library.

Security pitfalls

  • Keep the AIO interface on loopback. If you deliberately expose 8080 or 8443, restrict it to trusted administration addresses in the cloud firewall.
  • Do not put Nginx, Caddy, or another proxy in front of port 8080. An external proxy must use AIO's documented APACHE_PORT mode; this guide uses AIO's integrated HTTPS listener on 443.
  • Enable Nextcloud two-factor authentication and distribute recovery codes before inviting users.
  • Keep the administrator account for administration; use an ordinary account for sync clients.
  • Do not edit generated AIO containers as if they were a hand-written Compose stack. AIO owns their lifecycle.
  • Review app permissions before enabling community apps. Every app executes in the same security context as valuable files and metadata.
  • Do not place the database on a network filesystem. Keep database and active application data on the VPS's local SSD-backed disk.

Back up and restore before updating

Nextcloud AIO includes encrypted, deduplicated Borg backups. Configure its backup destination in the AIO interface, ideally as a remote SSH Borg repository on a different provider or physical system. A backup stored only on this 160 GB disk is lost with the VPS and competes with live data for space.

The backup password is required for restoration. Store it outside Nextcloud and outside the server. Enable scheduled backups only after an initial backup and a test restore succeed. External-storage mounts need separate coverage; they are not automatically protected merely because Nextcloud can see them.

Use the AIO interface to stop, update, and start its managed containers. Before each major Nextcloud or AIO update:

  1. Read the AIO and Nextcloud release notes.
  2. Run a fresh Borg backup and confirm its archive is visible remotely.
  3. Export or separately protect irreplaceable encryption and configuration material.
  4. Update from AIO and watch every container's log.
  5. Re-run occ status, upload/download tests, cron checks, and client sync.

LayerOne does not take snapshots or backups. Read Backups and snapshots before loading production files.

Official and LayerOne references

Still stuck

Chat with us from the portal.

Ask the assistant from the Chat bar. During business hours you can ask for a person and a human joins live.