Обсуждение Traefik 2.0

Всем привет,

Я переезжаю на новый сервер и хочу использовать Traefik 2.0 в качестве обратного прокси. Сейчас у меня возникают трудности с новой конфигурацией. Я добавил раздел в конец файла app.yml. (Источник: Discourse behind Traefik 🐁)

...

expose:
  - "8060:80"   # http
  - "8070:443" # https

...

docker_args:
  - "--network=web"
  - "--expose=8060"
  - "-l traefik.enable=true"
  - "-l traefik.http.routers.forum.rule=Host(`forum.example.com`)"
  - "-l traefik.http.routers.forum.entrypoints=websecure"
  - "-l traefik.http.routers.forum.tls=true"
  - "-l traefik.http.routers.forum.tls.certresolver=mytlschallenge"
  - "-l traefik.http.services.forum.loadbalancer.server.port=8060"
  - "-l traefik.docker.network=web"

Похоже, это не работает. При открытии маршрута я получаю ошибку Bad Gateway. Если же перейти напрямую по адресу ip_adress:8060, Discourse открывается.

У кого-нибудь есть опыт работы с Traefik 2.0?

Спасибо!

После некоторых попыток я смог решить проблему самостоятельно.

Для справки прикрепляю мой app.yml:

...

templates:
  - "templates/postgres.template.yml"
  - "templates/redis.template.yml"
  - "templates/web.template.yml"
  - "templates/web.ratelimited.template.yml"
## Раскомментируйте эти две строки, если хотите добавить Lets Encrypt (https)
  #- "templates/web.ssl.template.yml"
  #- "templates/web.letsencrypt.ssl.template.yml"
  #- "templates/web.socketed.template.yml" 

## Какие TCP/IP порты должен открывать этот контейнер?
## Если вы хотите, чтобы Discourse использовал порт совместно с другим веб-сервером, например Apache или nginx,
## см. https://meta.discourse.org/t/17247 для деталей
#expose:
#  - "8060:80"   # http
#  - "8070:443" # https

...

docker_args:
  - "--network=web"
  #- "--expose=8060"
  - "-l traefik.enable=true"
  - "-l traefik.http.routers.forum.rule=Host(`forum.example.com`)"
  - "-l traefik.http.routers.forum.entrypoints=websecure"
  - "-l traefik.http.routers.forum.tls=true"
  - "-l traefik.http.routers.forum.tls.certresolver=mytlschallenge"
  - "-l traefik.http.services.forum.loadbalancer.server.port=80"
  - "-l traefik.docker.network=web"

Почему необходимо использовать docker_args? Согласно GitHub - discourse/discourse_docker: A Docker image for Discourse · GitHub, это должно работать следующим образом:

labels:
  monitor: 'true'
  app_name: {{config}}_discourse

Добавление меток к текущему контейнеру. В приведённом примере к опциям при запуске контейнера будут добавлены --l monitor=true -l app_name=dev_discourse.

Кроме того, где объясняется docker_args?

@Cameron_D
Как вы узнали, что docker_args — это правильный путь?

Мне так и не удалось заставить секцию с метками работать как ожидалось. Я точно не знаю, почему она перестала работать, или была ли проблема исправлена, так как я оставил свою конфигурацию без изменений, потому что она работает.

Привет,
можешь поделиться своей конфигурацией Traefik?

У меня возникает ошибка 302: происходит автоматическое перенаправление на HTTPS, а затем всё замирает…
В панели управления Traefik всё отображается как в порядке.

вот мой docker-compose.yml
version: "3.7"
    services:
      traefik-reverse-proxy:   
        # Официальный образ Docker Traefik v2.0
        image: traefik:latest #traefik:v2.0
        container_name: "traefik"       
        command:
          # Указать Traefik слушать Docker 
          - --providers.docker          # (По умолчанию: true)
          # Включить API/панель управления / (указать конечную точку Docker для общения с API Docker)
          - --api=true                    # (По умолчанию: false)
          # Активировать панель управления. 
          - --api.dashboard               # (По умолчанию: true)
          # Включить веб-интерфейс / Traefik по умолчанию слушает порт 8080 для API запросов / Активировать API напрямую на entryPoint с именем traefik. (По умолчанию: false) --> порт '8080'v= entryPoint 'traefik', переопределяет --api
          - --api.insecure=true         # (По умолчанию: false) 
          # Включить дополнительные конечные точки для отладки и профилирования. 
          - --api.debug=true            # (По умолчанию: false)
          # Установить уровень отладки лога
          - --log.level=DEBUG    
          # Запись accesslog
          - --accesslog=true    
          # Определение места хранения внутри контейнера, файл лога записывается внутри контейнера. Чтобы сделать его доступным на хосте, он монтируется, см. раздел volumes
          - --log.filePath=/var/traefik-container/logs/traefik-log.log
          - --accesslog.filepath=/var/traefik-container/logs/traefik-access.log
          # Переопределить имя entryPoint по умолчанию для порта 80 на "web"
          - --entrypoints.web.address=:80
          # Объявить имя entryPoint для порта 443
          - --entrypoints.websecure.address=:443
          #--providers.docker.endpoint=unix:///var/run/docker.sock    
          # Let's Encrypt
          - --certificatesresolvers.mytlschallenge.acme.tlschallenge=true
          - --certificatesresolvers.mytlschallenge.acme.email=my@email.com
          - --certificatesresolvers.mytlschallenge.acme.storage=/var/traefik-container/letsencrypt/acme.json
        ports:
          # Порт HTTP
          - "80:80"
          # Порт HTTPS
          - "443:443"
          # Веб-интерфейс (включен через --api.insecure=true)
          - "8080:8080"
        volumes:        # синтаксис --> расположение-на-хосте:путь-в-контейнере
          # Чтобы Traefik мог слушать события Docker
          - /var/run/docker.sock:/var/run/docker.sock
          - /var/traefik/log:/var/traefik-container/logs
          - /var/traefik/letsencrypt:/var/traefik-container/letsencrypt
        labels:
          - "traefik.enable=true"
          - "traefik.docker.network=bridge_proxy_traefikv2"
          - "traefik.http.routers.traefikv2.rule=Host(`traefik.mydomain.community`)"
          - "traefik.http.routers.traefikv2.entrypoints=web"
          - "traefik.http.services.traefikv2.loadBalancer.server.port=80"

        networks:
          - traefik
          #- default
          
       #Tiny Go веб-сервер, выводящий информацию об ОС и HTTP-запросы в вывод
    #  whoami:
    #    image: "containous/whoami"
    #    container_name: "whoami"
    #    labels:
    #      - "traefik.enable=true"
    #      - "traefik.docker.network=bridge_proxy_traefikv2"
    #      - "traefik.http.routers.whoami.rule=Host(`mydomain.community`)"
    #      - "traefik.http.routers.whoami.entrypoints=web"
    #      - "traefik.http.services.whoami.loadBalancer.server.port=80"
    #    networks:
    #      - traefik
    #      #- default
          
      whoami_sub:
        image: "containous/whoami"
        container_name: "whoami_sub"
        labels:
          - "traefik.enable=true"
          - "traefik.name=whoami_sub"
          - "traefik.docker.network=bridge_proxy_traefikv2"
          - "traefik.http.routers.whoami_sub.rule=Host(`whoami.mydomain.community`)"
          - "traefik.http.routers.whoami_sub.entrypoints=web"
          #- "traefik.http.services.whoami_sub.loadBalancer.server.port=80"
        networks:
          - traefik
          - default

    networks:
      traefik:
        external:
          name: bridge_proxy_traefikv2
