Undefined has no JSON value representation. Object properties with undefined values are omitted, array positions become null, and a top-level undefined produces no JSON string.
Reproduce the behavior safely
Run this self-contained fixture in an empty temporary directory, separate from your project. Shell examples create only named fixture files there. JavaScript examples use local values and send no network requests.
const assert = require('node:assert/strict');
assert.equal(JSON.stringify({keep: 1, unset: undefined}), '{"keep":1}');
assert.equal(JSON.stringify([undefined, 1]), '[null,1]');
assert.equal(JSON.stringify(undefined), undefined);
const payload = {nickname: null, enabled: false};
assert.deepEqual(JSON.parse(JSON.stringify(payload)), payload);
const restored = JSON.parse(JSON.stringify({unset: undefined}));
assert.equal(Object.hasOwn(restored, 'unset'), false);
console.log(JSON.stringify(payload));Observed local output
{"nickname":null,"enabled":false}Why the result changes
An omitted property and a property explicitly set to null can carry different API meanings. A patch may interpret absence as leave unchanged and null as clear the field. Replacing undefined globally with null can therefore change an operation rather than merely repair formatting. Arrays retain their positions through a null placeholder, which is another reason to inspect the actual serialized shape.
Choose and verify the correction
Define each field as required, optional or explicitly nullable. Build the outbound data object under that schema before serialization. For an optional field, omit it intentionally; for a supported clear action, send the API-defined representation. Check that top-level serialization produced a string before passing it to a component that requires JSON text. Test the receiver interpretation as well as the sender bytes.
Limits and next checks
The fixture covers ordinary object fields and array elements. Custom toJSON methods and replacers can change serialization and must be reviewed separately. This guide does not solve BigInt or circular-reference failures; those require different data contracts. A successful stringify call does not prove lossless round-tripping, since functions, symbols and other values also need explicit handling.
Related: JSON and Large Integer IDs: Preserve the Digits with a String Contract.
Isolated fixture executed on macOS on November 10, 2026 (KST), with v26.5.0. The observed output verifies this example, not every application or runtime.