Nextcloud side-by-side migration blog home

Posted Friday, 04-Oct-2024 by Ingo Karkat

Why Nextcloud

Back in 2020, I had installed Nextcloud on an entry-level Linux cloud server (1 vCore, 2 GB RAM, 50 GB SSD, €3/month) to move away from the free-tier at Dropbox after exceeding the (low; I think I needed 2 clients at work and 3 for personal systems) limitations in the number of active clients. I never stored huge amounts of data there, and had been mostly content with their free service (apart from the unconventional Linux client installation, and the fact that my email address had been included in a leak and I've been regularly flooded with spam and fishing emails since then). Self-hosting looked attractive in light of the monetization and upselling that all the large cloud services were doing, as long as it's easy enough.

And Nextcloud scored really well on that matter; setup (as a Snap) on an Ubuntu 18.04 VM was as easy as vm1$ sudo snap install nextcloud followed by a couple of short command-line invocations to set the administrator password and enable HTTPS via Let's Encrypt. After that, the system can be tweaked (and applications installed) through a beautiful web interface.
I've mainly used the file sharing, calendar, and later also the news aggregator (with the Nextcloud News Android app and newsboat Linux terminal application). The cloud system also serves as my main Unison File Synchronizer repository for my personal Linux configuration and tooling (as the the setup on my NAS didn't go so well).

Though I'm still a bit sceptical about Snaps for desktop applications, on the server the ease of installation and automatic updating are a huge convenience. The server has been running for almost four years without any issues. But I knew that I eventually had to move the system to a newer operating system version, and a cost hike by the hoster (due to increased energy costs) made that a bit more pressing.

fears

