Individual IPs for Docker Apps - is it possible?

Under my TrueNAS CORE setup, I had a handful of Jails with apps (Nextcloud, Piwigo, etc.). Each jail had its own IP, and I was able to set up DNS on my router so that a name pointed to each jail’s internal IP. I also had / have a VM acting as a Proxy server, so that I could access the same URLs from the outside world. The local DNS at home just meant I was browsing directly to the Apps / Jails, instead of a proxy, when on my home network.

I’m looking at Electric Eel now, and trying to find a way to assign IPs to specific apps, so that I can keep the trend of just browsing directly to them without needing to change port numbers, set up a proxy, etc. Is this possible under EE, or will I need to set up the Proxy to forward to different ports for my Apps?

1 Like

Not currently possible to use custom IPs with default apps.

Can be done with a custom compose app (ie raw compose, Dockge, portainer, etc)

Stux, thank you for the reply. I’m coming over from a CORE / Jails world, and the world of Docker and composing files is all brand new to me.

I did look at your video on migrating to the new Dockge setup, but it looks like it assumes base knowledge, which I currently lack. Are you able to point me to documentation for someone new to SCALE (specifically EE) to set up multiple Apps with their own IPs? Honestly, I should back that up, as I am not sure how to set up Apps in EE at all, yet…

I realize this is a heavy ask. I’m looking at this as someone either migrating from CORE to SCALE, or just getting into TrueNAS for the first time on SCALE and looking to set up Apps on their own. If it would help, I’d love to make some documentation, in writing, on how to do this step-by-step that can later be made official or into a video.

Did you already watch my video on Sandboxes? (Similar to Jails)

  1. Sandboxes may be more familiar
  2. I go into Dockge app setup in more detail

And finally, I have been testing macvlan / static ip support in docker on eel, but as I said, there is currently no support in the iX apps for it, so you have to use custom apps.

I do plan on making a video in this once eel hits RC

Written documentation? Start here:

You want to make an ipvlan or macvlan, which you currently have to do either on the command line, through the compose file, or through Portainer (as an alternative to Dockge).

Another possible solution to this that I use (unless you have firewall rules applied to those per app IPs): run your apps on the same IP, but different ports, and use nginx proxy manager to route custom URLs to the correct IP:Port combination

For example:
sonarr running on http://host:30027, but nginx accepts connections to http://sonarr.host:443 and forwards it

You can also add a wildcard cert to nginx proxy manager to secure all connections to your apps. You also only have to open up one port (443) to the Internet to access all the apps that you proxy through NPM

Just pointing out the obvious. nginx/caddy, etc proxy http, not mariadb and other such apps. So, they are good for many apps, but not all apps. There are other proxies though that might help, and perhaps plugins but more work.

I’m using caddy with porkbun on Eel via simple compose custom apps and it’s working great. Once you move the default 80 and 443 ports away from the Scale UI, all my apps seem to be able to use their default ports and I can have app specific DNS names that are proxied as needed.

Sorry for the late reply, it’s been a rough week at work.

Stux, thank you for the Jailmaker tutorial. From what I am seeing, you’re making one Jail, and installing multiple apps in that jail? I’m guessing I would need to make an indivdual jail for each app, at least for now - when EE officially drops, I may be able to achieve what I am looking for more easily.

The video is for Dragonfish, installing Docker and compose in a sandbox (“jail”), and then all apps as containers in this jail.
If you want to reproduce FreeBSD jails in any version of SCALE, then you install each app in its own sandbox.
If you’re already on Electric Eel, with its native docker, you don’t even need sandboxes and can run containers directly—but you have to set up the networking you want in the YAML compose files, or use Portainer as a GUI.

1 Like

Right, that’s what I am trying to figure out how to do. At the moment, it looks like I need to learn Docker from the ground up, and figure out how to modify the compose files. I briefly looked at Portainer, but it was way too confusing for a beginner to pick up.

Many applications have sample or starting or even complete compose files already for them on github or docker hub. Most of my custom apps I created did. This gives you 90% or more of what you want. Certainly nextcloud (just one example) has sample compose files.

We’re back to the basic issue, though - as someone new to SCALE, I have no idea how to implement this. I get the general concept of a compose file, but I don’t know how to implement them in SCALE. The advice I am getting is “Just do it” or “It can be done.” What I am missing are the steps to do it.

