Arbitrary wildcard subdomain, redirect to docker container

Hello.

I’m trying to use Traefik to serve several websites / web applications:

I’ve managed to get the base domain and fixed subdomain working, but not the arbitrary subdomain.

From reading the high level docs, the closest I’ve come to solving this is using regex patterns within the routers.

I’ve attached the docker-compose I’m working on, the problematic entity is the wildcard_site.

Any help or links to specific examples would be appreciated.

Thank you

Docker-compose file: https://pastebin.com/U1tkn1jw

version: "3"

services:
  reverse-proxy:
    image: traefik:v2.2.6
    command:
      - --api.insecure=true
      - --providers.docker=true
      - --providers.docker.exposedbydefault=false
    ports:
      - "80:80"
      - "443:443"
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock
    labels:
      - "traefik.enable=true"
      - "traefik.frontend.rule=Host:admin.example.io" # Dashboard @ http://admin.example.io
      - "traefik.frontend.entryPoints=https-admin"
      - "traefik.http.routers.api.rule=Host(`admin.example.io`)"
      - "traefik.http.routers.api.service=api@internal"

  main_site:
    image: containous/whoami
    labels:
      - "traefik.enable=true"
      - "traefik.http.routers.main_site.rule=Host(`example.io`)"  # Base site
      # - "traefik.backend=whoami"
      # - "traefik.frontend.priority=1"

  subdomain_site:
    image: containous/whoami
    labels:
      - "traefik.enable=true"
      - "traefik.http.routers.subdomain_site.rule=Host(`subdomain.example.io`)"  # Named subdomain site
      # - "traefik.backend=whoami"
      # - "traefik.frontend.priority=2"

  wildcard_site:
    image: containous/whoami
    labels:
      - "traefik.enable=true"
      # - "traefik.http.routers.wildcard_site.rule=Host(`*.example.io`)"
      - "traefik.http.routers.wildcard_site.tls.domains[0].main=example.io"  
      - "traefik.http.routers.wildcard_site.tls.domains[0].sans=*.example.io" # Abritary subdomain site
      # - "traefik.frontend.rule=HostRegexp:{subdomain:[a-z]+}.example.io"
      # - "traefik.frontend.priority=3"

Have you tried a PathPrefix(`/`) rule?

1 Like

Hello, thanks for the response.

It’s not an issue with the path but rather the matching/mapping of the domain itself to a container. I have tried your suggestion, qualifying each container with an explict PathPrefix(/) rule and seems to have had no effect, as the path would be “/” for all requests to each of these containers regardless.

Using a PathPrefix of / on the wildcard_site would catch any request not matching another rule(they all have higher priority). As you have a wildcard san that should just work.

Hi @cakiwi

The PathPrefix did work along with setting appropriate priorities for the routers.

Thank you for the advice.

version: "3"

services:
  reverse-proxy:
    image: traefik:v2.2.6
    command:
      - --api.insecure=true
      - --providers.docker=true
      - --providers.docker.exposedbydefault=false
      - --providers.file.filename=/dynamic.yaml
      - --entrypoints.web.address=:80
      - --entrypoints.web-secured.address=:443
      - --certificatesresolvers.mytlschallenge.acme.tlschallenge=true
      - --certificatesresolvers.mytlschallenge.acme.email=hello@example.io
      - --certificatesresolvers.mytlschallenge.acme.storage=/certs/acme.json
      - --certificatesresolvers.mytlschallenge.acme.dnschallenge.provider=digitalocean
    ports:
      - "80:80"
      - "443:443"
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock
      - ./dynamic.yaml:/dynamic.yaml
      - ./certs:/certs
    labels:
      - "traefik.enable=true"
      - "traefik.frontend.rule=Host:admin.example.io" # Dashboard @ http://admin.example.io
      - "traefik.frontend.entryPoints=https-admin"
      - "traefik.http.routers.api.rule=Host(`admin.example.io`)"
      - "traefik.http.routers.api.service=api@internal"

  # Base site (example.io)
  main_site:
    image: adamgolab/hello-world
    environment:
      PORT: 8000
      WORLD: "Main"
    ports:
      - "8000:8000"
    labels:
      - "traefik.enable=true"
      - "traefik.http.routers.main_site.rule=Host(`example.io`)"
      - "traefik.http.routers.main_site.entrypoints=web"
      - "traefik.http.routers.main_site.priority=3"
      - "traefik.http.routers.main_site.middlewares=redirect@file"

      - "traefik.http.routers.main_site_secured.rule=Host(`example.io`)"
      - "traefik.http.routers.main_site_secured.entrypoints=web-secured"
      - "traefik.http.routers.main_site_secured.tls=true"
      - "traefik.http.routers.main_site_secured.tls.certresolver=mytlschallenge"

  # Named subdomain site (subdomain.example.io)
  subdomain_site:
    image: adamgolab/hello-world
    environment:
      PORT: 8000
      WORLD: "Subdomain"
    ports:
      - "8500:8000"
    labels:
      - "traefik.enable=true"
      - "traefik.http.routers.subdomain_site.rule=Host(`subdomain.example.io`)"
      - "traefik.http.routers.subdomain_site.entrypoints=web"
      - "traefik.http.routers.subdomain_site.priority=2"
      - "traefik.http.routers.subdomain_site.middlewares=redirect@file"

      - "traefik.http.routers.subdomain_site_secured.rule=Host(`subdomain.example.io`)"
      - "traefik.http.routers.subdomain_site_secured.entrypoints=web-secured"
      - "traefik.http.routers.subdomain_site_secured.tls=true"
      - "traefik.http.routers.subdomain_site_secured.tls.certresolver=mytlschallenge"

  # Abritary subdomain site (*.example.io)
  wildcard_site:
    image: adamgolab/hello-world
    environment:
      PORT: 8000
      WORLD: "Wildcard"
    ports:
      - "8501:8000"
    labels:
      - "traefik.enable=true"
      - "traefik.http.routers.wildcard_site.rule=Host(`example.io`)"
      - "traefik.http.routers.wildcard_site.entrypoints=web"
      - "traefik.http.routers.wildcard_site.rule=PathPrefix(`/`)"
      - "traefik.http.routers.wildcard_site.priority=1"
      - "traefik.http.routers.wildcard_site.middlewares=redirect@file"

      - "traefik.http.routers.wildcard_site_secured.rule=Host(`example.io`)"
      - "traefik.http.routers.wildcard_site_secured.entrypoints=web-secured"
      - "traefik.http.routers.wildcard_site_secured.rule=PathPrefix(`/`)"
      - "traefik.http.routers.wildcard_site_secured.tls=true"
      - "traefik.http.routers.wildcard_site_secured.tls.certresolver=mytlschallenge"
      - "traefik.http.routers.wildcard_site_secured.tls.domains[0].main=example.io"
      - "traefik.http.routers.wildcard_site_secured.tls.domains[0].sans=*.example.io"
1 Like

It is likely you don't have to set priority or that you only have to set it on the wildcard_site.

Rule priority is defined by then length of the rule, and I was pretty sure that the others were longer than PathPrefix(`/`)

In fact it looks like you only set priority on the routers on the web entrypoint. So you are infact doing that on the routers with tls enabled.