Traefik Certificate Resolvers: ACME and Tailscale Types Explained

Traefik provides two certificate resolvers—ACME for public Let's Encrypt certificates and Tailscale for private mesh network certificates—that automate TLS certificate acquisition and renewal when explicitly referenced by routers.

Certificate resolvers in the traefik/traefik repository abstract the complexity of TLS management by handling domain validation, certificate signing, and automatic renewal. These components are defined in the static configuration and activated per-router through the tls.certresolver option.

What Are Certificate Resolvers in Traefik?

A certificate resolver is a static configuration component responsible for obtaining and managing TLS certificates. According to the source code in pkg/config/static/static_config.go【/__modal/volumes/vo-cSqLfqnnIwYXEonuEJnnZa/repos/github.com/traefik/traefik/master/pkg/config/static/static_config.go#L77-L110】, resolvers are declared under the certificatesResolvers key and support two distinct providers: ACME and Tailscale.

Resolvers do not automatically apply to all routers. As documented in the Traefik reference, defining a certificate resolver does not imply that routers will use it automatically. Each router or entrypoint meant to use the resolver must explicitly reference it【/cache/repos/github.com/traefik/traefik/master/docs/content/reference/install-configuration/tls/certificate-resolvers/overview.md#L16-L19】.

ACME Certificate Resolver

The ACME resolver leverages the Lego library to interact with Let's Encrypt or any ACME-compatible Certificate Authority. The implementation resides primarily in pkg/provider/acme/provider.go.

Configuration Structure

The ACME resolver requires email, storage location, and challenge configuration. From the documentation【/cache/repos/github.com/traefik/traefik/master/docs/content/reference/install-configuration/tls/certificate-resolvers/acme.md#L18-L26】:

certificatesResolvers:
  letsencrypt:
    acme:
      email: [email protected]
      storage: /letsencrypt/acme.json
      httpChallenge:
        entryPoint: web

Challenge Types

Traefik supports three ACME challenge mechanisms:

  • HTTP-01: Traefik spins an HTTP listener on the entrypoint defined in httpChallenge.entryPoint to respond to the CA's validation request.
  • DNS-01: Delegates validation to the selected DNS provider via the Lego library, requiring configuration of dnsChallenge.provider.
  • TLS-ALPN-01: Uses the TLS handshake on the websecure entrypoint, configured via the tlsChallenge field.

Storage and Renewal

Obtained certificates are persisted to the path defined by storage (defaulting to acme.json). Traefik monitors certificate expiry and initiates renewal approximately 30 days before expiration for standard 90-day certificates【/cache/repos/github.com/traefik/traefik/master/docs/content/reference/install-configuration/tls/certificate-resolvers/acme.md#L9-L14】.

Tailscale Certificate Resolver

The Tailscale resolver provides certificates for services within a Tailscale mesh network. This resolver is implemented in pkg/provider/tailscale/provider.go【/__modal/volumes/vo-cSqLfqnnIwYXEonuEJnnZa/repos/github.com/traefik/traefik/master/pkg/provider/tailscale/provider.go#L1-L63】.

Configuration

The Tailscale resolver requires minimal configuration—simply enabling it with an empty object:

certificatesResolvers:
  ts:
    tailscale: {}

Domain Handling

Unlike ACME, the Tailscale resolver only serves certificates for Tailscale-specific domains matching the pattern *.domains-alias.ts.net or machine-name.domains-alias.ts.net. When a router references this resolver, Traefik extracts the domain from Host() or HostSNI() matchers, or from the explicit tls.domains list where the main field specifies the domain to request【/cache/repos/github.com/traefik/traefik/master/docs/content/reference/install-configuration/tls/certificate-resolvers/tailscale.md#L70-L75】.

Certificate Acquisition and Renewal

