// ブラウザ API の列挙値が日本語になっていないか、ビルド全体を調べる。
//
// 「音が出なくなった」の正体はこれだった:
//   tone.type = "lowpass"          → "ローパス"      … 例外を投げる
//   audioCtx.state === "running"   → "流れる"        … 永久に偽になる
//   function beep(..., type="square") → type="平方"  … 例外を投げる
//
// どれも構文は通り、lint も素通りし、画面も普通に出る。音だけが消える。
import fs from 'fs';
const B = fs.readFileSync(process.argv[2] || 'build/index.html', 'utf8');

// 値が決まった綴りしか取れない（＝訳してはいけない）プロパティ
// display / position / filter / direction などは、この作品では獣や品物の
// 「表示名」フィールドの名前でもある（o.display = "起き上がった" + …）。
// CSS の意味で使うときは必ず .style. が前に付くので、そちらだけを見る。
// ここに素の名前を入れると、正しい訳を毎回叱ることになる。
const ENUM_PROPS = [
  // Web Audio
  'type', 'oversample', 'panningModel', 'distanceModel',
  'channelCountMode', 'channelInterpretation', 'curve',
  // canvas 2D
  'textAlign', 'textBaseline', 'lineCap', 'lineJoin', 'globalCompositeOperation',
  // メディア / DOM 属性
  'crossOrigin', 'preload', 'referrerPolicy', 'decoding',
  'inputMode', 'enterKeyHint', 'autocomplete', 'encoding',
];
// 状態を表すプロパティ（比較の相手は必ずブラウザが決めた綴り）
const STATE_PROPS = ['state', 'readyState', 'visibilityState', 'protocol', 'nodeName', 'tagName'];

const ja = s => /[ぁ-んァ-ヴー一-龯]/.test(s);
const hits = [];

// 代入:  x.type = "..."   /  x.style.display = "..."
for (const m of B.matchAll(/\.([A-Za-z_$][\w$]*)\s*=\s*(["'])((?:\\.|(?!\2).)*)\2/g))
  if (ENUM_PROPS.includes(m[1]) && ja(m[3]))
    hits.push({ kind: '代入', prop: m[1], val: m[3], at: m.index });

// 既定引数:  function f(..., type="square")
for (const m of B.matchAll(/\b([A-Za-z_$][\w$]*)\s*=\s*(["'])((?:\\.|(?!\2).)*)\2\s*[),]/g))
  if (ENUM_PROPS.includes(m[1]) && ja(m[3]))
    hits.push({ kind: '既定引数', prop: m[1], val: m[3], at: m.index });

// 比較:  x.state === "running"
for (const m of B.matchAll(/\.([A-Za-z_$][\w$]*)\s*[!=]==?\s*(["'])((?:\\.|(?!\2).)*)\2/g))
  if ((STATE_PROPS.includes(m[1]) || ENUM_PROPS.includes(m[1])) && ja(m[3]))
    hits.push({ kind: '比較', prop: m[1], val: m[3], at: m.index });

// オブジェクト直値:  {type:"sine"}
for (const m of B.matchAll(/[{,]\s*([A-Za-z_$][\w$]*)\s*:\s*(["'])((?:\\.|(?!\2).)*)\2/g))
  if (ENUM_PROPS.includes(m[1]) && ja(m[3]))
    hits.push({ kind: 'オブジェクト', prop: m[1], val: m[3], at: m.index });

const seen = new Set();
const uniq = hits.filter(h => { const k = h.prop + '=' + h.val; if (seen.has(k)) return false; seen.add(k); return true; });

console.log(`API の列挙値に日本語が入っている箇所: ${hits.length}（異なり ${uniq.length}）`);
for (const h of uniq) {
  const n = hits.filter(x => x.prop === h.prop && x.val === h.val).length;
  console.log(`  [${h.kind}] .${h.prop} = ${JSON.stringify(h.val)}   ${n} 箇所`);
  console.log(`      …${B.slice(Math.max(0, h.at - 90), h.at + 60).replace(/\n\s*/g, ' ')}…`);
}
process.exit(hits.length ? 1 : 0);