вот мой app.yml для Discourse
## это шаблон контейнера Docker Discourse "всё в одном", автономный
##
## После внесения изменений в этот файл ОБЯЗАТЕЛЬНО выполните пересборку
## /var/discourse/launcher rebuild app
##
## БУДЬТЕ *ОЧЕНЬ* ОСТОРОЖНЫ ПРИ РЕДАКТИРОВАНИИ!
## YAML-ФАЙЛЫ ЧРЕЗВЫЧАЙНО ЧУВСТВИТЕЛЬНЫ К ОШИБКАМ В ПРОБЕЛАХ ИЛИ ВЫРАВНИВАНИИ!
## посетите http://www.yamllint.com/, чтобы при необходимости проверить этот файл

templates:
  - "templates/postgres.template.yml"
  - "templates/redis.template.yml"
  - "templates/web.template.yml"
  - "templates/web.ratelimited.template.yml"
## Раскомментируйте эти две строки, если хотите добавить Lets Encrypt (https)
  - "templates/web.ssl.template.yml"
  - "templates/web.letsencrypt.ssl.template.yml"

## какие TCP/IP-порты должен открывать этот контейнер?
## Если вы хотите, чтобы Discourse использовал тот же порт, что и другой веб-сервер, например Apache или nginx,
## см. https://meta.discourse.org/t/17247 для деталей
expose:
#  - "80:80"   # http
#  - "443:443" # https

params:
  db_default_text_search_config: "pg_catalog.english"

  ## Установите db_shared_buffers максимум в 25% от общего объема памяти.
  ## будет установлено автоматически при загрузке на основе обнаруженной оперативной памяти, или вы можете переопределить
  db_shared_buffers: "128MB"

  ## может улучшить производительность сортировки, но увеличивает использование памяти на соединение
  #db_work_mem: "40MB"

  ## Какую ревизию Git должен использовать этот контейнер? (по умолчанию: tests-passed)
  #version: tests-passed

labels:
  app_name:                                                 discourse  
  traefik.enable:                                           true
  traefik.docker.network:                                   bridge_proxy_traefikv2  
  traefik.http.services.forum.loadbalancer.server.port:     80
  traefik.http.routers.forum.rule:                          Host(`forum.mydomain.community`)
  traefik.http.routers.forum.entrypoints:                   websecure
  traefik.http.routers.forum.tls:                           true
  traefik.http.routers.forum.tls.certresolver:              mytlschallenge
     
docker_args:
  - "--network=bridge_proxy_traefikv2"
 # - "-l traefik.enable=true"
 # - "-l traefik.http.routers.forum.rule=Host(`fairbnb.community`)"
 # - "-l traefik.http.routers.forum.entrypoints=websecure"
 # - "-l traefik.http.routers.forum.tls=true"
 # - "-l traefik.http.routers.forum.tls.certresolver=mytlschallenge"
 # - "-l traefik.http.services.forum.loadbalancer.server.port=80"
 # - "-l traefik.docker.network=web"
  
env:
  LANG: en_US.UTF-8
  # DISCOURSE_DEFAULT_LOCALE: en

  ## Сколько одновременных веб-запросов поддерживается? Зависит от памяти и ядер CPU.
  ## будет установлено автоматически при загрузке на основе обнаруженных процессоров, или вы можете переопределить
  UNICORN_WORKERS: 2

  ## TODO: Доменное имя, на которое будет отвечать этот экземпляр Discourse
  ## Обязательно. Discourse не будет работать с чистым IP-адресом.
  DISCOURSE_HOSTNAME: forum.fairbnb.community

  ## Раскомментируйте, если хотите, чтобы контейнер запускался с тем же
  ## именем хоста (-h опция), что указано выше (по умолчанию "$hostname-$config")
  #DOCKER_USE_HOSTNAME: true

  ## TODO: Список email-адресов через запятую, которые станут администраторами и разработчиками
  ## при первой регистрации, например 'user1@example.com,user2@example.com'
  DISCOURSE_DEVELOPER_EMAILS: 'discourse@myemail.com'

  ## TODO: SMTP-сервер, используемый для проверки новых учетных записей и отправки уведомлений
  ## АДРЕС SMTP, имя пользователя и пароль обязательны
  # ВНИМАНИЕ: символ '#' в пароле SMTP может вызвать проблемы!
  DISCOURSE_SMTP_ADDRESS: smtp.zoho.eu
  DISCOURSE_SMTP_PORT: 587
  DISCOURSE_SMTP_USER_NAME: discourse@myemail.com
  DISCOURSE_SMTP_PASSWORD: "tempPassword"
  #DISCOURSE_SMTP_ENABLE_START_TLS: true           # (опционально, по умолчанию true)

  ## Если вы добавили шаблон Lets Encrypt, раскомментируйте ниже, чтобы получить бесплатный SSL-сертификат
  LETSENCRYPT_ACCOUNT_EMAIL: me@example.com

  ## Адрес http или https CDN для этого экземпляра Discourse (настроен на получение)
  ## см. https://meta.discourse.org/t/14857 для деталей
  #DISCOURSE_CDN_URL: https://discourse-cdn.example.com
  