The resolver calls the tscert package, which communicates with the local Tailscale daemon via its gRPC API to sign a leaf certificate for the requested domain. Renewal occurs 14 days before expiry to align with Tailscale daemon policies【/cache/repos/github.com/traefik/traefik/master/docs/content/reference/install-configuration/tls/certificate-resolvers/tailscale.md#L80-L83】.

How to Configure and Use Certificate Resolvers

Binding Resolvers to Routers

A resolver must be explicitly referenced in the router configuration. Using the file provider:

http:
  routers:
    my-app:
      rule: "Host(`app.example.com`)"
      entryPoints:
        - websecure
      tls:
        certResolver: letsencrypt

Using Docker labels:

labels:
  - "traefik.http.routers.my-app.rule=Host(`app.example.com`)"
  - "traefik.http.routers.my-app.tls.certresolver=letsencrypt"

Explicit Domain Specification

When the router rule does not contain a Host() matcher, or when requesting SANs, use the domains list:

http:
  routers:
    custom-domain:
      rule: "Path(`/metrics`)"
      entryPoints:
        - websecure
      tls:
        certResolver: letsencrypt
        domains:
          - main: example.com
            sans:
              - www.example.com

Tailscale-Specific Configuration

For internal Tailscale services:


# Static configuration

certificatesResolvers:
  ts:
    tailscale: {}

# Dynamic configuration

http:
  routers:
    internal-metrics:
      rule: "Host(`monitoring.myteam.ts.net`)"
      entryPoints:
        - websecure
      tls:
        certResolver: ts

Summary

  • Certificate resolvers are static configuration components in Traefik that automate TLS certificate acquisition and renewal, defined in pkg/config/static/static_config.go.
  • ACME resolver uses the Lego library to obtain public certificates from Let's Encrypt via HTTP-01, DNS-01, or TLS-ALPN-01 challenges, storing certificates in acme.json and renewing them ~30 days before expiry.
  • Tailscale resolver integrates with the local Tailscale daemon via tscert to issue private certificates for *.ts.net domains, renewing them 14 days before expiration.
  • Explicit binding required – Routers must reference resolvers via tls.certresolver; defining a resolver does not automatically apply it to all routes.

Frequently Asked Questions

What is the difference between ACME and Tailscale certificate resolvers in Traefik?

The ACME resolver obtains publicly trusted certificates from Let's Encrypt or other ACME-compatible CAs for any internet-facing domain you control, supporting automated validation via HTTP, DNS, or TLS challenges. The Tailscale resolver only works for devices inside a Tailscale mesh network, obtaining certificates for Tailscale-specific domains (*.ts.net) directly from the local Tailscale daemon without requiring public DNS validation.

How do I configure a certificate resolver to automatically renew TLS certificates?

Both resolvers handle renewal automatically once configured. For ACME, Traefik checks certificate expiry and initiates renewal approximately 30 days before expiration, storing the updated certificate in the configured storage file (default acme.json). For Tailscale, the resolver renews certificates 14 days before expiry by requesting a new certificate from the Tailscale daemon. No manual intervention is required for either resolver once the initial static configuration is applied.

Can I use multiple certificate resolvers in the same Traefik instance?

Yes, you can define multiple certificate resolvers in the static configuration under the certificatesResolvers key, each with a unique name (e.g., letsencrypt, letsencrypt-dns, tailscale). Individual routers then reference the specific resolver they need via the tls.certresolver option. This allows you to use ACME for public-facing services while simultaneously using Tailscale for internal mesh services, or to use different ACME challenge types for different domains.

Why is my certificate resolver not issuing certificates for my router?

The most common cause is failing to explicitly reference the resolver in the router configuration. As implemented in the Traefik source code, defining a certificate resolver in the static configuration does not automatically apply it to all routers. You must set tls.certresolver=<resolver_name> on each router that requires managed certificates. Additionally, for ACME resolvers, ensure the domain in the router's Host() rule or tls.domains list matches a domain you control and that the challenge type (HTTP-01, DNS-01, or TLS-ALPN-01) is correctly configured to validate that domain.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →