Browser VSCode docker image used to manage docker host with addon

This is a docker-compose.yaml for VS Code Server that allows host docker control in your browser window.

This is done by sharing the docker sock volume, docker-compose host folder and docker folder if you have it (for quick edits of config files) and using an environment variable to install the docker extension.

The docker-compose.yaml is from LinuxServer.io

---
services:
  code-server:
    image: lscr.io/linuxserver/code-server:latest
    container_name: code-server
    environment:
      - PUID=1000
      - PGID=1000
      - TZ=Etc/UTC
      - PASSWORD=password #optional
      - HASHED_PASSWORD= #optional
      - SUDO_PASSWORD=password #optional
      - SUDO_PASSWORD_HASH= #optional
      - PROXY_DOMAIN=code-server.my.domain #optional
      - DEFAULT_WORKSPACE=/config/workspace #optional
      - PWA_APPNAME=code-server #optional
    volumes:
      - /path/to/code-server/config:/config
    ports:
      - 8443:8443
    restart: unless-stopped


Create passwords for security, if you use your own auth and reverse proxy you can add Traefik and Authentik labels.

Note: If you use your own auth, just remove the password options.

My host docker-compose folder is found at – /home/richay/docker-compose
My host docker folder is found at – /home/richay/docker
The environment variable needed is – DOCKER_MODS=linuxserver/mods:universal-docker

Adding these in my new docker-compose will look like this

---
services:
  code-server:
    image: lscr.io/linuxserver/code-server:latest
    container_name: code-server
    environment:
      - PUID=1000
      - PGID=1000
      - TZ=Australia/Perth
      - DEFAULT_WORKSPACE=/config/workspace
      - PWA_APPNAME=code-server
      - DOCKER_MODS=linuxserver/mods:universal-docker
    volumes:
      - /home/richay/docker/code:/config
      - /home/richay/docker-compose:/config/workspace/docker-compose
      - /home/richay/docker:/config/workspace/docker
      - /var/run/docker.sock:/var/run/docker.sock
#    ports:
#      - 8443:8443
    restart: unless-stopped
    labels:
      - "traefik.enable=true"
      - "traefik.docker.network=proxy"
      - "traefik.http.routers.code-secure.entrypoints=https"
      - "traefik.http.routers.code-secure.rule=Host(`code-server.richay.au`)"
      - "traefik.http.routers.code-secure.tls=true"
      - "traefik.http.routers.code-secure.tls.certresolver=cloudflare"
      - "traefik.http.routers.code-secure.service=code"
      - "traefik.http.services.code.loadbalancer.server.port=8443"
      - "traefik.http.routers.code-secure.middlewares=authentik@file"
    networks:
      - proxy
networks:
  proxy:
    external: true


Note: Ports commented out as not needed with reverse proxy

If you dont have a reverse proxy and auth, then yours will look something like this

---
services:
  code-server:
    image: lscr.io/linuxserver/code-server:latest
    container_name: code-server
    environment:
      - PUID=1000
      - PGID=1000
      - TZ=Etc/UTC
      - PASSWORD=password #optional
      - HASHED_PASSWORD= #optional
      - SUDO_PASSWORD=password #optional
      - SUDO_PASSWORD_HASH= #optional
      - PROXY_DOMAIN=code-server.my.domain #optional
      - DEFAULT_WORKSPACE=/config/workspace #optional
      - PWA_APPNAME=code-server #optional
      - DOCKER_MODS=linuxserver/mods:universal-docker
    volumes:
      - /path/to/code-server/config:/config
      - /path/to/docker-compose:/config/workspace/docker-compose
      - /path/to/docker:/config/workspace/docker
      - /var/run/docker.sock:/var/run/docker.sock
    ports:
      - 8443:8443
    restart: unless-stopped


Head to either http://hostip:8443 if using standard or https://code-server.richay.au if using reverse proxy and enjoy direct access to your docker-compose files with the power of VS Code 🙂

Tailscale split dns by domain for secure home server access

This is how you can still have public facing web apps but still maintain private web apps while you’re connected to Tailscale.

My setup:
Domain is richay.au
Adguard (10.10.10.10) as my home network DNS / ad blocker – All webapps have a DNS cname record for *.richay.au to rewrite to my Traefik IP (so internal connections stay internal)
Traefik v3 (10.10.10.20) as my reverse proxy – All webapps are published here under subdomains for richay.au
Cloudflare tunnels to get around CGNAT for public facing web apps – Only public facing apps such as my blog are listed in my tunnels, and the private IP set to Traefik (10.10.10.20)
Proxmox for my hypervisor for Linux Debian VM’s.
Tailscale to make the magic happen.

The first step is to install Tailscale (tailscale.com) on either the Traefik host machine or the DNS host machine (or both). If only installing once you can use advertise a route to the other VM within Tailscale, this is the option I am choosing and install on my Traefik host of 10.10.10.20 – then advertising a route to my Adguard DNS of 10.10.10.10 this is done using this command once Tailscale has been setup:

sudo tailscale set --advertise-routes=10.10.10.10/32


You will need to go to the Tailscale admin console and locate the Traefik entry then click the 3 circles to open the menu.
Click on “Edit Route Settings”.

Confirm 10.10.10.10/32 and accept the new route to activate, now Traefik can talk to your DNS server through Tailscale.

