@tscircuit/cli 0.1.232 → 0.1.234
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.
- package/dist/main.js +123 -65
- package/package.json +1 -1
package/dist/main.js
CHANGED
|
@@ -173655,8 +173655,8 @@ var registerRemove = (program3) => {
|
|
|
173655
173655
|
};
|
|
173656
173656
|
|
|
173657
173657
|
// cli/build/register.ts
|
|
173658
|
-
import
|
|
173659
|
-
import
|
|
173658
|
+
import path29 from "node:path";
|
|
173659
|
+
import fs30 from "node:fs";
|
|
173660
173660
|
|
|
173661
173661
|
// cli/build/build-file.ts
|
|
173662
173662
|
import path26 from "node:path";
|
|
@@ -173800,10 +173800,55 @@ ${scriptBlock} <script src="https://cdn.tailwindcss.com"></script>
|
|
|
173800
173800
|
</html>`;
|
|
173801
173801
|
};
|
|
173802
173802
|
|
|
173803
|
+
// cli/build/build-preview-images.ts
|
|
173804
|
+
import fs29 from "node:fs";
|
|
173805
|
+
import path28 from "node:path";
|
|
173806
|
+
import {
|
|
173807
|
+
convertCircuitJsonToPcbSvg as convertCircuitJsonToPcbSvg3,
|
|
173808
|
+
convertCircuitJsonToSchematicSvg as convertCircuitJsonToSchematicSvg2
|
|
173809
|
+
} from "circuit-to-svg";
|
|
173810
|
+
import { convertCircuitJsonToSimple3dSvg } from "circuit-json-to-simple-3d";
|
|
173811
|
+
import sharp from "sharp";
|
|
173812
|
+
var buildPreviewImages = async ({
|
|
173813
|
+
builtFiles,
|
|
173814
|
+
distDir,
|
|
173815
|
+
mainEntrypoint
|
|
173816
|
+
}) => {
|
|
173817
|
+
const successfulBuilds = builtFiles.filter((file) => file.ok);
|
|
173818
|
+
const normalizedMainEntrypoint = mainEntrypoint ? path28.resolve(mainEntrypoint) : undefined;
|
|
173819
|
+
const previewBuild = (() => {
|
|
173820
|
+
if (normalizedMainEntrypoint) {
|
|
173821
|
+
const match = successfulBuilds.find((built) => path28.resolve(built.sourcePath) === normalizedMainEntrypoint);
|
|
173822
|
+
if (match)
|
|
173823
|
+
return match;
|
|
173824
|
+
}
|
|
173825
|
+
return successfulBuilds[0];
|
|
173826
|
+
})();
|
|
173827
|
+
if (!previewBuild) {
|
|
173828
|
+
console.warn("No successful build output available for preview image generation.");
|
|
173829
|
+
return;
|
|
173830
|
+
}
|
|
173831
|
+
try {
|
|
173832
|
+
const circuitJsonRaw = fs29.readFileSync(previewBuild.outputPath, "utf-8");
|
|
173833
|
+
const circuitJson = JSON.parse(circuitJsonRaw);
|
|
173834
|
+
const pcbSvg = convertCircuitJsonToPcbSvg3(circuitJson);
|
|
173835
|
+
const schematicSvg = convertCircuitJsonToSchematicSvg2(circuitJson);
|
|
173836
|
+
const simple3dSvg = await convertCircuitJsonToSimple3dSvg(circuitJson);
|
|
173837
|
+
fs29.writeFileSync(path28.join(distDir, "pcb.svg"), pcbSvg, "utf-8");
|
|
173838
|
+
fs29.writeFileSync(path28.join(distDir, "schematic.svg"), schematicSvg, "utf-8");
|
|
173839
|
+
if (simple3dSvg) {
|
|
173840
|
+
const pngBuffer = await sharp(Buffer.from(simple3dSvg)).png().toBuffer();
|
|
173841
|
+
fs29.writeFileSync(path28.join(distDir, "3d.png"), pngBuffer);
|
|
173842
|
+
}
|
|
173843
|
+
} catch (error) {
|
|
173844
|
+
console.error("Failed to generate preview images:", error);
|
|
173845
|
+
}
|
|
173846
|
+
};
|
|
173847
|
+
|
|
173803
173848
|
// cli/build/register.ts
|
|
173804
173849
|
var registerBuild = (program3) => {
|
|
173805
|
-
program3.command("build").description("Run tscircuit eval and output circuit json").argument("[file]", "Path to the entry file").option("--ignore-errors", "Do not exit with code 1 on errors").option("--ignore-warnings", "Do not log warnings").option("--disable-pcb", "Disable PCB outputs").option("--disable-parts-engine", "Disable the parts engine").option("--site", "Generate a static site in the dist directory").action(async (file, options) => {
|
|
173806
|
-
const { projectDir, circuitFiles } = await getBuildEntrypoints({
|
|
173850
|
+
program3.command("build").description("Run tscircuit eval and output circuit json").argument("[file]", "Path to the entry file").option("--ignore-errors", "Do not exit with code 1 on errors").option("--ignore-warnings", "Do not log warnings").option("--disable-pcb", "Disable PCB outputs").option("--disable-parts-engine", "Disable the parts engine").option("--site", "Generate a static site in the dist directory").option("--preview-images", "Generate preview images in the dist directory").action(async (file, options) => {
|
|
173851
|
+
const { projectDir, circuitFiles, mainEntrypoint } = await getBuildEntrypoints({
|
|
173807
173852
|
fileOrDir: file
|
|
173808
173853
|
});
|
|
173809
173854
|
const platformConfig2 = (() => {
|
|
@@ -173818,25 +173863,31 @@ var registerBuild = (program3) => {
|
|
|
173818
173863
|
}
|
|
173819
173864
|
return config;
|
|
173820
173865
|
})();
|
|
173821
|
-
const distDir =
|
|
173822
|
-
|
|
173866
|
+
const distDir = path29.join(projectDir, "dist");
|
|
173867
|
+
fs30.mkdirSync(distDir, { recursive: true });
|
|
173823
173868
|
let hasErrors = false;
|
|
173824
173869
|
const staticFileReferences = [];
|
|
173870
|
+
const builtFiles = [];
|
|
173825
173871
|
for (const filePath of circuitFiles) {
|
|
173826
|
-
const relative9 =
|
|
173872
|
+
const relative9 = path29.relative(projectDir, filePath);
|
|
173827
173873
|
const outputDirName = relative9.replace(/(\.board|\.circuit)?\.tsx$/, "");
|
|
173828
|
-
const outputPath =
|
|
173874
|
+
const outputPath = path29.join(distDir, outputDirName, "circuit.json");
|
|
173829
173875
|
const ok = await buildFile(filePath, outputPath, projectDir, {
|
|
173830
173876
|
ignoreErrors: options?.ignoreErrors,
|
|
173831
173877
|
ignoreWarnings: options?.ignoreWarnings,
|
|
173832
173878
|
platformConfig: platformConfig2
|
|
173833
173879
|
});
|
|
173880
|
+
builtFiles.push({
|
|
173881
|
+
sourcePath: filePath,
|
|
173882
|
+
outputPath,
|
|
173883
|
+
ok
|
|
173884
|
+
});
|
|
173834
173885
|
if (!ok) {
|
|
173835
173886
|
hasErrors = true;
|
|
173836
173887
|
} else if (options?.site) {
|
|
173837
|
-
const normalizedSourcePath = relative9.split(
|
|
173838
|
-
const relativeOutputPath =
|
|
173839
|
-
const normalizedOutputPath = relativeOutputPath.split(
|
|
173888
|
+
const normalizedSourcePath = relative9.split(path29.sep).join("/");
|
|
173889
|
+
const relativeOutputPath = path29.join(outputDirName, "circuit.json");
|
|
173890
|
+
const normalizedOutputPath = relativeOutputPath.split(path29.sep).join("/");
|
|
173840
173891
|
staticFileReferences.push({
|
|
173841
173892
|
filePath: normalizedSourcePath,
|
|
173842
173893
|
fileStaticAssetUrl: `./${normalizedOutputPath}`
|
|
@@ -173846,31 +173897,38 @@ var registerBuild = (program3) => {
|
|
|
173846
173897
|
if (hasErrors && !options?.ignoreErrors) {
|
|
173847
173898
|
process.exit(1);
|
|
173848
173899
|
}
|
|
173900
|
+
if (options?.previewImages) {
|
|
173901
|
+
await buildPreviewImages({
|
|
173902
|
+
builtFiles,
|
|
173903
|
+
distDir,
|
|
173904
|
+
mainEntrypoint
|
|
173905
|
+
});
|
|
173906
|
+
}
|
|
173849
173907
|
if (options?.site) {
|
|
173850
173908
|
const indexHtml = getStaticIndexHtmlFile({
|
|
173851
173909
|
files: staticFileReferences,
|
|
173852
173910
|
standaloneScriptSrc: "./standalone.min.js"
|
|
173853
173911
|
});
|
|
173854
|
-
|
|
173855
|
-
|
|
173912
|
+
fs30.writeFileSync(path29.join(distDir, "index.html"), indexHtml);
|
|
173913
|
+
fs30.writeFileSync(path29.join(distDir, "standalone.min.js"), standalone_min_default);
|
|
173856
173914
|
}
|
|
173857
173915
|
});
|
|
173858
173916
|
};
|
|
173859
173917
|
|
|
173860
173918
|
// lib/shared/snapshot-project.ts
|
|
173861
|
-
import
|
|
173862
|
-
import
|
|
173919
|
+
import fs32 from "node:fs";
|
|
173920
|
+
import path30 from "node:path";
|
|
173863
173921
|
import looksSame2 from "looks-same";
|
|
173864
|
-
import
|
|
173922
|
+
import sharp2 from "sharp";
|
|
173865
173923
|
import {
|
|
173866
|
-
convertCircuitJsonToPcbSvg as
|
|
173867
|
-
convertCircuitJsonToSchematicSvg as
|
|
173924
|
+
convertCircuitJsonToPcbSvg as convertCircuitJsonToPcbSvg4,
|
|
173925
|
+
convertCircuitJsonToSchematicSvg as convertCircuitJsonToSchematicSvg3
|
|
173868
173926
|
} from "circuit-to-svg";
|
|
173869
|
-
import { convertCircuitJsonToSimple3dSvg } from "circuit-json-to-simple-3d";
|
|
173927
|
+
import { convertCircuitJsonToSimple3dSvg as convertCircuitJsonToSimple3dSvg2 } from "circuit-json-to-simple-3d";
|
|
173870
173928
|
|
|
173871
173929
|
// lib/shared/compare-images.ts
|
|
173872
173930
|
import looksSame from "looks-same";
|
|
173873
|
-
import
|
|
173931
|
+
import fs31 from "node:fs/promises";
|
|
173874
173932
|
var compareAndCreateDiff = async (buffer1, buffer2, diffPath) => {
|
|
173875
173933
|
const { equal: equal2 } = await looksSame(buffer1, buffer2, {
|
|
173876
173934
|
strict: false,
|
|
@@ -173886,7 +173944,7 @@ var compareAndCreateDiff = async (buffer1, buffer2, diffPath) => {
|
|
|
173886
173944
|
tolerance: 2
|
|
173887
173945
|
});
|
|
173888
173946
|
} else {
|
|
173889
|
-
await
|
|
173947
|
+
await fs31.writeFile(diffPath, buffer2);
|
|
173890
173948
|
}
|
|
173891
173949
|
}
|
|
173892
173950
|
return { equal: equal2 };
|
|
@@ -173911,19 +173969,19 @@ var snapshotProject = async ({
|
|
|
173911
173969
|
...DEFAULT_IGNORED_PATTERNS,
|
|
173912
173970
|
...ignored.map(normalizeIgnorePattern)
|
|
173913
173971
|
];
|
|
173914
|
-
const resolvedPaths = filePaths.map((f) =>
|
|
173972
|
+
const resolvedPaths = filePaths.map((f) => path30.resolve(projectDir, f));
|
|
173915
173973
|
const boardFiles = resolvedPaths.length > 0 ? resolvedPaths.flatMap((p) => {
|
|
173916
|
-
if (
|
|
173974
|
+
if (fs32.existsSync(p) && fs32.statSync(p).isDirectory()) {
|
|
173917
173975
|
return globbySync(["**/*.board.tsx", "**/*.circuit.tsx"], {
|
|
173918
173976
|
cwd: p,
|
|
173919
173977
|
ignore
|
|
173920
|
-
}).map((f) =>
|
|
173978
|
+
}).map((f) => path30.join(p, f));
|
|
173921
173979
|
}
|
|
173922
173980
|
return [p];
|
|
173923
173981
|
}) : globbySync(["**/*.board.tsx", "**/*.circuit.tsx"], {
|
|
173924
173982
|
cwd: projectDir,
|
|
173925
173983
|
ignore
|
|
173926
|
-
}).map((f) =>
|
|
173984
|
+
}).map((f) => path30.join(projectDir, f));
|
|
173927
173985
|
if (boardFiles.length === 0) {
|
|
173928
173986
|
console.log("No entrypoint found. Run 'tsci init' to bootstrap a project or specify a file with 'tsci snapshot <file>'");
|
|
173929
173987
|
return onExit(0);
|
|
@@ -173935,12 +173993,12 @@ var snapshotProject = async ({
|
|
|
173935
173993
|
filePath: file,
|
|
173936
173994
|
platformConfig: platformConfig2
|
|
173937
173995
|
});
|
|
173938
|
-
const pcbSvg =
|
|
173939
|
-
const schSvg =
|
|
173940
|
-
const svg3d = threeD ? await
|
|
173941
|
-
const snapDir =
|
|
173942
|
-
|
|
173943
|
-
const base =
|
|
173996
|
+
const pcbSvg = convertCircuitJsonToPcbSvg4(circuitJson);
|
|
173997
|
+
const schSvg = convertCircuitJsonToSchematicSvg3(circuitJson);
|
|
173998
|
+
const svg3d = threeD ? await convertCircuitJsonToSimple3dSvg2(circuitJson) : null;
|
|
173999
|
+
const snapDir = path30.join(path30.dirname(file), "__snapshots__");
|
|
174000
|
+
fs32.mkdirSync(snapDir, { recursive: true });
|
|
174001
|
+
const base = path30.basename(file).replace(/\.tsx$/, "");
|
|
173944
174002
|
const pairs3 = [];
|
|
173945
174003
|
if (pcbOnly || !schematicOnly)
|
|
173946
174004
|
pairs3.push(["pcb", pcbSvg]);
|
|
@@ -173954,31 +174012,31 @@ var snapshotProject = async ({
|
|
|
173954
174012
|
}
|
|
173955
174013
|
for (const [type, newSvg] of pairs3) {
|
|
173956
174014
|
const is3d = type === "3d";
|
|
173957
|
-
const snapPath =
|
|
173958
|
-
const existing =
|
|
173959
|
-
const newContentBuffer = is3d ? await
|
|
174015
|
+
const snapPath = path30.join(snapDir, `${base}-${type}.snap.${is3d ? "png" : "svg"}`);
|
|
174016
|
+
const existing = fs32.existsSync(snapPath);
|
|
174017
|
+
const newContentBuffer = is3d ? await sharp2(Buffer.from(newSvg)).png().toBuffer() : Buffer.from(newSvg, "utf8");
|
|
173960
174018
|
const newContentForFile = is3d ? newContentBuffer : newSvg;
|
|
173961
174019
|
if (!existing) {
|
|
173962
|
-
|
|
173963
|
-
console.log("✅", kleur_default.gray(
|
|
174020
|
+
fs32.writeFileSync(snapPath, newContentForFile);
|
|
174021
|
+
console.log("✅", kleur_default.gray(path30.relative(projectDir, snapPath)));
|
|
173964
174022
|
didUpdate = true;
|
|
173965
174023
|
continue;
|
|
173966
174024
|
}
|
|
173967
|
-
const oldContentBuffer =
|
|
174025
|
+
const oldContentBuffer = fs32.readFileSync(snapPath);
|
|
173968
174026
|
const diffPath = snapPath.replace(is3d ? ".snap.png" : ".snap.svg", is3d ? ".diff.png" : ".diff.svg");
|
|
173969
174027
|
const { equal: equal2 } = await compareAndCreateDiff(oldContentBuffer, newContentBuffer, diffPath);
|
|
173970
174028
|
if (update) {
|
|
173971
174029
|
if (!forceUpdate && equal2) {
|
|
173972
|
-
console.log("✅", kleur_default.gray(
|
|
174030
|
+
console.log("✅", kleur_default.gray(path30.relative(projectDir, snapPath)));
|
|
173973
174031
|
} else {
|
|
173974
|
-
|
|
173975
|
-
console.log("✅", kleur_default.gray(
|
|
174032
|
+
fs32.writeFileSync(snapPath, newContentForFile);
|
|
174033
|
+
console.log("✅", kleur_default.gray(path30.relative(projectDir, snapPath)));
|
|
173976
174034
|
didUpdate = true;
|
|
173977
174035
|
}
|
|
173978
174036
|
} else if (!equal2) {
|
|
173979
174037
|
mismatches.push(`${snapPath} (diff: ${diffPath})`);
|
|
173980
174038
|
} else {
|
|
173981
|
-
console.log("✅", kleur_default.gray(
|
|
174039
|
+
console.log("✅", kleur_default.gray(path30.relative(projectDir, snapPath)));
|
|
173982
174040
|
}
|
|
173983
174041
|
}
|
|
173984
174042
|
}
|
|
@@ -174017,22 +174075,22 @@ var registerSnapshot = (program3) => {
|
|
|
174017
174075
|
};
|
|
174018
174076
|
|
|
174019
174077
|
// lib/shared/setup-github-actions.ts
|
|
174020
|
-
import
|
|
174021
|
-
import
|
|
174078
|
+
import fs33 from "node:fs";
|
|
174079
|
+
import path31 from "node:path";
|
|
174022
174080
|
var setupGithubActions = (projectDir = process.cwd()) => {
|
|
174023
174081
|
const findGitRoot = (startDir) => {
|
|
174024
|
-
let dir =
|
|
174025
|
-
while (dir !==
|
|
174026
|
-
if (
|
|
174082
|
+
let dir = path31.resolve(startDir);
|
|
174083
|
+
while (dir !== path31.parse(dir).root) {
|
|
174084
|
+
if (fs33.existsSync(path31.join(dir, ".git"))) {
|
|
174027
174085
|
return dir;
|
|
174028
174086
|
}
|
|
174029
|
-
dir =
|
|
174087
|
+
dir = path31.dirname(dir);
|
|
174030
174088
|
}
|
|
174031
174089
|
return null;
|
|
174032
174090
|
};
|
|
174033
174091
|
const gitRoot = findGitRoot(projectDir) ?? projectDir;
|
|
174034
|
-
const workflowsDir =
|
|
174035
|
-
|
|
174092
|
+
const workflowsDir = path31.join(gitRoot, ".github", "workflows");
|
|
174093
|
+
fs33.mkdirSync(workflowsDir, { recursive: true });
|
|
174036
174094
|
const buildWorkflow = `name: tscircuit Build
|
|
174037
174095
|
|
|
174038
174096
|
on:
|
|
@@ -174071,8 +174129,8 @@ jobs:
|
|
|
174071
174129
|
- run: bun install
|
|
174072
174130
|
- run: bunx tsci snapshot
|
|
174073
174131
|
`;
|
|
174074
|
-
writeFileIfNotExists(
|
|
174075
|
-
writeFileIfNotExists(
|
|
174132
|
+
writeFileIfNotExists(path31.join(workflowsDir, "tscircuit-build.yml"), buildWorkflow);
|
|
174133
|
+
writeFileIfNotExists(path31.join(workflowsDir, "tscircuit-snapshot.yml"), snapshotWorkflow);
|
|
174076
174134
|
};
|
|
174077
174135
|
|
|
174078
174136
|
// cli/setup/register.ts
|
|
@@ -174098,8 +174156,8 @@ var registerSetup = (program3) => {
|
|
|
174098
174156
|
};
|
|
174099
174157
|
|
|
174100
174158
|
// cli/convert/register.ts
|
|
174101
|
-
import
|
|
174102
|
-
import
|
|
174159
|
+
import fs34 from "node:fs/promises";
|
|
174160
|
+
import path32 from "node:path";
|
|
174103
174161
|
|
|
174104
174162
|
// node_modules/kicad-component-converter/dist/index.js
|
|
174105
174163
|
var __create4 = Object.create;
|
|
@@ -175411,8 +175469,8 @@ function getErrorMap() {
|
|
|
175411
175469
|
return overrideErrorMap;
|
|
175412
175470
|
}
|
|
175413
175471
|
var makeIssue = (params2) => {
|
|
175414
|
-
const { data, path:
|
|
175415
|
-
const fullPath = [...
|
|
175472
|
+
const { data, path: path32, errorMaps, issueData } = params2;
|
|
175473
|
+
const fullPath = [...path32, ...issueData.path || []];
|
|
175416
175474
|
const fullIssue = {
|
|
175417
175475
|
...issueData,
|
|
175418
175476
|
path: fullPath
|
|
@@ -175520,11 +175578,11 @@ var errorUtil;
|
|
|
175520
175578
|
errorUtil2.toString = (message) => typeof message === "string" ? message : message?.message;
|
|
175521
175579
|
})(errorUtil || (errorUtil = {}));
|
|
175522
175580
|
var ParseInputLazyPath = class {
|
|
175523
|
-
constructor(parent, value,
|
|
175581
|
+
constructor(parent, value, path32, key) {
|
|
175524
175582
|
this._cachedPath = [];
|
|
175525
175583
|
this.parent = parent;
|
|
175526
175584
|
this.data = value;
|
|
175527
|
-
this._path =
|
|
175585
|
+
this._path = path32;
|
|
175528
175586
|
this._key = key;
|
|
175529
175587
|
}
|
|
175530
175588
|
get path() {
|
|
@@ -179313,14 +179371,14 @@ function generateArcPath(start, mid, end, numPoints) {
|
|
|
179313
179371
|
if (angleDelta < 0) {
|
|
179314
179372
|
angleDelta += 2 * Math.PI;
|
|
179315
179373
|
}
|
|
179316
|
-
const
|
|
179374
|
+
const path32 = [];
|
|
179317
179375
|
for (let i = 0;i <= numPoints; i++) {
|
|
179318
179376
|
const angle = angleStart + i / numPoints * angleDelta;
|
|
179319
179377
|
const x = center2.x + radius * Math.cos(angle);
|
|
179320
179378
|
const y = center2.y + radius * Math.sin(angle);
|
|
179321
|
-
|
|
179379
|
+
path32.push({ x, y });
|
|
179322
179380
|
}
|
|
179323
|
-
return
|
|
179381
|
+
return path32;
|
|
179324
179382
|
}
|
|
179325
179383
|
var makePoint = (p) => {
|
|
179326
179384
|
if (Array.isArray(p)) {
|
|
@@ -179764,15 +179822,15 @@ var convertCircuitJsonToTscircuit = (circuitJson, opts) => {
|
|
|
179764
179822
|
var registerConvert = (program3) => {
|
|
179765
179823
|
program3.command("convert").description("Convert a .kicad_mod footprint to a tscircuit component").argument("<file>", "Path to the .kicad_mod file").option("-o, --output <path>", "Output TSX file path").option("-n, --name <component>", "Component name for export").action(async (file, options) => {
|
|
179766
179824
|
try {
|
|
179767
|
-
const inputPath =
|
|
179768
|
-
const modContent = await
|
|
179825
|
+
const inputPath = path32.resolve(file);
|
|
179826
|
+
const modContent = await fs34.readFile(inputPath, "utf-8");
|
|
179769
179827
|
const circuitJson = await parseKicadModToCircuitJson(modContent);
|
|
179770
|
-
const componentName = options.name ??
|
|
179828
|
+
const componentName = options.name ?? path32.basename(inputPath, ".kicad_mod");
|
|
179771
179829
|
const tsx = convertCircuitJsonToTscircuit(circuitJson, {
|
|
179772
179830
|
componentName
|
|
179773
179831
|
});
|
|
179774
|
-
const outputPath = options.output ?
|
|
179775
|
-
await
|
|
179832
|
+
const outputPath = options.output ? path32.resolve(options.output) : path32.join(path32.dirname(inputPath), `${componentName}.tsx`);
|
|
179833
|
+
await fs34.writeFile(outputPath, tsx);
|
|
179776
179834
|
console.log(kleur_default.green(`Converted ${outputPath}`));
|
|
179777
179835
|
} catch (error) {
|
|
179778
179836
|
console.error(kleur_default.red("Failed to convert footprint:"), error instanceof Error ? error.message : error);
|