gohugoio/hugo · error
failed to verify certificate: %v
Error message
failed to verify certificate: %v
What it means
The cached certificate parsed cleanly, but chain verification against the mkcert root CA failed for the requested hostname (`cert.Verify` with `DNSName` and the mkcert root pool). Hugo uses this check to decide whether a cached cert is still usable; failure typically means expiry, hostname mismatch, or a cert signed by a different (e.g. regenerated) mkcert root.
Source
Thrown at commands/server.go:747
return fmt.Errorf("failed to parse root certificate")
}
block, _ := pem.Decode(certPEM)
if block == nil {
return fmt.Errorf("failed to parse certificate PEM")
}
cert, err := x509.ParseCertificate(block.Bytes)
if err != nil {
return fmt.Errorf("failed to parse certificate: %v", err.Error())
}
opts := x509.VerifyOptions{
DNSName: name,
Roots: roots,
}
if _, err := cert.Verify(opts); err != nil {
return fmt.Errorf("failed to verify certificate: %v", err.Error())
}
return nil
}
func (c *serverCommand) createServerPorts(cd *simplecobra.Commandeer) error {
flags := cd.CobraCommand.Flags()
var cerr error
c.withConf(func(conf *commonConfig) {
isMultihost := conf.configs.IsMultihost
c.serverPorts = make([]serverPortListener, 1)
if isMultihost {
if !c.serverAppend {
cerr = errors.New("--appendPort=false not supported when in multihost mode")
return
}
c.serverPorts = make([]serverPortListener, len(conf.configs.Languages))
}View on GitHub ↗ (pinned to 8a468df065)
Solutions
- Delete `<hugo cacheDir>/_mkcerts/` so Hugo mints a fresh cert for the current hostname against the current mkcert root.
- If you changed the site's baseURL hostname, expect a new cert to be generated — clear the stale one for the old name.
- Re-run `mkcert -install` if the root CA was rotated, then regenerate.
- Check expiry: `openssl x509 -in <host>.pem -noout -dates -ext subjectAltName`.
Defensive patterns
Strategy: validation
Validate before calling
if _, err := cert.Verify(x509.VerifyOptions{Roots: pool, DNSName: host}); err != nil {
return fmt.Errorf("cert won't verify against provided CA: %w", err)
} Try / catch
cert, err := server.Serve()
if err != nil && strings.Contains(err.Error(), "failed to verify certificate") {
log.Fatal("TLS cert not signed by the given CA or expired — regenerate with mkcert/hugo server trust")
} Prevention
- Ensure the leaf cert was actually signed by the CA file you pass
- Check certificate expiry (`openssl x509 -enddate`)
- Confirm the cert's SANs cover the hostname hugo serves on
When it happens
Trigger: `hugo server --tlsAuto` where the cached cert is expired, its SANs don't cover the hostname derived from `--baseURL` (default `localhost`), or the mkcert root CA was reinstalled/rotated since the cert was minted so the chain no longer terminates at the current `rootCA.pem`.
Common situations: Changing `--baseURL`/config baseURL to a new hostname while an old `localhost` cert is cached; mkcert reinstalled after an OS refresh, invalidating old leaf certs; long-lived dev machines where the cached cert expired.
Related errors
- failed to parse root certificate
- failed to parse certificate PEM
- failed to parse certificate: %v
- cannot use --renderToMemory with --destination
- failed to create baseURL from %q: %s
AI-assisted analysis of gohugoio/hugo@8a468df065 (2026-07-31).
Data as JSON: /data/errors/045aabd313b0ca87.json.
Report an issue: GitHub ↗.