TrueNAS Scale Nextcloud and reverse proxy (https)

Recently I’ve migrated from TrueNAS Core (formerly known as FreeNAS, FreeBSD-based) to TrueNAS Scale (Debian-based). Thus, I had to move web apps like Nextcloud, Plex, etc. from FreeBSD Jails to Kubernetes Pods manually. I would like to briefly introduce these different two virtualization techniques here below.


2023.12.09 Update:

The configuration of TrueCharts and reverse proxy have changed a lot since I wrote this tutorial. I have also had lots of problems with TrueCharts because of frequent changes of app setting / trains. For example, people cannot simply upgrade their TrueCharts apps after they changed the validation [1,2]. Due to the frustration, I have migrated all apps (Nextcloud, Jellyfin, AdGuardHome, code-server, some game servers…) to docker containers I simply created. For reverse proxy, I am using nginx-proxy-manager instead of traefik now. The best practice is either mount your Nextcloud config/data into host (don’t use PVC to store them) or using SMB/NFS mounting functions in Nextcloud (without messing up with permission).

As a result, I removed all the TrueCharts setup and replaced it with tutorial for official docker images.

Join my discord server for discussion / troubleshooting!


FreeBSD Jail

First things first — what is FreeBSD? FreeBSD is an operating system which has a bunch of advanced features. One such feature is soft update for the UFS filesystem. Another such feature is called Jail, which is the front runner to the containers we use today. A Jail enables process and its children processes to run in a sandbox, i.e., they have separate file system, hostname, IP address, etc. In other words, jailed process cannot interact with processes in another jail, and each jail has its own superuser.

So… how did they implement Jail? They patched FreeBSD kernel to be aware of if it is inside jail. For example, there is a statement if(superuser) then do (something). After being modified, it should be if(superuser and in jail) then do (something) or more typically if(superuser and not in jail) then do (something).

Example FreeBSD kernel code for getting aware of jail.

The features of FreeBSD Jail make it a great candidate for hosting web applications. For example, we have a WordPress service running in one jail with its IP 192.168.0.100, and a Plex service running in another jail with IP 192.168.0.101. They cannot interact with each other and if one crashes, the other service is unaffected.

You would say we can run the applications in virtual machines (bhyve in FreeBSD) but don’t forget such VMs have its own OS layer and take much more resources.

Kubernetes (K8s)

Actually, Kubernetes is not a type of virtualization method, it is a container manager. Wait, what is container? It is more or less like FreeBSD Jail which runs a group of processes in an isolated environment by leveraging kernel features. The most popular one is Docker container. With kernel namespaces, every container has its own file system, users and network stack, and resources can be limited by cgroups (which FreeBSD Jail cannot provide with). We create Pods (a group of one or more containers) via Kubernetes just like we create FreeBSD Jail via iocage. For example, a WordPress pod may have three containers: one for apache web server, another for sql database, and the other for redis. Kubernetes provides some advanced features like scaling and load balancing, but here in TrueNAS Scale we just use its basic functions.

0. Prerequisites

In order to host Nextcloud with your custom domain name, you must have:

  1. TrueNAS Scale
  2. Domain
  3. Cloudflare account (or other supported DNS providers)
  4. Public IP
  5. Router with port forwarding and NAT hairpin enabled

1. Setup App environment

If you haven’t setup any app before, you are required to assign a pool for storing app. It might take a while to fetch app catalogs from the Internet.

Assign a pool for apps. Here I use pool “TANK” for example.

Since we will use nginx-proxy-manager and it’s under TrueNAS Official community train, head to “manage catalogs” tab and click three dots icon on Official to edit it.

After all the tasks are finished, head to “available applications”, you should find nginx-proxy-manager. If not, click “refresh all” button above.

2. Install and configure nginx-proxy-manager reverse proxy

Reverse proxy service routes network traffic from different hostnames to belonged apps. To install this, just head to “available applications” tab and search for nginx-proxy-manager. Click install to proceed.

You can leave port numbers as default. For the storage configuration, if you want to save your certificate and login information even after this app is removed, you can use “Host Path” as shown above. Otherwise, default type (ixVolume) is fine.

Click “next” to the end, and save the setting to install it! After that, you should see nginx-proxy-manager in “installed applications’ tab with clickable “Web Portal” button.

