dotdog 0.6.0 → 0.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. package/dist/cli.js +53 -0
  2. package/package.json +1 -1
package/dist/cli.js CHANGED
@@ -4675,6 +4675,59 @@ kitCmd.command("init <kit>").description("Init a project from a kit").option("-p
4675
4675
  Kit "${kit}" initialized in specs/${projectName}/`));
4676
4676
  console.log(source_default.gray(` Run: dotdog validate`));
4677
4677
  });
4678
+ program2.command("badge [dir]").description("Generate dotdog-badge.svg (shields.io style) showing savings").action((d = ".") => {
4679
+ const dir = resolvePath2(d);
4680
+ const dirs = [join3(dir, "projects"), join3(dir, "specs"), dir];
4681
+ let found = false;
4682
+ for (const dd of dirs) {
4683
+ if (!existsSync3(dd))
4684
+ continue;
4685
+ const projects = readdirSync3(dd, { withFileTypes: true }).filter((e) => e.isDirectory()).map((e) => e.name);
4686
+ for (const p of projects) {
4687
+ const pd = join3(dd, p);
4688
+ const dagFile = join3(pd, `${p}.dag`);
4689
+ if (!existsSync3(join3(pd, "SPEC.dog")))
4690
+ continue;
4691
+ if (!existsSync3(dagFile)) {
4692
+ console.log(source_default.red(` No .dag for ${p}. Run dotdog compile first.`));
4693
+ continue;
4694
+ }
4695
+ const dag = JSON.parse(readFileSync3(dagFile, "utf-8"));
4696
+ const savings = dag.tk && dag.tk.sv ? Math.round(dag.tk.sv) : 0;
4697
+ const label = "spec savings";
4698
+ const value = `${savings}%`;
4699
+ const color = savings > 90 ? "#4c1" : savings > 70 ? "#dfb317" : "#e05d44";
4700
+ const labelLen = Math.round(label.length * 7.2);
4701
+ const valueLen = Math.round(value.length * 7.2);
4702
+ const leftW = Math.max(labelLen + 10, 70);
4703
+ const rightW = Math.max(valueLen + 10, 40);
4704
+ const totalW = leftW + rightW;
4705
+ const leftX = leftW / 2 * 10;
4706
+ const rightX = (leftW + rightW / 2) * 10;
4707
+ const svg = `<svg xmlns="http://www.w3.org/2000/svg" width="${totalW}" height="20" role="img" aria-label="${label}: ${value}">
4708
+ <title>${label}: ${value}</title>
4709
+ <linearGradient id="s" x2="0" y2="100%"><stop offset="0" stop-color="#bbb" stop-opacity=".1"/><stop offset="1" stop-opacity=".1"/></linearGradient>
4710
+ <clipPath id="r"><rect width="${totalW}" height="20" rx="3" fill="#fff"/></clipPath>
4711
+ <g clip-path="url(#r)">
4712
+ <rect width="${leftW}" height="20" fill="#555"/>
4713
+ <rect x="${leftW}" width="${rightW}" height="20" fill="${color}"/>
4714
+ <rect width="${totalW}" height="20" fill="url(#s)"/>
4715
+ </g>
4716
+ <g fill="#fff" text-anchor="middle" font-family="Verdana,Geneva,DejaVu Sans,sans-serif" text-rendering="geometricPrecision" font-size="110">
4717
+ <g transform="scale(.1)">
4718
+ <text x="${leftX}" y="140" textLength="${labelLen * 10}">${label}</text>
4719
+ <text x="${rightX}" y="140" textLength="${valueLen * 10}">${value}</text>
4720
+ </g>
4721
+ </g>
4722
+ </svg>`;
4723
+ writeFileSync2(join3(dir, "dotdog-badge.svg"), svg);
4724
+ console.log(source_default.green(` ✓ dotdog-badge.svg (${label}: ${value})`));
4725
+ found = true;
4726
+ }
4727
+ }
4728
+ if (!found)
4729
+ console.log(source_default.yellow("No projects found. Run dotdog init first."));
4730
+ });
4678
4731
  program2.parse();
4679
4732
  export {
4680
4733
  parseToJSON,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "dotdog",
3
- "version": "0.6.0",
3
+ "version": "0.7.0",
4
4
  "description": "CLI tool for structured software specifications. Validate .dog files, compile .dag graphs, query via MCP.",
5
5
  "type": "module",
6
6
  "main": "dist/cli.js",