Image Base64 Tool

JSON to CSV without hiding value changes

Paste an array of flat JSON objects below to download CSV. Keep the original JSON if you need its types: in our paired local test, missing values, null and empty strings became empty CSV fields, and numeric zero became indistinguishable from the string zero.

No export yet.

Measured November 4, 2026 with Python 3.12.14 and Node v24.19.0. We created a fresh JSON input and ran Python json plus csv.writer against Node JSON.parse plus an explicit CSV encoder. Both used union headers, UTF-8 and CRLF record endings. Python csv.DictReader independently read both outputs.

What survived the conversion

Our new 386-byte input contained separate missing, null and empty-string records. Both exports left the value field empty for all three. The saved parsing report still distinguished property absence, a null value and a string; the CSV reread did not. Every recovered value was a string, including those empty fields. The case column identifies our controls but is not a general type-preservation mechanism.

The numeric-zero and string-zero controls both returned the text 0 from each exported file. Likewise, the boolean-false and string-false controls both returned the text false. Those pairs started with different JSON types but ended with matching value cells. We checked the decoded CSV fields rather than deciding from how a spreadsheet might display them; no spreadsheet was opened for this experiment.

Scroll the measured table sideways on a narrow screen.

ControlPython parsed typePython CSV rereadNode parsed typeNode CSV reread
missingmissing(empty)missing(empty)
nullnull(empty)null(empty)
emptystr(empty)string(empty)
number-zeroint0number0
string-zerostr0string0
boolean-falseboolfalsebooleanfalse
string-falsestrfalsestringfalse
large-numberint9007199254740993number9007199254740992
large-stringstr9007199254740993string9007199254740993
quotedstra,"b" Caféstringa,"b" Café

What the byte comparison found

Python preserved the integer 9007199254740993 before writing its decimal digits. Node parsed that numeric literal as 9007199254740992, and its CSV contained that changed value. The separate string control retained 9007199254740993 in both paths. The discrepancy was already present in the Node parsing report, before CSV quoting or download, so this control locates the change earlier than file export.

The two saved specimens are each 214 bytes, yet their SHA-256 checksums differ. A direct comparison found exactly one different byte at zero-based offset 149: the last digit of the large-number value. Equal file lengths therefore concealed a measured value change in this pair. The original 386-byte JSON and both complete CSV files are included so the comparison can be repeated.

Our final control contains a comma, embedded double quotes, an internal newline and the word Café. Both exported files reread that field as the original string, with the later column returning tail. The union header included that column even though it appeared only in the final input record. This successful control separates delimiter and quoting preservation from the earlier loss of type distinctions.

OutputBytesFull SHA-256
python.csv2145fa78ac9912a7b25c80d9e4583a2a3326a9f814d330bf45a0b97a2fb0f97c58d
node.csv214b0d93e4df00e8a45382c31dc62d6365f6b83064012e7fde09707da00afc14bea

Can CSV recover the original types?

Can CSV recover the original JSON types? These two exports cannot determine the original type from the matching value cells alone. Does matching file size prove matching data? Compare the complete bytes or checksums as well. Will this reproduce an online converter or Excel import? No: the measured paths are the supplied local programs.

Choose a schema before conversion when the difference between a missing value and an empty string matters. Store types in a separate schema or retain the original JSON alongside the export. Quoting a field makes CSV syntax valid; it does not specify a universal rule for reconstructing JSON types.

Reproduce these two paths

Download the script and run it with Python and Node installed in the same folder. It regenerates the fixed input, both exports and the raw report, then checks the paired observations. The source and output hashes cover exact file bytes; they are not measurements of speed, online-service limits or browser compatibility.

python reproduce.py

Limits and related tools

This conversion tool accepts a nonempty array of flat objects. Nested objects and arrays are rejected rather than silently flattened. It uses JavaScript numbers, so keep identifiers and large exact integers as JSON strings before parsing. It does not neutralize spreadsheet formulas; review untrusted exports before opening them in a spreadsheet. Processing stays in this page.

Three distinct inputs, one empty CSV field
Different JSON types, matching CSV text
Same length, different value
Locate the change before export