anomalyco/sst · error · VisibleError
You must provide a custom domain for ${port.listenProtocol.t
Error message
You must provide a custom domain for ${port.listenProtocol.toUpperCase()} protocol. What it means
Ports listening on https or tls require TLS termination at a custom domain. If a port's listen protocol is https/tls but `public.domain` is not set, normalizePublic throws, since the load balancer has no certificate to serve HTTPS/TLS without a domain.
Source
Thrown at platform/src/components/aws/service-v1.ts:274
forwardProtocol: forwardParts[1],
};
});
// validate protocols are consistent
const appProtocols = ports.filter(
(port) =>
["http", "https"].includes(port.listenProtocol) &&
["http", "https"].includes(port.forwardProtocol),
);
if (appProtocols.length > 0 && appProtocols.length < ports.length)
throw new VisibleError(
`Protocols must be either all http/https, or all tcp/udp/tcp_udp/tls.`,
);
// validate certificate exists for https/tls protocol
ports.forEach((port) => {
if (["https", "tls"].includes(port.listenProtocol) && !pub.domain) {
throw new VisibleError(
`You must provide a custom domain for ${port.listenProtocol.toUpperCase()} protocol.`,
);
}
});
return ports;
});
const domain = output(args.public).apply((pub) => {
if (!pub.domain) return undefined;
// normalize domain
const domain =
typeof pub.domain === "string" ? { name: pub.domain } : pub.domain;
return {
name: domain.name,
dns: domain.dns === false ? undefined : domain.dns ?? awsDns(),
cert: domain.cert,View on GitHub (pinned to a0bd20f762)
Solutions
- Add `domain` to the `public` block, e.g. `public: { domain: "api.example.com", ports: [...] }`
- Or change the listen protocol to `http` if TLS isn't needed at the LB
- Ensure a certificate for the domain is available in the region (Route53/ACM)
Example fix
// before
public: { ports: [{ listen: "443/https", forward: "8080/http" }] }
// after
public: { domain: "api.example.com", ports: [{ listen: "443/https", forward: "8080/http" }] } Defensive patterns
Strategy: validation
Validate before calling
const needsDomain = args.public?.ports?.some(p => /^(443\/)?(https|tls)/.test(p.listen));
if (needsDomain && !args.public?.domain) throw new Error("https/tls ports require public.domain"); Type guard
function needsDomain(pub?: { ports?: { listen: string }[]; domain?: string }): boolean {
return !!pub?.ports?.some(p => ["https","tls"].includes(p.listen.split("/")[1])) && !pub.domain;
} Prevention
- Set `public.domain` whenever any port listens on https/tls
- Provision an ACM certificate for the domain in the deployment region
- Switch to plain http during prototyping, add domain+TLS later
When it happens
Trigger: `public.ports` contains `"443/https"` or `"443/tls"` while `public.domain` is undefined; forgetting `domain` when switching a port from http to https.
Common situations: Adding TLS to an existing service; assuming a default AWS-provided domain supports https; missing certificate/hostname config.
Related errors
- You must provide a custom domain for ${rule.listenProtocol.t
- Missing "name" for domain.
- Need to provide a validated certificate via "cert" when DNS
- The DNS record "${partial.name}" cannot be created because t
- Need to provide a validated certificate via "cert" when DNS
AI-assisted analysis of anomalyco/sst@a0bd20f762 (2026-08-30).
Data as JSON: /api/errors/e893525d5bd5f89b.
Report an issue: GitHub.