import assert from "node:assert/strict";
import { execFile } from "node:child_process";
import { mkdtemp, rm, writeFile } from "node:fs/promises";
import { tmpdir } from "node:os";
import { join } from "node:path";
import { promisify } from "node:util";
import test from "node:test";
import * as A from "../kit/audit.mjs";
import { turning } from "../kit/turn-build.mjs";
const P={origin:[0,0],scale:1,azimuth:45,elevation:30};
const fixtures=[
["single quoted rectangle", ""],
["spaces around attribute equals", ''],
["single quoted nested transform", ""],
["numeric XML path references", ''],
["numeric XML transform references", ''],
["mixed attribute quotes and multiline path", ""],
["single quoted ellipse", ""],
["quoted attribute text is not geometry", ``],
["quoted greater-than delimiter", ``],
["quoted less-than delimiter", ``],
["ordinary double quoted rectangle", ''],
["ordinary transformed circle", ''],
];
let native;const directory=await mkdtemp(join(tmpdir(),"anatomy-svg-attributes-"));
try{
const page=join(directory,"figure.html");await writeFile(page,`
`);
const expression=`Array.from({length:${fixtures.length}},(_,i)=>{const b=document.querySelector('#f'+i).getBBox();return[b.x,b.y,b.x+b.width,b.y+b.height]})`;
const result=await promisify(execFile)(process.execPath,["scripts/drive.mjs",page,JSON.stringify([["eval",expression]])],{timeout:30000});native=JSON.parse(result.stdout.match(/eval: (.*)/)[1]);
}finally{await rm(directory,{recursive:true,force:true});}
fixtures.forEach(([name,markup],i)=>test(`public SVG bounds and fixed parts decode ${name}`,()=>{
assert.deepEqual(A.markupBox(markup),native[i]);
const T=turning(P);T.layer("figure");const part=T.fixed({name:"fixed",svg:markup,anchor:[0,0,0],shapes:[A.ball([0,0,0],50)]});
assert.deepEqual(part.spec.box,native[i].map((v,j)=>v+(j<2?-.5:.5)));
}));
test("coverage rejects a stand-in for single quoted real geometry",()=>{
const item={name:"quoted",svg:fixtures[0][1],shapes:[A.ball([0,0,0],.1)]};assert.equal(A.coverage([item],P).length,1);
assert.equal(A.coverage([{...item,shapes:[A.ball([0,0,0],50)]}],P).length,0);
});
test("quoted and escaped clip identifiers retain authored clipping",()=>{
const markup="";
assert.deepEqual(A.markupBox(markup),[2,3,6,8]);
});
test("quoted halo class remains excluded from authored bounds",()=>{
assert.deepEqual(A.markupBox(""),[2,3,6,8]);
});