Wildcard subdomain NGINX and ACME

Anyone know how to resolve the issue

error: A definition for option `systemd.services."acme-~^(?<subdomain>.+)\\.test\\.jayhenks\\.com\$".after."[definition 1-entry 5]"' is not of type `string matching the pattern [a-zA-Z0-9@%:_.\-]+[.](service|socket|device|mount|automount|swap|target|path|timer|scope|slice)'. Definition values:
- In `/nix/store/d3raxzxl79hz2k0d8di8lma931dgd1ny-source/nixos/modules/security/acme': "acme-selfsigned-~^(?<subdomain>.+)\\.test\\.jayhenks\\.com$.service"

Seems like systemd has problems with the wildcard, my use case is to have domains such as abc.test.jayhenks.com resolve to different directories in NGINX.

Config:

"*.test.jayhenks.com" = {
enableACME = true;
forceSSL = true;
serverName = "~^(?<subdomain>.+)\\.test\\.jayhenks\\.com$";
locations = {
"/" = {
alias = "/var/jayhenks/$subdomain/";
index = "index.html";
tryFiles = "$uri $uri/ $uri/index.html =404";
};
};
};

I need this dynamic behavior, otherwise statically it would probably be easy.

https://nixos.org/manual/nixos/stable/index.html#module-security-acme-config-dns

Use useACMEHost option in nginx. Here’s an example with cloudflare: hosts/mia/vaultwarden/default.nix · db88b4ae1c3a6cb5adfc9ed84fb062fb945f6881 · misuzu / nixos-configuration · GitLab

Thank you, but does this actually help me?

As far as I can see, the problem I have here is that for every NGINX domain, a separate systemd service is being created, and since what I am doing kind of requires dynamic systemd services it is not possible.

Does the useACMEHost option prevent this? I would appreciate a more detailed explanation if that works.

You’re trying to issue a certificate for “~^(?.+)\.test\.jayhenks\.com$” domain, which is obviously is not a valid domain. For wildcard domain you need to use security.acme.certs option instead and point nginx to it using useACMEHost option.

Something like this:

  security.acme.certs."test.jayhenks.com" = {
    domain = "*.test.jayhenks.com";
    dnsProvider = "cloudflare";
    credentialsFile = "/path/to/credentials.env"
    group = config.services.nginx.group;
  };

  services.nginx = {
    enable = true;
    virtualHosts = {
      "~^(?<subdomain>.+)\\.test\\.jayhenks\\.com$" = {
        useACMEHost = "test.jayhenks.com";
        <....>
      };
    };
  };
3 Likes

Thank you, works like a charm. If anyone stumbles across this issue as well, you need this additional ACME configuration block because wildcard certificates (e.g. *.example.com) cannot use the HTTP-01 challenge. They require a DNS-01 challenge, which you can provide via useACMEHost.

1 Like