I don’t know how to use a compose file. I get I can find them online, but how or where do I set them up in the TrueNAS UI? Stux’s video implies I need to install Dockge first before I can do anything else.

I’m not trying to be obstinate or pedantic, I swear. I’m looking at this from the viewpoint of a new user coming into SCALE fresh, and looking for a guide to help me learn terminology and concepts that are already known to people with experience, without having to figure out what I don’t know from the ground up. I can’t imagine I am the only person that has never worked with Docker before.

It depends on which version of truenas you’re using. If you’re on dragonfish you have to use either a jail and follow stux’s setup or a linux vm and run docker in side the vm. After setting up dockge you simply copy and paste the compose file in a field in the dockge gui.
Another option would be to save tha compose.yml to a dataset/folder and manually run docker-compose up-d from inside the folder for the container to start.

If you’re on electric eel there’s a truenas gui to add compose files and container name, then you press launch and the container will start.

Edit: finished half written thoughts :sweat_smile:

1 Like

What I can’t under stand is the no support for docker images on separate ip addresses. I mean you might want to use 443 also and syslogport and other ports that are in use by native truenas, Í tried to use containers and syslog which was no go unless I changed the port which was also a no go since lots of clients don’t support entering ports when specifying syslog.

I am using kubernetter in the stable true as release (dragon) , and I had to use truecharts to get that working with other ip address, which now is such a pain after truecharts repo went dead.

That briefly sums your options, yes. Either learn enough about compose.yaml files to set up what you want, or install Portainer and read the relevant chapters of its documentation. (It is not necessary to master, or even undestand, everything.)

I simply read:

Containers can be run under their own ip on dragonfish via custom apps and a bridge interface. I have plenty of them. They can also be used on Electric Eel coming soon.

It’s actually really easy if you can follow some basics. I don’t use compose as I don’t find it necessary and I think it can be confusing for many people. The standard (I think original) formatting example is as per below. If you enter the below with your individual settings you will have a runnable docker instance of plex. Also, always check docker.io which will typically tell you what all the container variables are.

sudo docker create --name=plex
–restart=always
–net=bridge
-e TZ=Pacific/Auckland
-p 32400:32400/tcp
-p 32410:32410/udp
-p 32412:32412/udp
-p 32413:32413/udp
-p 32414:32414/udp
-v /mnt/ssd1pool/docker2/plex/config:/config
-v /mnt/hdd2pool/vroot_media/video/television:/mnt/television
-v /mnt/hdd2pool/vroot_media/video/recordings:/mnt/recordings
-v /mnt/hdd1pool/vroot_media/video/VHS:/mnt/VHS
-v /mnt/hdd1pool/vroot_media/audeo:/mnt/audio
-v /mnt/hdd1pool/vroot_media/home_videos/Processed:/mnt/home_videos
-e PLEX_UID=568
-e PLEX_GID=658
-v /mnt/ssd1pool/plex_transcode:/transcode
-e PGID=568
-e PUID=568
plexinc/pms-docker:latest

The docker start plex and you’re go.

You can just copy all of that and adjust for your needs. Also, you can change --net=bridge to --net=host and you can do away with all the port mapping above - though there are different challenges you will need to understand. Mainly only one port of the same kind can sit on the host due to it being on the same IP. Answering your original question, I’m pretty sure you can set an individual IP for this I think the mode is --net=macvlan but I haven’t tried that yet. Hopefully this is helpful by way of example. Tested working in TrueNAS scale Electric Eel.

1 Like

I’m using tailscale sidecars to access my containers. This gives me a unique IP for each service, as well as a https endpoint.

The benefits are:

  • you have an IP per service, so you can bind to ports freely from within your container
  • the containers appear on your VPN, so you can securely get to your services from outside your LAN
  • you can optionally enable Tailscale Serve, which will automatically issue a LetsEncrypt cert for you and create a redirect from 443 → your http port. No more browser warnings
  • You can optionally enable Tailscale Funnel, which will then stick that https service on the public internet
  • Tailscale has a bunch of other (optional) fancy features, like SSH auth, exit nodes, selective sharing with other tailscale users etc

