In this guide we will setup OnlyOffice with internal HTTPS using generated self-signed certificates with Traefik.
warning
Recommended: Only use this guide if you have specific security requirements. Please, check the Traefik Setup Guide first if you are starting, because this guide is intended for advanced users and we will use that guide as base for this one.
services:onlyoffice:container_name:onlyofficeimage:onlyoffice/documentserverenvironment:TZ:$TZJWT_SECRET:$ONLYOFFICE_SECRETONLYOFFICE_HTTPS_HSTS_ENABLED:false# Add this two env varsSSL_CERTIFICATE_PATH:/var/www/onlyoffice/Data/certs/onlyoffice.crtSSL_KEY_PATH:/var/www/onlyoffice/Data/certs/onlyoffice.key# And this volume mountvolumes:- ./certs:/var/www/onlyoffice/Data/certs # Mount certificateslabels:- "traefik.enable=true"- "traefik.http.routers.${TRAEFIK_SERVICE_NAME}.tls=true"- "traefik.http.routers.${TRAEFIK_SERVICE_NAME}.entrypoints=websecure"- "traefik.http.routers.${TRAEFIK_SERVICE_NAME}.tls.certresolver=letsencrypt"- "traefik.http.routers.${TRAEFIK_SERVICE_NAME}.tls.options=default"- "traefik.http.routers.${TRAEFIK_SERVICE_NAME}.rule=Host(${DOMAIN_NAME})"- "traefik.http.routers.${TRAEFIK_SERVICE_NAME}.service=${TRAEFIK_SERVICE_NAME}"- "traefik.http.services.${TRAEFIK_SERVICE_NAME}.loadbalancer.server.url=${OFFICE_INTERNAL}"# change port with url, and set the container name with https- "traefik.http.services.${TRAEFIK_SERVICE_NAME}.loadbalancer.passhostheader=true"- "traefik.http.routers.${TRAEFIK_SERVICE_NAME}.middlewares=no-frame-block@file"# Headers for onlyoffice, see https://github.com/ONLYOFFICE/onlyoffice-nextcloud/issues/151 for details- "traefik.http.middlewares.${TRAEFIK_SERVICE_NAME}-headers.headers.accesscontrolalloworiginlist=*"networks:proxy_network:restart:unless-stoppednetworks:proxy_network:external:true
Then, modify the .env (environment) file of onlyoffice:
DOMAIN_NAME=your-domain.com # Your root domain here.DYNU_API_KEY=your-dynu-api-key-here # DDNS API Key (we are using dynu - check the traefik documentation about other providers)# Traefik Dashboard Credentials# Generate with: docker run --rm httpd:alpine htpasswd -nb your-username your-password | sed -e 's/\$/\$\$/g'TRAEFIK_DASHBOARD_CREDENTIALS=admin:$$apr1$$H6uskkkW$$IgXLP6ewTrSuBkTrqE8wj/
# Add thisOFFICE_INTERNAL=https://onlyoffice
warning
The certificates MUST be mounted at /var/www/onlyoffice/Data/certs (in the right side) and should be named onlyoffice.key and onlyoffice.crt.
In the previous guide, we used port 80, but now that is not neccesary, instead we will use URL that will be used to communicate with filebrowser: "traefik.http.services.${TRAEFIK_SERVICE_NAME}.loadbalancer.server.url=https://onlyoffice"
If you want, you can delete your ${TRAEFIK_SERVICE_PORT} from your .env file since is no longer needed.
Instead of use traefik labels as above, we can also deploy onlyoffice using File Provider.
This is similar to when we created the middlewares.yaml file. You should have a dynamic directory that traefik reads, so, in that same directory where the middlewares.yaml is, create a file called onlyoffice.yaml or how you prefer.
http:routers:onlyoffice:entrypoints:- websecurerule:Host(`onlyoffice.yourdomain.com`)tls:certResolver:letsencryptservice:onlyofficemiddlewares:- onlyoffice-headers- no-frame-blockservices:onlyoffice:loadBalancer:servers:- url:"https://onlyoffice"# Note: HTTPS, not HTTPserversTransport:onlyoffice # Reference to transport belowmiddlewares:onlyoffice-headers:headers:customRequestHeaders:X-Forwarded-Proto:"https"accessControlAllowOriginList:- "*"serversTransports:onlyoffice:insecureSkipVerify:true# This skips certificate verification
Traefik needs to be told to skip certificate verification, so if you followed the previous guide, we are validating the verification of the certificates in our traefik.yaml static config file by setting it to false, we need to set it to true:
serversTransport:insecureSkipVerify:true# Set this to true to skip the verificationforwardingTimeouts:dialTimeout:"60s"responseHeaderTimeout:"60s"idleConnTimeout:"90s"
report
If you don’t change insecureSkipVerify to true, you will have the next error in the traefik logs and OnlyOffice don’t will work
traefik | 2025-11-21T15:14:17-05:00 ERR github.com/traefik/traefik/v3/pkg/proxy/httputil/proxy.go:119 > 500 Internal Server Error error="tls: failed to verify certificate: x509: certificate relies on legacy Common Name field, use SANs instead"
integrations:office:url:"https://onlyoffice.yourdomain.com"# External HTTPS URLinternalUrl:"https://onlyoffice"# Internal HTTPS URL, the one that we defined in the .env file which should be the container name.secret:"your-jwt-secret"
# Check OnlyOffice is using HTTPS (You should see that is listening to 0.0.0.0:443 and is using SSL)docker exec onlyoffice cat /etc/onlyoffice/documentserver/nginx/ds.conf | grep ssl
# Test from Traefik perspective (Should perform the helthcheck successfully)docker exec traefik wget --no-check-certificate https://onlyoffice/healthcheck
Self-Signed Certificates with Full Verification link
warning
I haven’t found a way to make this work with labels, so if you want the full verification, you will need to use onlyoffice with file provider.
But the full verification is optional, we’ll just make sure that traefik trust our self-signed certificate, this is more complex and is prone to fail or to have issues… So I recommend to keep skip verification and use HTTPS externally.
First of all, make SURE that you have insecureSkipVerify set to false.
serversTransport:insecureSkipVerify:false# Set this to false to NOT skip the verificationforwardingTimeouts:dialTimeout:"60s"responseHeaderTimeout:"60s"idleConnTimeout:"90s"
[req]default_bits=2048prompt=nodefault_md=sha256distinguished_name=dnx509_extensions=v3_req[dn]CN=onlyoffice[v3_req]subjectAltName=@alt_names[alt_names]IP.1=192.168.2.125 # Static IP for OnlyOffice containerDNS.1=onlyoffice # Docker service name
info
Why IP and DNS?
IP.1: Allows verification via IP address from the onlyoffice container
DNS.1: Allows verification via Docker service name
Both are required for proper certificate validation
services:onlyoffice:image:onlyoffice/documentservercontainer_name:onlyofficeenvironment:- JWT_ENABLED=true- JWT_SECRET=your-secret- ONLYOFFICE_HTTPS_HSTS_ENABLED=falsevolumes:- ./certs:/var/www/onlyoffice/Data/certsnetworks:proxy_network:ipv4_address:192.168.2.125# Must match cert.conf
warning
IP Address Rules:
Must be in your Docker network subnet (e.g., 192.168.2.0/24)
Must match exactly what’s in cert.conf
If you followed the previous guide we created a docker network with a reserved range of IPs, you can set one IP inside that range, since these IPs are reserved and the auto-allocation of traefik will never take them.
But if you used the simplified command, you will need to set a very high number to avoid the auto-allocation.
Traefik needs access to the certificate to verify it:
info
This ONLY is for traefik, the service, NOT for the whole container, traefik will trust the certificate letting us access to onlyoffice throught our domain.
That means that if we try to verify the validation from other ways like trying to use wget from inside the traefik container, this will be rejected saying that is “not trusted”, but meanwhile we can access to onlyoffice throught the browser is fine.
# Restart all servicesdocker compose restart traefik
docker compose restart onlyoffice
docker compose restart filebrowser
# Check Traefik can verify certificatedocker exec traefik wget https://onlyoffice/healthcheck
# Should succeed without certificate errors
info
Now Traefik should validate OnlyOffice’s certificate using the provided CA, if you have issues, try to follow the troubleshooting steps, but how I said, this might not work well for some people…
If you used the full verification method, you could have some errors with the certificates.
Some common errors could be:
x509: certificate signed by unknown authority: Maybe you forget to specify the rootCAs in transport when configuting file provider for onlyoffice.
x509: certificate is valid for X, not Y: Maybe you set the wrong IP adress or DNS, either in the certificate configuration or in the container, and now is mismatching. Make sure that they are the same in both.
tls: bad certificate: You mounted a wrong path for the certificate in onlyoffice, or traefik.
If for some reason the filebrowser container doesn’t trust the certificates (even configured via traefik), you’ll need to mount and update the certificates of the filebrowser container in startup.
If you have other issues related with onlyoffice and filebrowser, check the Office Troubleshooting guide, which covers some of the most commons issues with solutions.