## Контейнер Docker не имеет состояния; все данные хранятся в /shared
volumes:
  - volume:
      host: /var/discourse/shared/standalone
      guest: /shared
  - volume:
      host: /var/discourse/shared/standalone/log/var-log
      guest: /var/log

## Плагины размещаются здесь
## см. https://meta.discourse.org/t/19157 для деталей
hooks:
  after_code:
    - exec:
        cd: $home/plugins
        cmd:
          - git clone https://github.com/discourse/docker_manager.git

## Любые пользовательские команды для выполнения после сборки
run:
  - exec: echo "Начало пользовательских команд"
  ## Если вы хотите установить адрес электронной почты 'From' для вашей первой регистрации, раскомментируйте и измените:
  ## После получения первого письма о регистрации закомментируйте строку обратно. Она нужна только один раз.
  - exec: rails r "SiteSetting.notification_email='discourse@zoho.fairbnb.community'"
  - exec: echo "Конец пользовательских команд"

There were problems make Traefik’s dashboard available via a subdomain but discourse is still not reachable, see https://community.containo.us/t/discourse-instance-is-handled-by-api-internal-is-that-normal/3690/1
Here are my working configs.

  1. With my comments

    docker-compose: traefikV2_docker-compose.yaml
    # https://stackoverflow.com/questions/49718431/docker-compose-yml-file-naming-convention
    version: "3.7"
    
    services:
      traefik-reverse-proxy:   
        # The official v2.0 Traefik docker image
        #image: traefik:latest 
        #image: traefik:v2.0
        image: traefik:v2.1.1
        container_name: traefik
        #command: 
        ## to work with custom traefik configuration file you have to declare the local path and mount the location on the host, see volume section
        #- --configFile=/etc/traefik/traefik-config.yaml
        
        ports:
          # The HTTP port
          - 80:80
          # The HTTPS port
          - 443:443
          # The Web UI (enabled by --api.insecure=true)
          #- "8080:8080"
        
        volumes:         
        # syntax --> host-location:path-in-container, see https://docs.docker.com/compose/compose-file/#volumes
          # So that Traefik can listen to the Docker events
          - /var/run/docker.sock:/var/run/docker.sock
          # mount the location for the log files to the host, so that I can read them on the host
            # chosen based on https://unix.stackexchange.com/questions/104936/where-are-all-the-posibilities-of-storing-a-log-file
          - /var/log/traefik:/var/log
          # mount the location for the certifcates to the host, so that I can read them on the host
            #based on https://www.getpagespeed.com/server-setup/ssl-directory and https://serverfault.com/questions/62496/ssl-certificate-location-on-unix-linux
          - /etc/ssl/certs/traefik/letsencrypt:/etc/ssl/certs/letsencrypt
          # I use a customized "traefik.toml", so it has to be mounted into the traefik container (or stored there), combine 
            # https://stackoverflow.com/questions/47382756/why-is-my-traefik-toml-file-not-be-read-by-docker-compose-configuration
            # https://stackoverflow.com/questions/57200728/can-the-default-location-of-the-traefik-configuration-file-be-changed-in-the-off
            # https://stackoverflow.com/questions/45902133/how-to-use-custom-traefik-toml-file
            # https://docs.traefik.io/getting-started/configuration-overview/
          - /opt/traefik/traefik-config.yaml:/etc/traefik/traefik.yaml
        
        labels:
          - traefik.enable=true
          #- "traefik.docker.network=bridge_proxy_traefikv2"
          - traefik.http.routers.traefik_dashboard-router.rule=Host(`traefik.fairbnb.community`)
          - traefik.http.routers.traefik_dashboard-router.entrypoints=web
          #- "traefik.http.services.traefik_dashboard-service.loadBalancer.server.port=8080"
          - traefik.http.routers.traefik_dashboard-router.service=api@internal
    
        networks:
          - traefik
          #- default
          
       #Tiny Go webserver that prints os information and HTTP request to output
       #  whoami:
       #    image: "containous/whoami"
       #    container_name: "whoami"
       #    labels:
       #      - "traefik.enable=true"
       #      - "traefik.docker.network=bridge_proxy_traefikv2"
       #      - "traefik.http.routers.whoami-router.rule=Host(`fairbnb.community`)"
       #      - "traefik.http.routers.whoami-router.entrypoints=web"
       #      - "traefik.http.services.whoami-service.loadBalancer.server.port=80"
       #    networks:
       #      - traefik
       #      #- default
          
      whoami_viaSubdomain:
        image: "containous/whoami"
        container_name: "whoami_viaSubdomain"
        labels:
          - traefik.enable=true
          - traefik.docker.network=bridge_proxy_traefikv2
          - traefik.http.routers.whoami_viaSubdomain-router.rule=Host(`whoami.fairbnb.community`)
          - traefik.http.routers.whoami_viaSubdomain-router.entrypoints=web
          #- "traefik.http.services.whoami_viaSubdomain-service.loadBalancer.server.port=80"
        networks:
          - traefik
          #- default
    
    networks:
      traefik:
        external:
          name: bridge_proxy_traefikv2
           
           
    
    
    
    Traefik configuration: traefik-config.yaml
    global:
      checkNewVersion: true
    #  sendAnonymousUsage: true
    #serversTransport:
    #  insecureSkipVerify: true
    #  rootCAs:
    #  - foobar
    #  maxIdleConnsPerHost: 42
    #  forwardingTimeouts:
    #    dialTimeout: 42
    #    responseHeaderTimeout: 42
    #    idleConnTimeout: 42
    
    entryPoints:
      web:
        address: :80
        #transport:
        #  lifeCycle:
        #    requestAcceptGraceTimeout: 42
        #    graceTimeOut: 42
        #  respondingTimeouts:
        #    readTimeout: 42
        #    writeTimeout: 42
        #    idleTimeout: 42
        #proxyProtocol:
        #  insecure: true
        #  trustedIPs:
        #  - foobar
        #  - foobar
        #forwardedHeaders:
        #  insecure: true
        #  trustedIPs:
        #  - foobar
        #  - foobar
      websecure:
        address: :443
      #traefik_dashboard:
         #address: ":8080"     
    
    api: 
    #api: {}   
    # Activate dashboard. 
      ## Enables the web UI @ port 8080/ Traefik will listen on port 8080 by default for API request. / Activate API directly on the entryPoint named traefik. (Default: false) --> port '8080'v= entryPoint 'traefik', overrides --api  
      #insecure: true
      ## Activate dashboard. (Default: true)
      # dashboard: true
      # Enable additional endpoints for debugging and profiling. 
       debug: true    
      
    providers:
    # providersThrottleDuration: 42
      docker:
        #constraints: foobar
        ## Watch provider. (Default: true)
        #watch: true
        ## Docker server endpoint. Can be a tcp or a unix socket endpoint. (Default: unix:///var/run/docker.sock)
        #endpoint: unix:///var/run/docker.sock
        #defaultRule: foobar
        #tls:
          #ca: foobar
          #caOptional: true
          #cert: foobar
          #key: foobar
          #insecureSkipVerify: true
        # Expose containers by default. (Default: true) / By default, routes for all detected containers are creates. ITo limit the scope of Traefik's service discovery, i.e. disallow route creation for some containers, you can do so in two different ways: gerneric exposedByDefault (overriden by traefik.enable), or with a finer granularity mechanism based on constraints.
        exposedByDefault: false
        #useBindPortIP: true
        #swarmMode: true
        # Default Docker network used.
        network: bridge_proxy_traefikv2
        # swarmModeRefreshSeconds: 42  
    
    not used currently-metrics:    # this is only hear to fold/unfold the commented region in  Notepad++
    #metrics:
    #  prometheus:
    #    buckets:
    #    - 42
    #    - 42
    #    addEntryPointsLabels: true
    #    addServicesLabels: true
    #    entryPoint: foobar
    #    manualRouting: true
    #  datadog:
    #    address: foobar
    #    pushInterval: 42
    #    addEntryPointsLabels: true
    #    addServicesLabels: true
    #  statsD:
    #    address: foobar
    #    pushInterval: 42
    #    addEntryPointsLabels: true
    #    addServicesLabels: true
    #    prefix: traefik
    #  influxDB:
    #    address: foobar
    #    protocol: foobar
    #    pushInterval: 42
    #    database: foobar
    #    retentionPolicy: foobar
    #    username: foobar
    #    password: foobar
    #    addEntryPointsLabels: true
    #    addServicesLabels: true
    #ping:
    #  entryPoint: foobar
    #  manualRouting: true
       #
    log:
    #Traefik's log file 
      # set debug level of the log
      level: DEBUG
      # defining the storage location inside the container, log file is written inside the container. To make it avaiable on the host it is mounted, see volumes section in docker-compose file
        # chosen based on https://unix.stackexchange.com/questions/104936/where-are-all-the-posibilities-of-storing-a-log-file
      filePath: /var/log/traefik-log.log
      # Traefik log format: json | common (Default: common)
      #format: common
    
    accessLog:      
    # Logging access attempts   
      # defining the storage location inside the container, log file is written inside the container. To make it avaiable on the host it is mounted, see volumes section in docker-compose file
        # chosen based on https://unix.stackexchange.com/questions/104936/where-are-all-the-posibilities-of-storing-a-log-file  
      filePath: /var/log/traefik-access.log
      # Access log format: json | common (Default: common)
      #format: common
    #  filters:
    #    statusCodes:
    #    - foobar
    #    - foobar
    #    retryAttempts: true
    #    minDuration: 42
    #  fields:
    #    defaultMode: foobar
    #    names:
    #      name0: foobar
    #      name1: foobar
    #    headers:
    #      defaultMode: foobar
    #      names:
    #        name0: foobar
    #        name1: foobar
    #  bufferingSize: 42
       #
       
    not used currently-tracing:    # this is only hear to fold/unfold the commented region in  Notepad++
    #tracing:   
    #  serviceName: foobar
    #  spanNameLimit: 42
    #  jaeger:
    #    samplingServerURL: foobar
    #    samplingType: foobar
    #    samplingParam: 42
    #    localAgentHostPort: foobar
    #    gen128Bit: true
    #    propagation: foobar
    #    traceContextHeaderName: foobar
    #    collector:
    #      endpoint: foobar
    #      user: foobar
    #      password: foobar
    #  zipkin:
    #    httpEndpoint: foobar
    #    sameSpan: true
    #    id128Bit: true
    #    sampleRate: 42
    #  datadog:
    #    localAgentHostPort: foobar
    #    globalTag: foobar
    #    debug: true
    #    prioritySampling: true
    #    traceIDHeaderName: foobar
    #    parentIDHeaderName: foobar
    #    samplingPriorityHeaderName: foobar
    #    bagagePrefixHeaderName: foobar
    #  instana:
    #    localAgentHost: foobar
    #    localAgentPort: 42
    #    logLevel: foobar
    #  haystack:
    #    localAgentHost: foobar
    #    localAgentPort: 42
    #    globalTag: foobar
    #    traceIDHeaderName: foobar
    #    parentIDHeaderName: foobar
    #    spanIDHeaderName: foobar
    #    baggagePrefixHeaderName: foobar
       #
    not used currently-hostResolver:     # this is only hear to fold/unfold the commented region in  Notepad++
    #hostResolver:
    #  cnameFlattening: true
    #  resolvConfig: foobar
    #  resolvDepth: 42
      #
    certificatesResolvers:
      tlsChallenge_letsencrypt:
        acme:
          email: my.secret@gmail.com
          # CA server to use. (Default: https://acme-v02.api.letsencrypt.org/directory)
          #caServer:        
          # location chosen based on  on https://www.getpagespeed.com/server-setup/ssl-directory and https://serverfault.com/questions/62496/ssl-certificate-location-on-unix-linux
          storage: /etc/ssl/certs/letsencrypt/acme.json
          # KeyType used for generating certificate private key. Allow value 'EC256', 'EC384', 'RSA2048', 'RSA4096', 'RSA8192'. (Default: RSA4096)
          #keyType: {}         
          #dnsChallenge:
            # provider: foobar
            # delayBeforeCheck: 42
            # resolvers:
            # - foobar
            # - foobar
            # disablePropagationCheck: true
          #httpChallenge:
            # entryPoint: foobar
          tlsChallenge: {}
      #CertificateResolver1:
      #  acme:
      #    email: my.secret@gmail.com
      #    caServer: foobar
      #    storage: foobar
      #    keyType: foobar
      #    dnsChallenge:
      #      provider: foobar
      #      delayBeforeCheck: 42
      #      resolvers:
      #      - foobar
      #      - foobar
      #      disablePropagationCheck: true
      #    httpChallenge:
      #      entryPoint: foobar
      #    tlsChallenge: {}
    
  2. Without my comments

    docker-compose: traefikV2_docker-compose.yaml
    root@Ubuntu18:/opt/10_docker-compose.yml-files# cat traefikV2_docker-compose.yaml | grep -v "#"
    version: "3.7"
    
    services:
      traefik-reverse-proxy:
        image: traefik:v2.1.1
        container_name: traefik
    
        ports:
          - 80:80
          - 443:443
    
        volumes:
          - /var/run/docker.sock:/var/run/docker.sock
          - /var/log/traefik:/var/log
          - /etc/ssl/certs/traefik/letsencrypt:/etc/ssl/certs/letsencrypt
          - /opt/traefik/traefik-config.yaml:/etc/traefik/traefik.yaml
    
        labels:
          - traefik.enable=true
          - traefik.http.routers.traefik_dashboard-router.rule=Host(`traefik.fairbnb.community`)
          - traefik.http.routers.traefik_dashboard-router.entrypoints=web
          - traefik.http.routers.traefik_dashboard-router.service=api@internal
    
        networks:
          - traefik
    
    
      whoami_viaSubdomain:
        image: "containous/whoami"
        container_name: "whoami_viaSubdomain"
        labels:
          - traefik.enable=true
          - traefik.docker.network=bridge_proxy_traefikv2
          - traefik.http.routers.whoami_viaSubdomain-router.rule=Host(`whoami.fairbnb.community`)
          - traefik.http.routers.whoami_viaSubdomain-router.entrypoints=web
        networks:
          - traefik
    
    networks:
      traefik:
        external:
          name: bridge_proxy_traefikv2
    
    
    Traefik configuration: traefik-config.yaml
    root@Ubuntu18:/opt/traefik# cat traefik-config.yaml | grep -v "#"
    global:
      checkNewVersion: true
    
    entryPoints:
      web:
        address: :80
      websecure:
        address: :443
    
    api:
       debug: true
    
    providers:
      docker:
        exposedByDefault: false
        network: bridge_proxy_traefikv2
    
    log:
      level: DEBUG
      filePath: /var/log/traefik-log.log
    
    accessLog:
      filePath: /var/log/traefik-access.log
    
    certificatesResolvers:
      tlsChallenge_letsencrypt:
        acme:
          email: my.secret@gmail.com
          storage: /etc/ssl/certs/letsencrypt/acme.json
          tlsChallenge: {}
    
    

