Guide

Best practices

Patterns that make PAC files reliable, fast, and maintainable.

  • DNS-free checks go first. Order your conditions so that isPlainHostName(), dnsDomainIs(), and shExpMatch() are evaluated before anything that triggers DNS. The majority of internal traffic matches these checks and exits early — saving DNS round-trips for the rest.
  • Resolve DNS once. Assign dnsResolve(host) to a variable at the top of the function and reuse it for every isInNet() call. Calling dnsResolve() or isResolvable() multiple times for the same host multiplies your DNS cost.
  • Guard DNS failures. dnsResolve() returns an empty string "" on failure, not null. Always check if (ip && ...) before passing to isInNet() — an empty string will produce incorrect matches.
  • Logical operators at the start of lines. In multi-line conditions, place || and && at the beginning of each continuation line, not the end. This way every line is self-contained — you can safely copy/paste, delete, or comment out any line without worrying about whether the previous line now has a dangling operator.
  • Always include a catch-all return. The last line of your function must unconditionally return something. If execution falls through without returning, the browser's behaviour is undefined — it may throw an error, go direct, or refuse the request entirely.
  • Serve with the correct MIME type. The PAC file must be served as application/x-ns-proxy-autoconfig. Some clients also accept application/x-javascript-config or text/javascript, but the former is the most widely supported. An incorrect MIME type will cause clients to silently ignore the file.
  • Keep fallback chains short. Each entry in a semicolon-separated return chain adds a full connection timeout before the browser moves to the next one. Limit yourself to two proxies plus DIRECT at most. If you need more proxies, use load balancing logic in the PAC file itself.
  • Version your PAC files. Add a comment at the top with a version number and date. PAC files are often cached aggressively — a version comment makes it easy to verify which version a client actually loaded during debugging.
  • Remove all alert() calls before deploying. Debug alerts break PAC evaluation in some browsers and can expose internal routing logic to end users. Use pacparser or browser DevTools for testing instead.
  • Use IP addresses in subnet patterns. In isInNet(host, pattern, mask), pattern must always be a dotted-decimal IP — never a hostname. Hostnames in pattern can fail silently across browsers.