9007199254740993が別のIDになる理由
このJSONをJSON.parseで読み、JSON.stringifyで書くとidの末尾が変わります。1.00は1、1e3は1000になります。後者2つは同じ数値の別表記ですが、IDでは元の整数値が失われます。
const source = '{"id":9007199254740993,"price":1.00,"scale":1e3}';
JSON.stringify(JSON.parse(source));
// {"id":9007199254740992,"price":1,"scale":1000}JavaScript Numberの最大安全整数は9007199254740991です。それを超える整数すべてが丸められるわけではありませんが、異なる整数が同じNumber値になることがあります。JSONの数値構文と各パーサーの精度制限を区別してください。
ECMAScript: Number.MAX_SAFE_INTEGER
重複キー:構文が正しくても互換性は別問題
同じオブジェクトにmodeが2回あると、標準のJSON.parseは前の値を後の値で上書きします。RFC 8259は名前の一意性を推奨し、重複名への処理がプログラムごとに異なる場合を説明しています。すべてのパーサーが同じ動作とは限りません。
JSON.stringify(JSON.parse('{"mode":"first","mode":"last"}'));
// {"mode":"last"}Moyoutilは重複キーを自動削除しません。保持は重複の使用を推奨する意味ではありません。受信側とデータ仕様を確認し、元データを作る段階で重複名を解決してください。
Moyoutilで元の表記を保持して検証する
現在のformatJSONはJSON.parseで構文を調べますが、出力は解析済みオブジェクトではなく原文のトークンから作ります。大きな整数、小数・指数表記、重複キーとキー順を保持します。ただし空白や改行が変わり、バイト単位で原文と同じとは限りません。圧縮は文字列内の空白を消す処理ではありません。
formatJSON('{"id":9007199254740993,"price":1.00,"scale":1e3}', 0).output
// {"id":9007199254740993,"price":1.00,"scale":1e3}原本を保存しJSONツールに貼り付け、整形または圧縮します。重要なIDと数値表記を結果で比較してからダウンロードしてください。入力を変更すると前の結果が消えてコピーが無効になるため、再検証が必要です。入力上限はUTF-8で2MiB、入れ子は128段階です。
構文検証は業務ルール、JSON Schemaや受信サーバーの解釈を検証しません。数値を文字列に変えると型も変わるため、自動的な解決策ではありません。文字列IDが許可される仕様か確認してください。本物の秘密鍵や個人情報ではなく架空のデータで再現します。
よくある質問
検証に成功すれば別のサーバーでも数値が保持されますか?
いいえ。出力表記は保持しますが、受信側で数値として解析すれば、そのパーサーの精度制限が適用されます。
JSON圧縮はZIPファイルを作りますか?
いいえ。構文上不要な空白や改行を減らしたJSONテキストを作る機能です。ZIPファイルは作りません。