import {test} from 'node:test'; import assert from 'node:assert/strict'; import {detachJsonData,hasDetachedJsonData} from '../../src/lib/canvas-core/json-data.ts'; test('JSON detachment owns only its copied immutable result and preserves JSON semantics',()=>{ let calls=0;const external={nested:{text:'before'},date:new Date('2026-01-01Z'),custom:{toJSON(){calls++;return{value:2};}},array:[,undefined,NaN],['__proto__']:{safe:true}}; const value=detachJsonData(external);assert.equal(calls,1);assert.equal(hasDetachedJsonData(value),true);assert.equal(hasDetachedJsonData(external),false); external.nested.text='after';external.date.setUTCFullYear(2027); assert.equal(value.nested.text,'before');assert.equal(value.date,'2026-01-01T00:00:00.000Z');assert.deepEqual(value.array,[null,null,null]);assert.equal(Object.hasOwn(value,'__proto__'),true); assert.ok(Object.isFrozen(value.nested));assert.throws(()=>{value.nested.text='mutate';},TypeError); assert.equal(hasDetachedJsonData(Object.freeze({...value})),false);assert.equal(hasDetachedJsonData(structuredClone(value)),false); assert.equal(hasDetachedJsonData(Object.freeze({nested:{mutable:true}})),false); const cycle={};cycle.self=cycle;assert.throws(()=>detachJsonData(cycle));assert.throws(()=>detachJsonData({big:1n})); });