My initial research had brought up a lot of information about backup procedures and migration. Frankly, after the smooth initial setup I wasn't prepared for technical maintenance tasks of an application I barely understood its architecture on a server that I didn't physically control (and unlike with a local VM couldn't easily take a snapshot of). A couple of community posts described the procedure for snaps, but also reported potential problems due to the Snap's inherent limitations with accessing file system locations. Did I get tricked by the initial low hurdle and now had to pay my dues?!

new server

Turns out the migration was super-easy, and any fears unfounded. I'm writing this down so that other anxious users have another data point on how easy that is. Even though my machine is super-tiny, the fact that I didn't have many shared files avoided any issues with disk space and inaccessible mounts. My full Nextcloud backup is just 2.2 GB in size, and that fit comfortably on a system with a single 50 GB filesystem (with 30 GB free space).

My new server has 2 vCores, 2 GB RAM, 50 GB SSD, €2/month, and is running Ubuntu 24.04. First, I've installed Nextcloud as a snap, following this guide:

vm2$ sudo snap install nextcloud
vm2$ sudo nextcloud.manual-install administrator hunter2
Nextcloud was successfully installed
vm2$ sudo nextcloud.occ config:system:set trusted_domains 1 --value=vm2.karkat.de
System config value trusted_domains => 1 set to string vm2.karkat.de
vm2$ sudo nextcloud.enable-https lets-encrypt

HTTPS setup

My original server could be reached at vm1.karkat.de (well, actually the server just comes with one IPv4 address, and I configured an A record on my web presence for the hostname). But I had thought ahead and also registered an alias cloud.karkat.de, and that's where the SSL certificate was registered for. This way, after the migration I would just need to reconfigure the A record, and all of my Nextcloud clients would seamlessly reconnect to the new server.

On the new server, the actual cloud.karkat.de alias cannot be configured yet, because all hostnames need to be online and point to the current system; that's how Let's Encrypt verifies that you actually own the server. Community posts mentioned that the HTTPS setup is separate from the backup; actually what they mean is that the configuration is contained in the full backup, but when that backup is restored on a different server (i.e. side-by-side), the configuration won't match any longer and needs to be redone.

I only did the initial HTTPS setup on the new server to verify that the (still empty) server is fully working. Strictly, I could have skipped that and simply restored the backup onto it.

migration time!

On the old system, all data is exported:

vm1$ sudo nextcloud.export
WARNING: This functionality is still experimental and under
development, use at your own risk. Note that the CLI interface is
unstable, so beware if using from within scripts.

Enabling maintenance mode... done
Exporting apps...
		122.67M 100%   58.19MB/s    0:00:02 (xfr#1568, to-chk=0/1785)
Exporting database...
Exporting config...
Exporting data...
		1.96G 100%   22.36MB/s    0:01:23 (xfr#8291, to-chk=0/25428)

Successfully exported /var/snap/nextcloud/common/backups/20241002-144147
Disabling maintenance mode... done

Prior to the export, the system is put into maintenance mode (so that clients cannot do any file uploads, add calendar entries, etc.) Since the system will be decommissioned, I put it back into maintenance mode via vm1$ sudo nextcloud.occ maintenance:mode --on. Should any problems arise on the new system, the old one's still waiting to be re-enabled; that's the big benefit of a side-by-side migration!

The backup is in a timestamped directory under /var/snap/nextcloud/common/backups/; now that backup needs to be transferred to the new host. I use rsync for this:

vm1$ sudo -E rsync -avz /var/snap/nextcloud/common/backups/20241002-144147 root@vm2.karkat.de:/var/snap/nextcloud/common/backups
sending incremental file list
sent 1,216,786,120 bytes  received 260,402 bytes  7,222,828.02 bytes/sec
total size is 2,234,270,782  speedup is 1.84

On the new system, the transferred backup is imported:

vm2$ sudo nextcloud.import /var/snap/nextcloud/common/backups/20241002-144147/
WARNING: This functionality is still experimental and under
development, use at your own risk. Note that the CLI interface is
unstable, so beware if using from within scripts.

Enabling maintenance mode... done
Clearing existing non-default apps... done
Importing apps...
		122.67M 100%  128.24MB/s    0:00:00 (xfr#1568, to-chk=0/1785)
Dropping existing database... done
Creating new database... done
Granting database privileges to existing user... done
Importing database...
Importing config...
Clearing existing data... done
Importing data...
		1.96G 100%  118.15MB/s    0:00:15 (xfr#8291, to-chk=0/25428)
Disabling maintenance mode... done

The new instance cannot be accessed, as the SSL configuration has also been migrated. The browser says

Access through untrusted domain
Please contact your administrator. If you are an administrator, edit the "trusted_domains" setting in config/config.php like the example in config.sample.php.

And the configuration confirms that:

vm2$ sudo nextcloud.occ config:system:get trusted_domains
localhost
cloud.karkat.de

Clearly, the HTTPS configuration is part of the backup and restore. As I don't want to commit to the new instance yet, I do this step by step and first reconfigure the direct vm2 hostname, but do not yet move the "virtual" A record for cloud.

vm2$ sudo nextcloud.occ config:system:set trusted_domains 1 --value=vm2.karkat.de
System config value trusted_domains => 1 set to string vm2.karkat.de
vm2$ sudo nextcloud.enable-https lets-encrypt
[...]
Please enter your domain name(s) (space-separated): vm2.karkat.de
Attempting to obtain certificates... done
Restarting apache... done

✓ I can login as my user, and my files, calendar, and news are all there! Time to commit and move the A-record for cloud.karkat.de from vm1 to vm2.
Not a minute later the Nextcloud client popped up an "untrusted certificate" warning:

Cannot connect securely to cloud.karkat.de: The host name did not match any of the valid hosts for this certificate with Certificate vm2.karkat.de

After confirming with $ dig cloud.karkat.de, it's time to re-configure HTTPS for the last time:

vm2$ sudo nextcloud.occ config:system:set trusted_domains 2 --value=cloud.karkat.de
System config value trusted_domains => 2 set to string cloud.karkat.de
vm2$ sudo nextcloud.occ config:system:get trusted_domains
localhost
vm2.karkat.de
cloud.karkat.de
vm2$ sudo nextcloud.enable-https lets-encrypt
[...]
Please enter your domain name(s) (space-separated): vm2.karkat.de cloud.karkat.de
Attempting to obtain certificates... done
Restarting apache... done

🎉 I can now access Nextcloud via https://cloud.karkat.de/index.php/login and the Nextcloud desktop app re-connected, too.

next steps

My old server will be shut down early December, and I'm on the lookout for a good offer for another server. As maintenance is so easy, I plan to set up regular scheduled backups (via cron job) that also copy the data to the other server, so that I always have a fallback available. The Unison repository has been migrated via rsync, too.

Ingo Karkat, 04-Oct-2024

ingo's blog is licensed under Attribution-ShareAlike 4.0 International

blog comments powered by Disqus