3. Setup ACME certificates with Cloudflare account

Here we use DNS challenge to get our certificate.

3.1. Fetch Cloudflare API

Let’s suppose you are using Cloudflare to manage your domain name. We will need a API Token (not global key), which can be created in settings -> API Tokens tab.

You can just use “Edit zone DNS” template, and for the Zone Resources, select “All zones”

After that, you’ll get a API token, please copy it to somewhere else as it will not be shown again.

3.2. Setup ACME DNS challenges

After login to Nginx Proxy Manager web UI, head to “SSL Certificates” tab and click on “Add SSL Certificate”, “Let’s Encrypt” button.

For the domain names, if you’re going to just host nextcloud, you can enter a specific domain name. Otherwise, you can also use wildcard like *.windsketch.cc which matches all sub-domains as shown above.

Paste your cloudflare API Token after dns_cloudflare_api_token = . After that, click save and wait for a few minutes for certificate validation. If you see a certificate entry with valid expired date, you are all set!

4. Install Nextcloud

In this section, we will install both official Nextcloud and its database (we use mariadb here), so we will create two apps.

3.1. Setup mariadb

Since the official nextcloud docker itself does not come with any database to store any information, we need a create a separate database for that. Here we’re going to use official mariadb image. Click “Launch Docker Image” in TrueNAS Apps tab:

Image repository is mariadb.

For the container environment variables, you are going to add a database and user/password:

Since it uses TCP port 3306, you will need to expose this port by doing port forwarding. For example, I’m using port 13306 as node port here, so MY.TRUENAS.IP:13306 will head to port 3306 of this app.

For the storage, I use host path volumes again here for persistent storage. Click “Save” to launch docker image.

3.2. Setup Nextcloud

Click “Launch Docker Image” in Truenas Apps tab again for creating Nextcloud app.

Image repository is nextcloud.

For the container entrypoint, since I will use SMB as external storage in Nextcloud, smbclient is required and I simply add a command to install it:

(If you’re not going to use SMB, you don’t have to add anything here.)

For environment variables, you will need to add database information:

For MYSQL_HOST shown below, the format of value is IP:PORT. For example if the local IP of your TrueNAS is 192.168.1.254 and “node port” for mariadb (in pervious section) is 13306, then the value is 192.168.1.254:13306 here.

NEXTCLOUD_TRUSTED_DOMAINS is the domain you’re going to use for Nextcloud (which matches the one setup in nginx-proxy-manager). NEXTCLOUD_TRUSTED_PROXIES is you TrueNAS local IP again.

We only want to accept https connections, so OVERWRITEPROTOCOL is set as https here.

For port forwarding, add one with container port 80. I use 18080 as node port here:

For the storage, I use host path volumes again here for persistent storage for potential upgrade/migrate. Click “Save” to launch docker image.

Head to Nginx Proxy Manager web UI to add a proxy host: In “Hosts” tab, click “Add Proxy Host” button.

Select your valid certificate in SSL tab:

5. Setup DNS and port forwarding

Finally, you should add an “A” type DNS record in Cloudflare to point your domain name to the external IP address of TrueNAS, and add port forwarding entries in your router:

Remember the default ports when you were creating nginx-proxy-manager? You will forward port 80/443 coming into WAN to port 30021/30022 in your TrueNAS.

Let’s say if you browse https://your.domain.name/, and for example your public IP is 1.2.3.4 and TrueNAS local IP is 192.168.1.254.

the IP will be resolved via Cloudflare DNS entry and then will try to establish connection to your router, which is 1.2.3.4:443. By port forwarding rules from your router, it will redirect to 192.168.1.54:30022. Next, with the Nginx Proxy Manager inspect the hostname (your.domain.name) and found a match entry in hosts, so it redirects to port 192.168.1.254:18080, which is the local IP and port for your Nextcloud.

Note that you have to enable NAT hairpin (NAT loopback) in your router. Without that, you cannot connect to Nextcloud (or other apps) with domain name when you’re under the same LAN.

If you want proxy enabled for Cloudflare DNS entry, you have to set SSL/TLS encryption mode to “full” to avoid ERR_TOO_MANY_REDIRECTS error.

From now on, access your Nextcloud via https://your.domain.name/ and enjoy 😀!