@Cameron_D
@SvenC56
@Cerix
@huberfe
Извините, что упоминаю вас напрямую, но, похоже, вы — единственные задокументированные пользователи, запускающие Discourse за Traefik.
Несмотря на обещания, что Traefik позаботится обо всём, настройка, похоже, не так проста.
Пока что мне не удалось добиться успеха:

Рабочие URL:
Не работающий URL:

Я был бы крайне признателен, если бы вы могли поделиться полной конфигурацией Discourse и Traefik, чтобы я мог лучше разобраться в проблеме.

Мои конфигурации Traefik на момент публикации этого сообщения: Endless 502 / forwarding when calling dashboard via subdomain #6123 - #9 by PackElend - Traefik v2 - Traefik Labs Community Forum

Так как я сейчас только с мобильного, пожалуйста, проверьте мою конфигурацию здесь: traefik - SeAT Discourse Documentation
Обратите внимание: я запускал это только с версиями v1.6 и v1.7 Traefik. Не знаю, будет ли это работать с v2.

С этой настройкой несколько пользователей могли использовать мой плагин, Discourse и Traefik.

Примечание: я не прочитал ни одного сообщения в этой теме, просто отвечаю на уведомление.

Спасибо большое :slight_smile: :partying_face:

Я попробую перевести это с v1 на v2.

