Skip to content

Commit

Permalink
refactor(sharing-editor): migrate from runtypes to superstruct (#1255)
Browse files Browse the repository at this point in the history
* refactor(sharing-editor): migrate from runtypes to superstruct for type checking

- Replace runtypes Record, String, Array with superstruct object and array
- Update type definitions to use s.Infer instead of Static
- Replace .check() with s.assert() for runtime validation

Co-Authored-By: t.yic.yt@gmail.com <t.yic.yt@gmail.com>

* chore(sharing-editor): remove runtypes dependency

Co-Authored-By: t.yic.yt@gmail.com <t.yic.yt@gmail.com>

* chore: update yarn.lock after removing runtypes

Co-Authored-By: t.yic.yt@gmail.com <t.yic.yt@gmail.com>

* chore(sharing-editor): add superstruct dependency

Co-Authored-By: t.yic.yt@gmail.com <t.yic.yt@gmail.com>

---------

Co-authored-by: Devin AI <158243242+devin-ai-integration[bot]@users.noreply.github.com>
Co-authored-by: t.yic.yt@gmail.com <t.yic.yt@gmail.com>
  • Loading branch information
devin-ai-integration[bot] and whitphx authored Jan 11, 2025
1 parent c5cd44d commit 4c908b9
Show file tree
Hide file tree
Showing 3 changed files with 23 additions and 25 deletions.
41 changes: 22 additions & 19 deletions packages/sharing-editor/bin/gen-sample-app-manifests-json.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,25 +3,27 @@
import path from "path";
import fsPromises from "fs/promises";
import fsExtra from "fs-extra";
import { Record, String, Array, Static } from "runtypes";
import * as s from "superstruct";
import { parseRequirementsTxt } from "@stlite/common";

const rootDirPath = path.resolve(__dirname, "..");
const sampleAppRootDirPath = path.join(rootDirPath, "./public/samples");
const srcDirPath = path.join(rootDirPath, "./src");
const jsonOutputPath = path.join(srcDirPath, "./sample-app-manifests.json");

const SampleAppRawManifest = Record({
title: String,
entrypoint: String,
const SampleAppRawManifestStruct = s.object({
title: s.string(),
entrypoint: s.string(),
});
type SampleAppRawManifest = Static<typeof SampleAppRawManifest>;
const SampleAppManifest = SampleAppRawManifest.extend({
files: Array(String),
requirements: Array(String),
basePath: String,
type SampleAppRawManifest = s.Infer<typeof SampleAppRawManifestStruct>;
const SampleAppManifestStruct = s.object({
title: s.string(),
entrypoint: s.string(),
files: s.array(s.string()),
requirements: s.array(s.string()),
basePath: s.string(),
});
type SampleAppManifest = Static<typeof SampleAppManifest>;
type SampleAppManifest = s.Infer<typeof SampleAppManifestStruct>;

async function walk(dirPath: string, relative: boolean): Promise<string[]> {
const filePaths: string[] = [];
Expand All @@ -36,7 +38,7 @@ async function walk(dirPath: string, relative: boolean): Promise<string[]> {
} else {
filePaths.push(childPath);
}
})
}),
);

if (!relative) {
Expand All @@ -47,7 +49,7 @@ async function walk(dirPath: string, relative: boolean): Promise<string[]> {
}

async function readRequirements(
requirementsTxtPath: string
requirementsTxtPath: string,
): Promise<string[]> {
try {
const requirementsTxtData = await fsPromises.readFile(requirementsTxtPath, {
Expand All @@ -56,29 +58,30 @@ async function readRequirements(
return parseRequirementsTxt(requirementsTxtData);
} catch {
console.log(
`Failed to read ${requirementsTxtPath}. Use [] as the requirements.`
`Failed to read ${requirementsTxtPath}. Use [] as the requirements.`,
);
return [];
}
}

async function parseManifestAndFiles(
sampleAppDirName: string
sampleAppDirName: string,
): Promise<SampleAppManifest> {
const sampleAppDirPath = path.join(sampleAppRootDirPath, sampleAppDirName);

const rawManifestFileName = "stlite.json";
const rawManifestFilePath = path.join(sampleAppDirPath, rawManifestFileName);
const maybeRawManifest = await fsExtra.readJSON(rawManifestFilePath);
const rawManifest = SampleAppRawManifest.check(maybeRawManifest);
s.assert(maybeRawManifest, SampleAppRawManifestStruct);
const rawManifest = maybeRawManifest;

const requirementsTxtName = "requirements.txt";
const requirementsTxtPath = path.join(sampleAppDirPath, requirementsTxtName);
const requirements = await readRequirements(requirementsTxtPath);

const files = (await walk(sampleAppDirPath, true)).filter(
(fileName) =>
fileName !== rawManifestFileName && fileName !== requirementsTxtName
fileName !== rawManifestFileName && fileName !== requirementsTxtName,
);

return {
Expand All @@ -104,16 +107,16 @@ async function main() {
dirents
.filter((dirent) => dirent.isDirectory())
.map((dirent) => dirent.name)
.sort()
.sort(),
);

const sampleAppManifests = await Promise.all(
sampleDirNames.map((sampleDirName) =>
parseManifestAndFiles(sampleDirName).then((manifest) => ({
id: extractSampleAppId(sampleDirName),
...manifest,
}))
)
})),
),
);

await fsExtra.writeJSON(jsonOutputPath, sampleAppManifests);
Expand Down
2 changes: 1 addition & 1 deletion packages/sharing-editor/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
"react-dom": "^18.2.0",
"react-icons": "^5.0.1",
"react-router-dom": "^7.1.1",
"superstruct": "^1.0.3",
"usehooks-ts": "^3.1.0",
"web-vitals": "^3.5.2"
},
Expand Down Expand Up @@ -46,7 +47,6 @@
"@types/nprogress": "^0.2.3",
"@vitejs/plugin-react": "^4.3.4",
"jsdom": "^20.0.3",
"runtypes": "^6.6.0",
"vite": "^5.1.5"
}
}
5 changes: 0 additions & 5 deletions yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -16481,11 +16481,6 @@ run-parallel@^1.1.9:
dependencies:
queue-microtask "^1.2.2"

runtypes@^6.6.0:
version "6.7.0"
resolved "https://registry.npmjs.org/runtypes/-/runtypes-6.7.0.tgz"
integrity sha512-3TLdfFX8YHNFOhwHrSJza6uxVBmBrEjnNQlNXvXCdItS0Pdskfg5vVXUTWIN+Y23QR09jWpSl99UHkA83m4uWA==

rw@1, rw@^1.3.3:
version "1.3.3"
resolved "https://registry.npmjs.org/rw/-/rw-1.3.3.tgz"
Expand Down

0 comments on commit 4c908b9

Please sign in to comment.