The second step is to allow Tailscale to use IP forwarding in Linux, these instructions can be found here.

After these have been configured you will need to return to the Tailscale admin console to configure the Tailscale DNS settings.
Under nameservers click Add nameserver.
In the pop up enter your home Adguard DNS 10.10.10.10, check the box for split DNS and enter your domain.


Hit save, and now you should have an active split dns while connected to tailscale.
Add your mobile device to tailscale and you will be able to access secure web apps from your phone wherever you are.

Portainer and Authentik / Traefik failling to login due to UFW

I use Authentik with Traefik. This is also assuming you followed the official Authentik intergration guide found here.

This is the screen that I had when logging into Authentik:


On the right there is a 404 error when inspecting the console, which leads to the 401 error – unauthorized. After lots of trial and error, turns out it was due to Uncomplicated Firewall (UFW) blocking the port access of 443 (https).

They are both on the same docker network, I also use labels for traefik. I tried using my config setup in traefik with no luck either. Disabling UFW to test the login process.

sudo ufw disable


This worked! So all that was left was to re-enable authentik and add in the two rules for port 80 (http) and port 443 (https) then reload UFW to enforce the changes

sudo ufw enable
sudo ufw allow 80/tcp comment 'Allow HTTP for Traefik'
sudo ufw allow 443/tcp comment 'Allow HTTPS for Traefik'
sudo ufw reload

Proxmox cluster with Traefik

With Traefik you can load balance between the different nodes of your cluster with one web page.

ie, https://proxmox.richay.au could access either one of the three nodes I have available, but it comes with one issue, you wont be able to use the shell as the websocket it uses needs to be upgraded in Traefik.

This is my dynamic config.yaml in traefik

http:
  routers:
    proxmox:
      entryPoints:
        - "https"
      rule: "Host(`proxmox.richay.au`)"
      middlewares:
        - https-redirectscheme
        - websocket-upgrade
      tls: {}
      service: proxmox
 
  services:
    proxmox:
      loadBalancer:
        sticky:
          cookie: {}
        servers:
          - url: "https://10.10.10.1:8006" # IP of node 1
          - url: "https://10.10.10.2:8006" # IP of node 2
          - url: "https://10.10.10.3:8006" # IP of node 3
        passHostHeader: true

  middlewares:
    https-redirectscheme:
      redirectScheme:
        scheme: https
        permanent: true
    websocket-upgrade:
      headers:
        CustomRequestHeaders:
          Upgrade: websocket
          Connection: Upgrade

          


This will allow the proxmox shells to work 🙂

Authentik and Home Assistant with working Companion App solution using Traefik proxy

I absolutely love the fact I can log into authentik and then bypass all app login screens for instant access. This was a slight challenge with Home Assistant as placing this behind Authentik behind this would break the phone companion app. Here is a quick guide on how I overcame this.

This was solved by setting two pathways leading back to my home assistant in traefik, one being behind authentik for the SSO, and the other using the default home assistant login screen for the companion app.

This requires a few things first:
Traefik setup with dynamic config
HTTP Header Authentication integration for home assistant found here
Authentik setup with provider and application, instructions found here

The added lines I used in configuration.yaml in Home Assistant

http:
  use_x_forwarded_for: true
  trusted_proxies:
    - 10.10.10.0/24 # Change to your home network
    - 172.22.0.0/16 # Change to your traefik proxy network

auth_header:
  username_header: X-authentik-username


The config.yaml for my traefik
Please not there is two routers for the one service, one being behind Authentik (/auth) and the other bypassing Authentik. There is also a path prefix for the outpost so there is no 404 error.

http:
  routers:
    # Router for SSO - PROTECTED by Authentik
    home-assistant:
      entryPoints:
        - "https"
      rule: "Host(`home-assistant.richay.au`) && PathPrefix(`/auth`) && !PathPrefix(`/auth/token`) || PathPrefix(`/outpost.goauthentik.io`))" # Change host domain
      middlewares:
        - https-redirectscheme
        - authentik
      tls: {}
      service: home-assistant
    # Router for Companion App - UNPROTECTED by Authentik
    home-companion:
      entryPoints:
        - "https"
      rule: "Host(`home-companion.richay.au`) || Host(`home-assistant.richay.au`)" # Change host domain
      middlewares:
        - https-redirectscheme
      tls: {}
      service: home-assistant 
 
  services:
    home-assistant:
      loadBalancer:
        servers:
          - url: "http://10.10.10.10:8123" # change this to your IP of your Home Assistant
        passHostHeader: true

  middlewares:
    authentik:
      forwardAuth:
        address: "http://authentik-server:9000/outpost.goauthentik.io/auth/traefik"
        trustForwardHeader: true
        authResponseHeaders:
          - X-authentik-username
          - X-authentik-groups
          - X-authentik-email
          - X-authentik-name
          - X-authentik-uid
          - X-authentik-jwt
          - X-authentik-meta-jwks
          - X-authentik-meta-outpost
          - X-authentik-meta-provider
          - X-authentik-meta-app
          - X-authentik-meta-version
          - authorization
    https-redirectscheme:
      redirectScheme:
        scheme: https
        permanent: true

          


When you select your server on the companion app, choose the
https://home-companion.richay.au option. This will allow the app to work.

When using a web browser, use https://home-assistant.richay.au for SSO access using Authentik.