У меня уже есть представление о том, как это сделать, нужно несколько часов, чтобы всё обдумать.

Я предполагаю, что шаблоны для SSL и Let’s Encrypt закомментированы, поэтому раздел шаблонов выглядит так:

    templates:
          - "templates/postgres.template.yml"
          - "templates/redis.template.yml"
          - "templates/web.template.yml"
          - "templates/web.ratelimited.template.yml"
        ## Раскомментируйте эти две строки, если хотите добавить Lets Encrypt (https)
          #- "templates/web.ssl.template.yml"
          #- "templates/web.letsencrypt.ssl.template.yml"

Да, зачем вам нужно, чтобы контейнер Discourse управлял вашими SSL-сертификатами, если вы собираетесь включить прокси перед ним?

Пожалуйста, опубликуйте ваше решение, как только закончите.

В Run other websites on the same machine as Discourse - #301 см.

Я бы предложил также добавить раздел с шаблонами в документацию. Я заметил, что в моей установке они не были закомментированы, так как я сначала настраивал standalone-версию, чтобы получить app.yml. В самом начале я забыл их закомментировать. Это могло бы помочь избежать аналогичных проблем у других.

Конечно

Здесь не отображается статическая конфигурация Traefik, верно?

Отличные новости, все! http://forum.fairbnb.community/ доступен.