View Comments (27)

  • Hi I am not able to make this working. Could you please help me?
    Do I have to configure the nextcloud config file somehow?

    Best
    Dejan

    • Hi, what errors or blockers were you facing? Normally default nextcloud config.php should be fine. If you have trusted domain issues, then you might configure config.php or re-create the pod.

  • Maybe a stupid question, but every app uses their own port. My Nextcloud set itself as 10020, my Jellyfin 8096. Buuut, websecure in Traefik is forcing everything onto subdomain.domain.eu:9443?? Can you please show your Nextcloud container Networking and Services section>

    • Hi there! I forgot to mention in the post but I am using different subdomain for each service (e.g., nextcloud.domain.eu, jellyfin.domain.eu, etc.) in the step 6 Ingress while creating apps, so that Traefik can forward incoming request to specific port and app based on the url. You can use 'CNAME' type DNS record to point them to a single 'A' record. In addition, if you're using wildcard (e.g., *.domain.eu) while creating certificate, it's good to go and there's no need to create multiple certificates for every subdomain. Hope this helps to your question.

  • Hi, i have followed you completely until step 5, everything worked so far as intended. Unfortunately, i am not able to access my nextcloud instance via the defined subdomain.domain... Could you help me detailing part 5 of the guide a bit more? What do you mean by i should put an "A" type entry in cloudflare? My domain is set as a

    • Sure thing! For adding type A entry, it means create a DNS record to point your defined subdomain.domain... to the IP address you're hosting nextcloud. You can add one in "DNS" tab by clicking "add record". If it is setup correctly, you can see your IP address by pinging your domain.

  • Followed your instruction pretty well, Traefik shows the same but I don't get next cloud (next cloud words well locally). Don't know where it went wrong. I do have a Cloudshare but I have turned off the proxie

    • Hi, if you already have CloudFlare account and valid domain, can you verify the IP is correct from pinging your domain (without proxy)? If DNS is working correctly, then something you should probably look at is port forwarding.

  • Pinging goes fine, and I have plex and another site (home automation) running from the site. I did everyting as stated and I recevive a copy of truenas from nextcloud.my.website. I dont know what is wrong, I have setup config files in docker before ..... I setup all the needed port forwards,

  • I did ping my website and it went fine. I also have plex running and through another compter my home automation. When I enter nextcloud.my.website I get a the inlog screen of TrueNAS (also from outside my network). I have setup nextcloud many times (through config.php), but this is something different, I have no clue what traefik does, only my screen is identical to yours.

    • Hi sorry it seems that some replies went to spam automatically. If you get login screen of TrueNAS when you go to https://nextcloud.my.web then I think you put port forward from 443 to 443 (or 80 to 80) for the TrueNAS local IP, which is not intended to be. Do you have discord account? My ID is windsketch#3025 and if you would like to we can have a quick talk on discord.

  • Any chance of you doing a example of the non truecharts version of nextcloud aio? I want to set that version up as it is much more complete than the truecharts version. I am figuring it could work with the docker compose truecharts app then the external services app to give it ssl. That would be awesome as Truecharts will not support the AIO edition. Thank you

    • Yes I can do that later. There's a "custom-app" made by TrueCharts which integrates Ingress with it so that we no longer need external-service app. Once I figure it out I will let you know!

  • Hi,

    I am also running in similar issues as above.
    I’ve got an domain name at Cloudflare, made a A record for “mydomain.com” to my ip address at home, and a CNAME record “nextcloud.mydomain.com”

    I setup everything as above in you write-up, including the port forwarding 443->9443 and 80->9080
    In my edgemax router i also see Packets and Bytes coming by for these forwarding rules.

    Is there still anything that you could point me to that i might do wrong?
    I it’s more convenient i can also contact you via discord

  • Hi, thank you for the detailed tutorial.. It is very helpful however I am stuck in one point. I followed all the steps and redo it several times. I do not get any errors but I do not see an entry in Traefik. Everything looks working except the URL entry so can you please help me identify what am I doing wrong?

    • Sure. Were you able to get Nextcloud app running? The entry will be automatically added in Traefik once the app is successfully started (and Ingress is setup correctly as well). I would say first make sure "enable Ingress" is checked in Nextcloud setting tab. My ID is windsketch#3025 and if you would like to we can have a quick talk on discord.

Related Post