Some drawbacks:

  • you can’t access your services if you’re not on the vpn (except via Funnel)
  • more containers and config to manage
  • the server parts are not open source
  • commercial use needs a paid plan

It’s a bit complicated to set up the first one, but once that’s done you have a cookie cutter approach you can use for all your containers. I’ll try to explain how below.
I’m not on Electric Eel yet, (using jlmkr + dockge) but I believe this approach will just work under EE as well. As a general rule, dockge is better for managing compose stacks (like the one below) but portainer or plain docker are also possible.

Here’s an example compose.yaml:

services:
  wiki:
    container_name: ${NAME}
    image: m0wer/tiddlywiki:latest
    restart: unless-stopped
    volumes:
      # You could mount a directory from your NAS instead
      - wiki:/var/lib/tiddlywiki
    environment:
      - NODE_MEM=256
    depends_on:
      - tailscale-sidecar
    # Black magic - delegate networking to the other container.
    # TiddlyWiki will bind on port 8080 and just appear on the tailscale VPN. 
    network_mode: service:tailscale-sidecar
  tailscale-sidecar:
    image: tailscale/tailscale:latest
    hostname: ${NAME}
    restart: unless-stopped
    volumes:
      - tailscale-data:/var/lib/tailscale
      - /dev/net/tun:/dev/net/tun
      # only if you want tailscale to manage https for you
      - $PWD/ts/config:/config
    environment:
      - TS_AUTHKEY=${TS_AUTHKEY}?ephemeral=false
      - TS_STATE_DIR=/var/lib/tailscale
      # By tagging this node, you can configure an ACL to allow auto-provisioning the funnel.
      # Only required for tailscale-managed https.
      - TS_EXTRA_ARGS=--advertise-tags=tag:container
      # This config is only required if you want the HTTPS tunnel.
      - TS_SERVE_CONFIG=/config/serve.json
      - TS_ACCEPT_DNS=true
    cap_add:
      - net_admin
      - sys_module
# This section is optional, it sticks a link in the dockge panel so you can click through to your service.
x-dockge:
  urls:
    - https://${NAME}.${DOMAIN}/
networks: {}
volumes:
  tailscale-data:
    driver: local
  wiki:
    driver: local

Variables are in .env (which dockge understands), but you could just put them inline if you want to.

TS_AUTHKEY=ts-client-create-this-in-tailscale-admin-settings-oauth-clients
NAME=wiki
# Find this under DNS in the tailscale web console. You'll also need to enable HTTPS certs and MagicDNS on that page if you want tailscale HTTPS to work.
DOMAIN=tailnet-name.ts.net

The tailscale serve config file needs to be created outside of dockge, which is a bit of a pain. Not needed unless you want tailscale to set up a https tunnel for you. It looks like this.
There’s only two things to configure:

  • the port (8080) that your service listens on. Incoming requests on your tailscale network on port 443 will be redirected there.
  • AllowFunnel can be set to true. This will expose your service on the public internet, so make sure you have authentication set up within the app if you choose to do this (and keep up with patches, etc).
{
  "TCP": {
    "443": {
      "HTTPS": true
    }
  },
  "Web": {
    "${TS_CERT_DOMAIN}:443": {
      "Handlers": {
        "/": {
          "Proxy": "http://127.0.0.1:8080"
        }
      }
    }
  },
  "AllowFunnel": {
    "${TS_CERT_DOMAIN}:443": false
  }
}

One last thing (again, only if you want https): this is a one-time change to your tailscale ACL that lets any container create a funnel:

	"nodeAttrs": [
		{
                        // there's some default config that lives here...
		},
		{
			// Funnel policy, which lets containers enable Funnel.
			"target": ["tag:container"],
			"attr":   ["funnel"],
		},
	],

I cobbled most of this together from this blog post. If you like this approach but don’t want to use tailscale or the http tunnel, the same thing can be achieved with other tools:

  • About half the complexity above is just there to enable the https tunnel, you can drop those parts if you just want a dedicated IP
  • The same network_mode: service trick can be used with other vpn containers, e.g. tinc
  • If you never need to access your services outside your local network, ditch the vpn and use macvlan as others have suggested. I do this for my jails but haven’t tried it with containers
1 Like