Это конфигурация с минимальными изменениями в app.yml для работы через http. В выходные я займусь настройкой https.

templates:
    - "templates/postgres.template.yml"
    - "templates/redis.template.yml"
    - "templates/web.template.yml"
    - "templates/web.ratelimited.template.yml"
    ## Раскомментируйте эти две строки, если хотите добавить Lets Encrypt (https)
    #- "templates/web.ssl.template.yml"
    #- "templates/web.letsencrypt.ssl.template.yml"  

expose:
      #- "80:80"   # http
      #- "443:443" # https

labels:
    traefik.enable:                                               true
    traefik.http.services.discourse.loadbalancer.server.port:     80
    traefik.http.routers.discourse.rule:                          Host(`forum.fairbnb.community`)
    traefik.http.routers.discourse.entrypoints:                   web

Для SSL просто настройте Traefik + Let’s Encrypt, вам не нужно использовать встроенный SSL Discourse.

Traefik будет управлять шифрованием для всех ваших контейнеров.

Сейчас я использую Traefik 1.6, поэтому пока не знаю, как включить это в Traefik v2.

Да, см. Run other websites on the same machine as Discourse, но похоже, что Discourse ожидает определённую информацию в заголовках, когда клиент обращается к прокси через HTTPS.

Я бегло ознакомился с этим. Постараюсь изложить это простым языком, понятным обычному пользователю.

Да, см. также Redirecting.... В начале я сразу настроил HTTPS, и создание сертификата прошло успешно, но на этом всё. Теперь мне нужно привести всё в соответствие с теми знаниями, которые я получил с тех пор.

То есть вы обращаетесь к своему форуму через HTTPS, верно?
Можете ли вы поделиться конфигурацией Traefik и Discourse? Чем больше информации будет предоставлено, тем проще мне будет разобраться в этом в выходные.
Руководство по миграции с v1 на v2 доступно по адресу Redirecting..., но я постараюсь объяснить это здесь в выходные.

OK, это мой файл traefik.toml, который не подходит для новой версии v2

defaultEntryPoints = ["http", "https"]

[web]
address = ":8080"
  [web.auth.basic]
  users = ["yourusername:yourpassword"]

[entryPoints]
  [entryPoints.http]
  address = ":80"
    [entryPoints.http.redirect]
      entryPoint = "https"
  [entryPoints.https]
  address = ":443"
    [entryPoints.https.tls]

[acme]
email = "XXXXXXXX"
storage = "acme.json"
entryPoint = "https"
onHostRule = true
onDemand = false
[acme.httpChallenge]
entryPoint = "http"
minVersion = "VersionTLS12"

часть конфигурации Discourse

templates:
  - "templates/postgres.template.yml"
  - "templates/redis.template.yml"
  - "templates/web.template.yml"
  - "templates/web.ratelimited.template.yml"

expose:
  - "80"   # http ------ просто экспонируем порты контейнера
  - "443" # https ------ вам не нужно экспонировать внешний порт хоста

labels:
  traefik.port: '80'
  traefik.backend: 'mycontainername'
  traefik.frontend.rule: 'Host:www.myhost.com'
  traefik.docker.network: 'mynetworkname'
docker_args:
  - "--network=mynetworkname"

с этой конфигурацией Traefik перенаправляет все запросы с порта 80 (http) на порт 443 (https),
включите принудительное использование HTTPS в панели администратора Discourse, чтобы избежать ошибок.

@pfaffman, не знаю, работает ли уведомление, если я процитирую ваш ответ в другой теме, поэтому я упоминаю вас.

Итак, ваша конфигурация выглядит как выше, но

