为何XMLHttpRequest.setRequestHeader()会将undefined/null转为字符串?
XMLHttpRequest.setRequestHeader() convert undefined to the string "undefined"? Great question—this behavior is definitely a common gotcha for frontend developers, especially if you expect an undefined value to skip the header entirely. Let’s break down the design choices behind this:
1. Early Web API design & JavaScript type coercion rules
Back when XMLHttpRequest was first standardized (in the early 2000s), JavaScript’s type system leaned heavily into implicit coercion. HTTP request headers are inherently string-based—there’s no concept of undefined in HTTP’s specification. So the XHR API was built to follow JS’s default behavior: any non-string value passed to setRequestHeader() gets converted to a string using the toString() method.
Since undefined.toString() returns the literal string "undefined", that’s what ends up being sent in the header. This was consistent with how other XHR methods handled non-string inputs at the time (e.g., passing a number would convert it to its string representation).
2. Backward compatibility
Once browsers shipped this behavior, changing it later would risk breaking existing code. Even if it’s an edge case, some older applications might have accidentally relied on undefined being converted to "undefined" in headers. Breaking that behavior could introduce subtle, hard-to-track bugs, so maintainers kept the original coercion logic intact to avoid disrupting legacy systems.
3. Explicit behavior over silent failure
Another key consideration is avoiding silent failures. If passing undefined simply skipped the header, developers might struggle to debug why their header isn’t being sent—was the value truly undefined, or did a typo cause the variable to be missing? By converting it to a visible string, the behavior is explicit: you can inspect the request in dev tools and immediately see that "undefined" was sent, which clues you in to check your value’s type.
How to get your expected behavior
If you want to skip sending the header when the value is undefined, just add a quick check before calling setRequestHeader():
const xhr = new XMLHttpRequest(); const customHeaderValue = undefined; // Only set the header if the value is defined if (customHeaderValue !== undefined) { xhr.setRequestHeader("x-custom-header", customHeaderValue); }
内容的提问来源于stack exchange,提问作者Benjamin