и используете переменные окружения (этот подход упоминается в https://stackoverflow.com/questions/52804610/how-do-you-set-environmental-variables-for-traefik и https://blog.raveland.org/post/traefik_compose)

Итак, HTTPS работает :partying_face: :partying_face: :partying_face: :partying_face: :partying_face:
и я думаю, что понял, как всё это устроено :slight_smile:. В ближайшие дни я постараюсь записать это

моя конфигурация

извлечение app.yml для Discourse

templates:
  - "templates/postgres.template.yml"
  - "templates/redis.template.yml"
  - "templates/web.template.yml"
  - "templates/web.ratelimited.template.yml"
## Раскомментируйте эти две строки, если хотите добавить Lets Encrypt (HTTPS)
  #- "templates/web.ssl.template.yml"
  #- "templates/web.letsencrypt.ssl.template.yml"

## какие TCP/IP порты должен открывать этот контейнер?
## Если вы хотите, чтобы Discourse использовал порт совместно с другим веб-сервером, например Apache или nginx,
## см. https://meta.discourse.org/t/17247 для деталей
expose:
  #- "80:80"   # http
  #- "443:443" # https
  #- "80"      # http
  #- "443"     # https
  #- "40080:80"
  #- "40443:443"

labels:
  app_name:                                                                     discourse

  #----Метки Traefik------------------------
  traefik.enable:                                                               true
  traefik.docker.network:                                                       bridge_proxy_traefikv2

   #---РАЗДЕЛ HTTP-РОУТЕРА-------------------
  traefik.http.routers.discourse.rule:                                          Host(`forum.fairbnb.community`)
    #--РАЗДЕЛ HTTP--------------------------
  traefik.http.routers.discourse.entrypoints:                                   web
  traefik.http.routers.discourse.middlewares:                                   discourse_redirect2https         
  #traefik.http.services.discourse.loadbalancer.server.port:                     80  

   #---РАЗДЕЛ HTTPS-РОУТЕРА
  traefik.http.routers.discourse_secure.rule:                                   Host(`forum.fairbnb.community`)
    #--РАЗДЕЛ HTTPS
  traefik.http.routers.discourse_secure.entrypoints:                            websecure
  traefik.http.services.discourse_secure.loadbalancer.server.port:              80
    #--РАЗДЕЛ TLS
  traefik.http.routers.discourse_secure.tls.certresolver:                       tlsChallenge_letsencrypt

   #---РАЗДЕЛ МЕДИАВАРЕЙ перенаправление HTTP на HTTPS
  traefik.http.middlewares.discourse_redirect2https.redirectscheme.scheme:      https

docker_args:
  - "--network=bridge_proxy_traefikv2"
  
params:

Статическая конфигурация Traefik

global:
  checkNewVersion: true
entryPoints:
  web:
    address: :80
  websecure:
    address: :443

api:
   debug: true

providers:
  docker:
    exposedByDefault: false
    network: bridge_proxy_traefikv2

log:
  level: DEBUG
  filePath: /var/log/traefik-log.log

accessLog:
  filePath: /var/log/traefik-access.log

certificatesResolvers:
  tlsChallenge_letsencrypt:
    acme:
      email: my.secret@gmail.com
      storage: /etc/ssl/certs/letsencrypt/acme.json
      tlsChallenge: {}

Приветствую,

Я использовал этот пост в качестве руководства по настройке Discourse для работы с Traefik. У меня уже работает Traefik с другим веб-приложением.

При переходе на форум.private.com я получаю ошибку «404 страница не найдена».

Что-то, похоже, работает, потому что на панели управления Traefik во вкладке «Services» я вижу discourse@docker и discourse_secure@docker.

Однако во вкладке «Routers» ничего для Discourse нет.

Внесённые мной изменения в файл app.yml приведены ниже; они в значительной степени основаны на упомянутом выше посте. Я добавил открытый порт в аргументах Docker в конце файла, что, как мне казалось, открыло доступ к упомянутым выше службам. Буду признателен за любую помощь!

Traefik docker-compose
version: "3.3"

services:
  ################################################
  ####        Настройка прокси Traefik           #####
  ###############################################
  traefik:
    image: traefik:v2.0
    restart: always
    container_name: traefik
    ports:
      - "80:80" # <== http
      - "8080:8080" # <== :8080 — порт, на котором работает панель управления
      - "443:443" # <== https
    command:
    #### Это команды CLI, которые настроят Traefik и укажут, как он должен работать! ####

      - --api.insecure=true # <== Включение небезопасного API, НЕ РЕКОМЕНДУЕТСЯ ДЛЯ ПРОИЗВОДСТВЕННОЙ СРЕДЫ
      - --api.dashboard=true # <== Включение панели управления для просмотра служб, промежуточного ПО, маршрутизаторов и т. д.
      - --api.debug=true # <== Включение дополнительных конечных точек для отладки и профилирования
      ## Настройки логирования (варианты: ERROR, DEBUG, PANIC, FATAL, WARN, INFO) - https://docs.traefik.io/observability/logs/ ##
      - --log.level=DEBUG # <== Установка уровня логов Traefik
      ## Настройки провайдера - https://docs.traefik.io/providers/docker/#provider-configuration ##
      - --providers.docker=true # <== Включение Docker как провайдера для Traefik
      - --providers.docker.exposedbydefault=false # <== Не открывать доступ к каждому контейнеру через Traefik, только к тем, у которых это явно включено
      - --providers.file.filename=/dynamic.yaml # <== Ссылка на файл динамической конфигурации
      - --providers.docker.network=web # <== Работа в сети Docker с именем web
      ## Настройки точек входа - https://docs.traefik.io/routing/entrypoints/#configuration ##
      - --entrypoints.web.address=:80 # <== Определение точки входа для порта :80 с именем web
      - --entrypoints.web-secured.address=:443 # <== Определение точки входа для HTTPS на порту :443 с именем web-secured
      ## Настройки сертификатов (Let's Encrypt) -  https://docs.traefik.io/https/acme/#configuration-examples ##
      - --certificatesresolvers.mytlschallenge.acme.tlschallenge=true # <== Включение TLS-ALPN-01 для генерации и обновления сертификатов ACME
      - --certificatesresolvers.mytlschallenge.acme.email=private@private.com # <== Установка email для сертификатов
      - --certificatesresolvers.mytlschallenge.acme.storage=/letsencrypt/acme.json # <== Определение файла ACME для хранения информации о сертификатах
    volumes:
      - ./letsencrypt:/letsencrypt # <== Том для сертификатов (TLS)
      - /var/run/docker.sock:/var/run/docker.sock # <== Том для администрирования Docker
      - ./dynamic.yaml:/dynamic.yaml # <== Том для файла динамической конфигурации, **ссылка: строка 27
    networks:
      - web # <== Размещение Traefik в сети с именем web для доступа к контейнерам в этой сети
    labels:
    #### Метки определяют поведение и правила прокси Traefik для этого контейнера ####
      - "traefik.enable=true" # <== Включение Traefik для самого себя, чтобы просмотреть панель управления и назначить поддомен для доступа к ней
      - "traefik.http.routers.api.rule=Host(`monitor.private.com`)" # <== Установка домена для панели управления
      - "traefik.http.routers.api.service=api@internal" # <== Включение API как службы для доступа


networks:
  web:
    external: true
  backend:
    external: false

volumes:
  db_data: {}
  wordpress:
    external: true
  db:
    external: true

Discourse app.yml
## Это шаблон контейнера Docker Discourse «всё в одном», автономный
##
## После внесения изменений в этот файл вы ОБЯЗАНЫ выполнить пересборку
## /var/discourse/launcher rebuild app
##
## БУДЬТЕ *ОЧЕНЬ* ОСТОРОЖНЫ ПРИ РЕДАКТИРОВАНИИ!
## YAML-ФАЙЛЫ ЧРЕЗВЫЧАЙНО ЧУВСТВИТЕЛЬНЫ К ОШИБКАМ В ПРОБЕЛАХ ИЛИ ВЫРАВНИВАНИИ!
## посетите http://www.yamllint.com/, чтобы проверить файл при необходимости

templates:
  - "templates/postgres.template.yml"
  - "templates/redis.template.yml"
  - "templates/web.template.yml"
  - "templates/web.ratelimited.template.yml"
## Раскомментируйте эти две строки, если хотите добавить Lets Encrypt (https)
  #- "templates/web.ssl.template.yml"
  # "templates/web.letsencrypt.ssl.template.yml"

## Какие TCP/IP-порты должен открывать этот контейнер?
## Если вы хотите, чтобы Discourse использовал один порт с другим веб-сервером, например Apache или nginx,
## см. https://meta.discourse.org/t/17247 для деталей
expose:
  #- "80:80"   # http
  #- "443:443" # https

params:
  db_default_text_search_config: "pg_catalog.english"

  ## Установите db_shared_buffers максимум на 25% от общего объёма памяти.
  ## будет установлено автоматически при загрузке на основе обнаруженной RAM, или вы можете переопределить
  db_shared_buffers: "128MB"

  ## может улучшить производительность сортировки, но увеличивает использование памяти на подключение
  #db_work_mem: "40MB"

  ## Какую ревизию Git должен использовать этот контейнер? (по умолчанию: tests-passed)
  #version: tests-passed

env:
  LANG: en_US.UTF-8
  # DISCOURSE_DEFAULT_LOCALE: en

  ## Сколько одновременных веб-запросов поддерживается? Зависит от памяти и количества ядер CPU.
  ## будет установлено автоматически при загрузке на основе обнаруженных CPU, или вы можете переопределить
  UNICORN_WORKERS: 2

  ## TODO: Доменное имя, на которое будет отвечать этот экземпляр Discourse
  ## Обязательно. Discourse не будет работать с чистым IP-адресом.
  DISCOURSE_HOSTNAME: forum.private.com

  ## Раскомментируйте, если хотите, чтобы контейнер запускался с тем же
  ## именем хоста (опция -h), что указано выше (по умолчанию "$hostname-$config")
  #DOCKER_USE_HOSTNAME: true

  ## TODO: Список email-адресов через запятую, которые станут администраторами и разработчиками
  ## при первой регистрации, например 'user1@example.com,user2@example.com'
  DISCOURSE_DEVELOPER_EMAILS: 'private@private.com'

  ## TODO: SMTP-сервер, используемый для проверки новых аккаунтов и отправки уведомлений
  ## Адрес SMTP, имя пользователя и пароль обязательны
  # ВНИМАНИЕ: символ '#' в пароле SMTP может вызвать проблемы!
  DISCOURSE_SMTP_ADDRESS: in-v3.mailjet.com
  DISCOURSE_SMTP_PORT: 587
  DISCOURSE_SMTP_USER_NAME: redacted
  DISCOURSE_SMTP_PASSWORD: "redacted"
  #DISCOURSE_SMTP_ENABLE_START_TLS: true           # (опционально, по умолчанию true)

  ## Если вы добавили шаблон Lets Encrypt, раскомментируйте ниже, чтобы получить бесплатный SSL-сертификат
  LETSENCRYPT_ACCOUNT_EMAIL: private@private.com

  ## Адрес http или https CDN для этого экземпляра Discourse (настроен на извлечение)
  ## см. https://meta.discourse.org/t/14857 для деталей
  #DISCOURSE_CDN_URL: https://discourse-cdn.example.com

## Контейнер Docker не сохраняет состояние; все данные хранятся в /shared
volumes:
  - volume:
      host: /var/discourse/shared/standalone
      guest: /shared
  - volume:
      host: /var/discourse/shared/standalone/log/var-log
      guest: /var/log

## Плагины размещаются здесь
## см. https://meta.discourse.org/t/19157 для деталей
hooks:
  after_code:
    - exec:
        cd: $home/plugins
        cmd:
          - git clone https://github.com/discourse/docker_manager.git

## Любые пользовательские команды для выполнения после сборки
run:
  - exec: echo "Начало пользовательских команд"
  ## Если вы хотите установить адрес email в поле 'От' для первой регистрации, раскомментируйте и измените:
  ## После получения первого email регистрации закомментируйте строку обратно. Она нужна только один раз.
  #- exec: rails r "SiteSetting.notification_email='info@unconfigured.discourse.org'"
  - exec: echo "Конец пользовательских команд"

labels:
  app_name:                                                                     discourse

  #----Метки Traefik------------------------
  traefik.enable:                                                               true
  traefik.docker.network:                                                       web

   #---СЕКЦИЯ HTTP-МАРШРУТИЗАЦИИ-------------------
  traefik.http.routers.discourse.rule:                                          Host(`forum.private.com`)
    #--СЕКЦИЯ HTTP--------------------------
  traefik.http.routers.discourse.entrypoints:                                   web
  traefik.http.routers.discourse.middlewares:                                   discourse_redirect2https         
  traefik.http.services.discourse.loadbalancer.server.port:                     80  

   #---СЕКЦИЯ HTTPS-МАРШРУТИЗАЦИИ
  traefik.http.routers.discourse_secure.rule:                                   Host(`forum.private.com`)
    #--СЕКЦИЯ HTTPS
  traefik.http.routers.discourse_secure.entrypoints:                            web-secured
  traefik.http.services.discourse_secure.loadbalancer.server.port:              80
    #--СЕКЦИЯ TLS
  traefik.http.routers.discourse_secure.tls.certresolver:                       tlsChallenge_letsencrypt

   #---СЕКЦИЯ ПРОМЕЖУТОЧНОГО ПО перенаправление http на https
  traefik.http.middlewares.discourse_redirect2https.redirectscheme.scheme:      https

docker_args:
  - "--network=web"
  - "--expose=80"

Спасибо