@zuplo/cli 6.62.7 → 6.62.9
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/README.md +36 -4
- package/dist/__tests__/import-openapi-utils.test.js +1 -2
- package/dist/__tests__/import-openapi-utils.test.js.map +1 -1
- package/dist/__tests__/import-openapi.test.js +1 -5
- package/dist/__tests__/import-openapi.test.js.map +1 -1
- package/dist/cli.js +2 -0
- package/dist/cli.js.map +1 -1
- package/dist/cmds/open-api/convert.d.ts +9 -0
- package/dist/cmds/open-api/convert.d.ts.map +1 -0
- package/dist/cmds/open-api/convert.js +66 -0
- package/dist/cmds/open-api/convert.js.map +1 -0
- package/dist/cmds/open-api/index.d.ts +4 -0
- package/dist/cmds/open-api/index.d.ts.map +1 -0
- package/dist/cmds/open-api/index.js +15 -0
- package/dist/cmds/open-api/index.js.map +1 -0
- package/dist/cmds/open-api/merge.d.ts +9 -0
- package/dist/cmds/open-api/merge.d.ts.map +1 -0
- package/dist/cmds/open-api/merge.js +57 -0
- package/dist/cmds/open-api/merge.js.map +1 -0
- package/dist/cmds/open-api/overlay.d.ts +9 -0
- package/dist/cmds/open-api/overlay.d.ts.map +1 -0
- package/dist/cmds/open-api/overlay.js +85 -0
- package/dist/cmds/open-api/overlay.js.map +1 -0
- package/dist/cmds/source/import-openapi.d.ts +1 -0
- package/dist/cmds/source/import-openapi.d.ts.map +1 -1
- package/dist/cmds/source/import-openapi.js +6 -9
- package/dist/cmds/source/import-openapi.js.map +1 -1
- package/dist/cmds/source/migrate.js +1 -1
- package/dist/cmds/source/migrate.js.map +1 -1
- package/dist/common/file-format.d.ts +25 -0
- package/dist/common/file-format.d.ts.map +1 -0
- package/dist/common/file-format.js +72 -0
- package/dist/common/file-format.js.map +1 -0
- package/dist/common/runner.d.ts.map +1 -0
- package/dist/common/runner.js.map +1 -0
- package/dist/common/utils/stringify-config.d.ts.map +1 -0
- package/dist/common/utils/stringify-config.js.map +1 -0
- package/dist/common/utils/stringify-config.test.d.ts.map +1 -0
- package/dist/common/utils/stringify-config.test.js.map +1 -0
- package/dist/open-api/convert/convert-engine.d.ts +26 -0
- package/dist/open-api/convert/convert-engine.d.ts.map +1 -0
- package/dist/open-api/convert/convert-engine.js +20 -0
- package/dist/open-api/convert/convert-engine.js.map +1 -0
- package/dist/open-api/convert/convert-engine.spec.d.ts +2 -0
- package/dist/open-api/convert/convert-engine.spec.d.ts.map +1 -0
- package/dist/open-api/convert/convert-engine.spec.js +268 -0
- package/dist/open-api/convert/convert-engine.spec.js.map +1 -0
- package/dist/open-api/convert/handler.d.ts +9 -0
- package/dist/open-api/convert/handler.d.ts.map +1 -0
- package/dist/open-api/convert/handler.js +54 -0
- package/dist/open-api/convert/handler.js.map +1 -0
- package/dist/open-api/convert/handler.spec.d.ts +2 -0
- package/dist/open-api/convert/handler.spec.d.ts.map +1 -0
- package/dist/open-api/convert/handler.spec.js +291 -0
- package/dist/open-api/convert/handler.spec.js.map +1 -0
- package/dist/open-api/merge/ajv.d.ts.map +1 -0
- package/dist/open-api/merge/ajv.js.map +1 -0
- package/dist/open-api/merge/handler.d.ts +9 -0
- package/dist/open-api/merge/handler.d.ts.map +1 -0
- package/dist/{source/import-openapi → open-api/merge}/handler.js +16 -42
- package/dist/open-api/merge/handler.js.map +1 -0
- package/dist/open-api/merge/handler.spec.d.ts +2 -0
- package/dist/open-api/merge/handler.spec.d.ts.map +1 -0
- package/dist/open-api/merge/handler.spec.js +335 -0
- package/dist/open-api/merge/handler.spec.js.map +1 -0
- package/dist/open-api/merge/interfaces.d.ts.map +1 -0
- package/dist/open-api/merge/interfaces.js.map +1 -0
- package/dist/open-api/merge/merge-engine.d.ts +23 -0
- package/dist/open-api/merge/merge-engine.d.ts.map +1 -0
- package/dist/open-api/merge/merge-engine.js +33 -0
- package/dist/open-api/merge/merge-engine.js.map +1 -0
- package/dist/open-api/merge/merge-engine.spec.d.ts +2 -0
- package/dist/open-api/merge/merge-engine.spec.d.ts.map +1 -0
- package/dist/open-api/merge/merge-engine.spec.js +117 -0
- package/dist/open-api/merge/merge-engine.spec.js.map +1 -0
- package/dist/open-api/merge/utils.d.ts.map +1 -0
- package/dist/open-api/merge/utils.js.map +1 -0
- package/dist/open-api/overlay/handler.d.ts +10 -0
- package/dist/open-api/overlay/handler.d.ts.map +1 -0
- package/dist/open-api/overlay/handler.js +92 -0
- package/dist/open-api/overlay/handler.js.map +1 -0
- package/dist/open-api/overlay/handler.spec.d.ts +2 -0
- package/dist/open-api/overlay/handler.spec.d.ts.map +1 -0
- package/dist/open-api/overlay/handler.spec.js +304 -0
- package/dist/open-api/overlay/handler.spec.js.map +1 -0
- package/dist/open-api/overlay/overlay-engine.d.ts +55 -0
- package/dist/open-api/overlay/overlay-engine.d.ts.map +1 -0
- package/dist/open-api/overlay/overlay-engine.js +280 -0
- package/dist/open-api/overlay/overlay-engine.js.map +1 -0
- package/dist/open-api/overlay/overlay-engine.spec.d.ts +2 -0
- package/dist/open-api/overlay/overlay-engine.spec.d.ts.map +1 -0
- package/dist/open-api/overlay/overlay-engine.spec.js +609 -0
- package/dist/open-api/overlay/overlay-engine.spec.js.map +1 -0
- package/dist/source/migrate/dev-portal/handler.d.ts.map +1 -0
- package/dist/{cmds/source/migrate → source/migrate/dev-portal}/handler.js +53 -4
- package/dist/source/migrate/dev-portal/handler.js.map +1 -0
- package/dist/{cmds/source/migrate → source/migrate/dev-portal}/types.d.ts +12 -1
- package/dist/source/migrate/dev-portal/types.d.ts.map +1 -0
- package/dist/source/migrate/dev-portal/types.js.map +1 -0
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +5 -4
- package/dist/cmds/source/migrate/handler.d.ts.map +0 -1
- package/dist/cmds/source/migrate/handler.js.map +0 -1
- package/dist/cmds/source/migrate/runner.d.ts.map +0 -1
- package/dist/cmds/source/migrate/runner.js.map +0 -1
- package/dist/cmds/source/migrate/stringify-config.d.ts.map +0 -1
- package/dist/cmds/source/migrate/stringify-config.js.map +0 -1
- package/dist/cmds/source/migrate/stringify-config.test.d.ts.map +0 -1
- package/dist/cmds/source/migrate/stringify-config.test.js.map +0 -1
- package/dist/cmds/source/migrate/types.d.ts.map +0 -1
- package/dist/cmds/source/migrate/types.js.map +0 -1
- package/dist/source/import-openapi/ajv.d.ts.map +0 -1
- package/dist/source/import-openapi/ajv.js.map +0 -1
- package/dist/source/import-openapi/handler.d.ts +0 -13
- package/dist/source/import-openapi/handler.d.ts.map +0 -1
- package/dist/source/import-openapi/handler.js.map +0 -1
- package/dist/source/import-openapi/interfaces.d.ts.map +0 -1
- package/dist/source/import-openapi/interfaces.js.map +0 -1
- package/dist/source/import-openapi/utils.d.ts.map +0 -1
- package/dist/source/import-openapi/utils.js.map +0 -1
- /package/dist/{cmds/source/migrate → common}/runner.d.ts +0 -0
- /package/dist/{cmds/source/migrate → common}/runner.js +0 -0
- /package/dist/{cmds/source/migrate → common/utils}/stringify-config.d.ts +0 -0
- /package/dist/{cmds/source/migrate → common/utils}/stringify-config.js +0 -0
- /package/dist/{cmds/source/migrate → common/utils}/stringify-config.test.d.ts +0 -0
- /package/dist/{cmds/source/migrate → common/utils}/stringify-config.test.js +0 -0
- /package/dist/{source/import-openapi → open-api/merge}/ajv.d.ts +0 -0
- /package/dist/{source/import-openapi → open-api/merge}/ajv.js +0 -0
- /package/dist/{source/import-openapi → open-api/merge}/interfaces.d.ts +0 -0
- /package/dist/{source/import-openapi → open-api/merge}/interfaces.js +0 -0
- /package/dist/{source/import-openapi → open-api/merge}/utils.d.ts +0 -0
- /package/dist/{source/import-openapi → open-api/merge}/utils.js +0 -0
- /package/dist/{cmds/source/migrate → source/migrate/dev-portal}/handler.d.ts +0 -0
- /package/dist/{cmds/source/migrate → source/migrate/dev-portal}/types.js +0 -0
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"import-openapi.d.ts","sourceRoot":"","sources":["../../../src/cmds/source/import-openapi.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,OAAO,CAAC
|
|
1
|
+
{"version":3,"file":"import-openapi.d.ts","sourceRoot":"","sources":["../../../src/cmds/source/import-openapi.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,OAAO,CAAC;;;;;qBASV,IAAI,KAAG,IAAI,CAAC,OAAO,CAAC;oBAoBf,OAAO;;AAxB/B,wBAgCE"}
|
|
@@ -1,17 +1,12 @@
|
|
|
1
1
|
import { captureEvent } from "../../common/analytics/lib.js";
|
|
2
|
-
import {
|
|
2
|
+
import { printDiagnosticsToConsole } from "../../common/output.js";
|
|
3
|
+
import { importOpenApi } from "../../open-api/merge/handler.js";
|
|
3
4
|
export default {
|
|
4
|
-
desc: "Import an OpenAPI file into your Zuplo project",
|
|
5
|
+
desc: "Import an OpenAPI file into your Zuplo project (use 'oas merge' instead)",
|
|
5
6
|
command: "import-openapi",
|
|
7
|
+
deprecated: "Use 'zuplo oas merge' instead",
|
|
6
8
|
builder: (yargs) => {
|
|
7
9
|
return yargs
|
|
8
|
-
.option("dir", {
|
|
9
|
-
type: "string",
|
|
10
|
-
describe: "The directory containing your project",
|
|
11
|
-
default: ".",
|
|
12
|
-
normalize: true,
|
|
13
|
-
hidden: true,
|
|
14
|
-
})
|
|
15
10
|
.option("source", {
|
|
16
11
|
type: "string",
|
|
17
12
|
describe: "The OpenAPI file to import",
|
|
@@ -30,6 +25,8 @@ export default {
|
|
|
30
25
|
});
|
|
31
26
|
},
|
|
32
27
|
handler: async (argv) => {
|
|
28
|
+
printDiagnosticsToConsole("WARNING: 'zuplo source import-openapi' is deprecated. Please use 'zuplo oas merge' instead.");
|
|
29
|
+
printDiagnosticsToConsole("");
|
|
33
30
|
await captureEvent({ argv, event: "zuplo source import-openapi" });
|
|
34
31
|
await importOpenApi(argv);
|
|
35
32
|
},
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"import-openapi.js","sourceRoot":"","sources":["../../../src/cmds/source/import-openapi.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,YAAY,EAAE,MAAM,+BAA+B,CAAC;AAC7D,OAAO,
|
|
1
|
+
{"version":3,"file":"import-openapi.js","sourceRoot":"","sources":["../../../src/cmds/source/import-openapi.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,YAAY,EAAE,MAAM,+BAA+B,CAAC;AAC7D,OAAO,EAAE,yBAAyB,EAAE,MAAM,wBAAwB,CAAC;AACnE,OAAO,EAAa,aAAa,EAAE,MAAM,iCAAiC,CAAC;AAE3E,eAAe;IACb,IAAI,EAAE,0EAA0E;IAChF,OAAO,EAAE,gBAAgB;IACzB,UAAU,EAAE,+BAA+B;IAC3C,OAAO,EAAE,CAAC,KAAW,EAAiB,EAAE;QACtC,OAAO,KAAK;aACT,MAAM,CAAC,QAAQ,EAAE;YAChB,IAAI,EAAE,QAAQ;YACd,QAAQ,EAAE,4BAA4B;YACtC,SAAS,EAAE,CAAC,YAAY,CAAC;SAC1B,CAAC;aACD,MAAM,CAAC,aAAa,EAAE;YACrB,IAAI,EAAE,QAAQ;YACd,QAAQ,EACN,+EAA+E;SAClF,CAAC;aACD,YAAY,CAAC,CAAC,QAAQ,EAAE,aAAa,CAAC,CAAC;aACvC,MAAM,CAAC,YAAY,EAAE;YACpB,IAAI,EAAE,QAAQ;YACd,QAAQ,EAAE,uDAAuD;YACjE,OAAO,EAAE,CAAC,aAAa,EAAE,cAAc,CAAC;YACxC,OAAO,EAAE,aAAa;SACvB,CAAC,CAAC;IACP,CAAC;IACD,OAAO,EAAE,KAAK,EAAE,IAAa,EAAE,EAAE;QAC/B,yBAAyB,CACvB,6FAA6F,CAC9F,CAAC;QACF,yBAAyB,CAAC,EAAE,CAAC,CAAC;QAC9B,MAAM,YAAY,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,6BAA6B,EAAE,CAAC,CAAC;QACnE,MAAM,aAAa,CAAC,IAAiB,CAAC,CAAC;IACzC,CAAC;CACF,CAAC","sourcesContent":["import { Argv } from \"yargs\";\nimport { captureEvent } from \"../../common/analytics/lib.js\";\nimport { printDiagnosticsToConsole } from \"../../common/output.js\";\nimport { Arguments, importOpenApi } from \"../../open-api/merge/handler.js\";\n\nexport default {\n desc: \"Import an OpenAPI file into your Zuplo project (use 'oas merge' instead)\",\n command: \"import-openapi\",\n deprecated: \"Use 'zuplo oas merge' instead\",\n builder: (yargs: Argv): Argv<unknown> => {\n return yargs\n .option(\"source\", {\n type: \"string\",\n describe: \"The OpenAPI file to import\",\n conflicts: [\"source-url\"],\n })\n .option(\"destination\", {\n type: \"string\",\n describe:\n \"The destination file name. Defaults to the inferred path from the source name\",\n })\n .demandOption([\"source\", \"destination\"])\n .option(\"merge-mode\", {\n type: \"string\",\n describe: \"The merge mode to use when importing the OpenAPI file\",\n choices: [\"path-method\", \"operation-id\"],\n default: \"path-method\",\n });\n },\n handler: async (argv: unknown) => {\n printDiagnosticsToConsole(\n \"WARNING: 'zuplo source import-openapi' is deprecated. Please use 'zuplo oas merge' instead.\"\n );\n printDiagnosticsToConsole(\"\");\n await captureEvent({ argv, event: \"zuplo source import-openapi\" });\n await importOpenApi(argv as Arguments);\n },\n};\n"]}
|
|
@@ -2,7 +2,7 @@ import { groupHandler } from "../../common/handler.js";
|
|
|
2
2
|
import setBlocking from "../../common/output.js";
|
|
3
3
|
import { identify } from "../../common/middleware/user-identification.js";
|
|
4
4
|
import { captureEvent } from "../../common/analytics/lib.js";
|
|
5
|
-
import { migrateDevPortal } from "
|
|
5
|
+
import { migrateDevPortal } from "../../source/migrate/dev-portal/handler.js";
|
|
6
6
|
const commands = {
|
|
7
7
|
describe: "Migration commands",
|
|
8
8
|
command: "migrate",
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"migrate.js","sourceRoot":"","sources":["../../../src/cmds/source/migrate.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,YAAY,EAAE,MAAM,yBAAyB,CAAC;AACvD,OAAO,WAAW,MAAM,wBAAwB,CAAC;AACjD,OAAO,EAAE,QAAQ,EAAE,MAAM,gDAAgD,CAAC;AAC1E,OAAO,EAAE,YAAY,EAAE,MAAM,+BAA+B,CAAC;AAC7D,OAAO,EAAE,gBAAgB,EAAE,MAAM,
|
|
1
|
+
{"version":3,"file":"migrate.js","sourceRoot":"","sources":["../../../src/cmds/source/migrate.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,YAAY,EAAE,MAAM,yBAAyB,CAAC;AACvD,OAAO,WAAW,MAAM,wBAAwB,CAAC;AACjD,OAAO,EAAE,QAAQ,EAAE,MAAM,gDAAgD,CAAC;AAC1E,OAAO,EAAE,YAAY,EAAE,MAAM,+BAA+B,CAAC;AAC7D,OAAO,EAAE,gBAAgB,EAAE,MAAM,4CAA4C,CAAC;AAG9E,MAAM,QAAQ,GAAG;IACf,QAAQ,EAAE,oBAAoB;IAC9B,OAAO,EAAE,SAAS;IAClB,OAAO,EAAE,CAAC,KAAK,EAAE,EAAE,CACjB,KAAK;SACF,OAAO,CAAC;QACP,QAAQ,EACN,uEAAuE;QACzE,OAAO,EAAE,YAAY;QACrB,OAAO,EAAE,CAAC,KAAW,EAAE,EAAE,CACvB,KAAK;aACF,MAAM,CAAC,KAAK,EAAE;YACb,IAAI,EAAE,QAAQ;YACd,QAAQ,EACN,mEAAmE;YACrE,OAAO,EAAE,GAAG;YACZ,SAAS,EAAE,IAAI;SAChB,CAAC;aACD,MAAM,CAAC,OAAO,EAAE;YACf,IAAI,EAAE,SAAS;YACf,QAAQ,EAAE,mCAAmC;YAC7C,OAAO,EAAE,KAAK;SACf,CAAC;aACD,UAAU,CAAC,CAAC,WAAW,EAAE,QAAQ,CAAC,CAAC;QACxC,OAAO,EAAE,KAAK,EAAE,IAAa,EAAE,EAAE;YAC/B,MAAM,YAAY,CAAC;gBACjB,IAAI;gBACJ,KAAK,EAAE,iCAAiC;aACzC,CAAC,CAAC;YACH,MAAM,gBAAgB,CAAC,IAAiB,CAAC,CAAC;QAC5C,CAAC;KACF,CAAC;SACD,IAAI,EAAE;IACX,OAAO,EAAE,YAAY;CACE,CAAC;AAE1B,eAAe,QAAQ,CAAC","sourcesContent":["import type { Argv, CommandModule } from \"yargs\";\nimport { groupHandler } from \"../../common/handler.js\";\nimport setBlocking from \"../../common/output.js\";\nimport { identify } from \"../../common/middleware/user-identification.js\";\nimport { captureEvent } from \"../../common/analytics/lib.js\";\nimport { migrateDevPortal } from \"../../source/migrate/dev-portal/handler.js\";\nimport type { Arguments } from \"../../source/migrate/dev-portal/types.js\";\n\nconst commands = {\n describe: \"Migration commands\",\n command: \"migrate\",\n builder: (yargs) =>\n yargs\n .command({\n describe:\n \"Migrates legacy dev portal configuration to the new dev portal format\",\n command: \"dev-portal\",\n builder: (yargs: Argv) =>\n yargs\n .option(\"dir\", {\n type: \"string\",\n describe:\n \"The directory containing your Zuplo project and dev portal config\",\n default: \".\",\n normalize: true,\n })\n .option(\"force\", {\n type: \"boolean\",\n describe: \"Force overwrite of existing files\",\n default: false,\n })\n .middleware([setBlocking, identify]),\n handler: async (argv: unknown) => {\n await captureEvent({\n argv,\n event: \"zuplo source migrate dev-portal\",\n });\n await migrateDevPortal(argv as Arguments);\n },\n })\n .help(),\n handler: groupHandler,\n} satisfies CommandModule;\n\nexport default commands;\n"]}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
export type FileFormat = "json" | "yaml";
|
|
2
|
+
export declare function detectFormatFromExtension(
|
|
3
|
+
filePath: string
|
|
4
|
+
): FileFormat | null;
|
|
5
|
+
export declare function detectFormatFromContent(content: string): FileFormat;
|
|
6
|
+
export declare function parseContent(content: string, format: FileFormat): any;
|
|
7
|
+
export declare function parseFlexible(
|
|
8
|
+
content: string,
|
|
9
|
+
knownFormat?: FileFormat
|
|
10
|
+
): {
|
|
11
|
+
document: any;
|
|
12
|
+
detectedFormat: FileFormat;
|
|
13
|
+
};
|
|
14
|
+
export declare function serializeContent(
|
|
15
|
+
document: any,
|
|
16
|
+
format: FileFormat
|
|
17
|
+
): string;
|
|
18
|
+
export declare function parseFile(
|
|
19
|
+
content: string,
|
|
20
|
+
filePath: string
|
|
21
|
+
): {
|
|
22
|
+
document: any;
|
|
23
|
+
detectedFormat: FileFormat;
|
|
24
|
+
};
|
|
25
|
+
//# sourceMappingURL=file-format.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"file-format.d.ts","sourceRoot":"","sources":["../../src/common/file-format.ts"],"names":[],"mappings":"AAEA,MAAM,MAAM,UAAU,GAAG,MAAM,GAAG,MAAM,CAAC;AAMzC,wBAAgB,yBAAyB,CAAC,QAAQ,EAAE,MAAM,GAAG,UAAU,GAAG,IAAI,CAS7E;AAMD,wBAAgB,uBAAuB,CAAC,OAAO,EAAE,MAAM,GAAG,UAAU,CAcnE;AAMD,wBAAgB,YAAY,CAAC,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,UAAU,GAAG,GAAG,CAKrE;AAOD,wBAAgB,aAAa,CAC3B,OAAO,EAAE,MAAM,EACf,WAAW,CAAC,EAAE,UAAU,GAEvB;IAAE,QAAQ,EAAE,GAAG,CAAC;IAAC,cAAc,EAAE,UAAU,CAAA;CAAE,CAuB/C;AAMD,wBAAgB,gBAAgB,CAAC,QAAQ,EAAE,GAAG,EAAE,MAAM,EAAE,UAAU,GAAG,MAAM,CAK1E;AAMD,wBAAgB,SAAS,CACvB,OAAO,EAAE,MAAM,EACf,QAAQ,EAAE,MAAM,GAEf;IAAE,QAAQ,EAAE,GAAG,CAAC;IAAC,cAAc,EAAE,UAAU,CAAA;CAAE,CAa/C"}
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
import yaml from "js-yaml";
|
|
2
|
+
export function detectFormatFromExtension(filePath) {
|
|
3
|
+
const ext = filePath.toLowerCase();
|
|
4
|
+
if (ext.endsWith(".json")) {
|
|
5
|
+
return "json";
|
|
6
|
+
}
|
|
7
|
+
if (ext.endsWith(".yaml") || ext.endsWith(".yml")) {
|
|
8
|
+
return "yaml";
|
|
9
|
+
}
|
|
10
|
+
return null;
|
|
11
|
+
}
|
|
12
|
+
export function detectFormatFromContent(content) {
|
|
13
|
+
try {
|
|
14
|
+
JSON.parse(content);
|
|
15
|
+
return "json";
|
|
16
|
+
}
|
|
17
|
+
catch {
|
|
18
|
+
try {
|
|
19
|
+
yaml.load(content);
|
|
20
|
+
return "yaml";
|
|
21
|
+
}
|
|
22
|
+
catch {
|
|
23
|
+
throw new Error("Failed to parse content as either JSON or YAML");
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
export function parseContent(content, format) {
|
|
28
|
+
if (format === "json") {
|
|
29
|
+
return JSON.parse(content);
|
|
30
|
+
}
|
|
31
|
+
return yaml.load(content);
|
|
32
|
+
}
|
|
33
|
+
export function parseFlexible(content, knownFormat) {
|
|
34
|
+
if (knownFormat) {
|
|
35
|
+
return {
|
|
36
|
+
document: parseContent(content, knownFormat),
|
|
37
|
+
detectedFormat: knownFormat,
|
|
38
|
+
};
|
|
39
|
+
}
|
|
40
|
+
try {
|
|
41
|
+
const document = JSON.parse(content);
|
|
42
|
+
return { document, detectedFormat: "json" };
|
|
43
|
+
}
|
|
44
|
+
catch {
|
|
45
|
+
try {
|
|
46
|
+
const document = yaml.load(content);
|
|
47
|
+
return { document, detectedFormat: "yaml" };
|
|
48
|
+
}
|
|
49
|
+
catch (err) {
|
|
50
|
+
throw new Error("Failed to parse content as either JSON or YAML", {
|
|
51
|
+
cause: err,
|
|
52
|
+
});
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
export function serializeContent(document, format) {
|
|
57
|
+
if (format === "json") {
|
|
58
|
+
return `${JSON.stringify(document, null, 2)}\n`;
|
|
59
|
+
}
|
|
60
|
+
return yaml.dump(document, { lineWidth: -1, noRefs: false });
|
|
61
|
+
}
|
|
62
|
+
export function parseFile(content, filePath) {
|
|
63
|
+
const formatFromExt = detectFormatFromExtension(filePath);
|
|
64
|
+
if (formatFromExt) {
|
|
65
|
+
return {
|
|
66
|
+
document: parseContent(content, formatFromExt),
|
|
67
|
+
detectedFormat: formatFromExt,
|
|
68
|
+
};
|
|
69
|
+
}
|
|
70
|
+
return parseFlexible(content);
|
|
71
|
+
}
|
|
72
|
+
//# sourceMappingURL=file-format.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"file-format.js","sourceRoot":"","sources":["../../src/common/file-format.ts"],"names":[],"mappings":"AAAA,OAAO,IAAI,MAAM,SAAS,CAAC;AAQ3B,MAAM,UAAU,yBAAyB,CAAC,QAAgB;IACxD,MAAM,GAAG,GAAG,QAAQ,CAAC,WAAW,EAAE,CAAC;IACnC,IAAI,GAAG,CAAC,QAAQ,CAAC,OAAO,CAAC,EAAE,CAAC;QAC1B,OAAO,MAAM,CAAC;IAChB,CAAC;IACD,IAAI,GAAG,CAAC,QAAQ,CAAC,OAAO,CAAC,IAAI,GAAG,CAAC,QAAQ,CAAC,MAAM,CAAC,EAAE,CAAC;QAClD,OAAO,MAAM,CAAC;IAChB,CAAC;IACD,OAAO,IAAI,CAAC;AACd,CAAC;AAMD,MAAM,UAAU,uBAAuB,CAAC,OAAe;IAErD,IAAI,CAAC;QACH,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;QACpB,OAAO,MAAM,CAAC;IAChB,CAAC;IAAC,MAAM,CAAC;QAEP,IAAI,CAAC;YACH,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;YACnB,OAAO,MAAM,CAAC;QAChB,CAAC;QAAC,MAAM,CAAC;YACP,MAAM,IAAI,KAAK,CAAC,gDAAgD,CAAC,CAAC;QACpE,CAAC;IACH,CAAC;AACH,CAAC;AAMD,MAAM,UAAU,YAAY,CAAC,OAAe,EAAE,MAAkB;IAC9D,IAAI,MAAM,KAAK,MAAM,EAAE,CAAC;QACtB,OAAO,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;IAC7B,CAAC;IACD,OAAO,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;AAC5B,CAAC;AAOD,MAAM,UAAU,aAAa,CAC3B,OAAe,EACf,WAAwB;IAGxB,IAAI,WAAW,EAAE,CAAC;QAChB,OAAO;YACL,QAAQ,EAAE,YAAY,CAAC,OAAO,EAAE,WAAW,CAAC;YAC5C,cAAc,EAAE,WAAW;SAC5B,CAAC;IACJ,CAAC;IAGD,IAAI,CAAC;QACH,MAAM,QAAQ,GAAG,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;QACrC,OAAO,EAAE,QAAQ,EAAE,cAAc,EAAE,MAAM,EAAE,CAAC;IAC9C,CAAC;IAAC,MAAM,CAAC;QAEP,IAAI,CAAC;YACH,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;YACpC,OAAO,EAAE,QAAQ,EAAE,cAAc,EAAE,MAAM,EAAE,CAAC;QAC9C,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,MAAM,IAAI,KAAK,CAAC,gDAAgD,EAAE;gBAChE,KAAK,EAAE,GAAG;aACX,CAAC,CAAC;QACL,CAAC;IACH,CAAC;AACH,CAAC;AAMD,MAAM,UAAU,gBAAgB,CAAC,QAAa,EAAE,MAAkB;IAChE,IAAI,MAAM,KAAK,MAAM,EAAE,CAAC;QACtB,OAAO,GAAG,IAAI,CAAC,SAAS,CAAC,QAAQ,EAAE,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC;IAClD,CAAC;IACD,OAAO,IAAI,CAAC,IAAI,CAAC,QAAQ,EAAE,EAAE,SAAS,EAAE,CAAC,CAAC,EAAE,MAAM,EAAE,KAAK,EAAE,CAAC,CAAC;AAC/D,CAAC;AAMD,MAAM,UAAU,SAAS,CACvB,OAAe,EACf,QAAgB;IAGhB,MAAM,aAAa,GAAG,yBAAyB,CAAC,QAAQ,CAAC,CAAC;IAE1D,IAAI,aAAa,EAAE,CAAC;QAElB,OAAO;YACL,QAAQ,EAAE,YAAY,CAAC,OAAO,EAAE,aAAa,CAAC;YAC9C,cAAc,EAAE,aAAa;SAC9B,CAAC;IACJ,CAAC;IAGD,OAAO,aAAa,CAAC,OAAO,CAAC,CAAC;AAChC,CAAC","sourcesContent":["import yaml from \"js-yaml\";\n\nexport type FileFormat = \"json\" | \"yaml\";\n\n/**\n * Detect file format from extension\n * Returns null if extension is unknown or missing\n */\nexport function detectFormatFromExtension(filePath: string): FileFormat | null {\n const ext = filePath.toLowerCase();\n if (ext.endsWith(\".json\")) {\n return \"json\";\n }\n if (ext.endsWith(\".yaml\") || ext.endsWith(\".yml\")) {\n return \"yaml\";\n }\n return null;\n}\n\n/**\n * Detect format from content by trying to parse as both JSON and YAML\n * Tries JSON first as it's faster to validate\n */\nexport function detectFormatFromContent(content: string): FileFormat {\n // Try JSON first\n try {\n JSON.parse(content);\n return \"json\";\n } catch {\n // Try YAML\n try {\n yaml.load(content);\n return \"yaml\";\n } catch {\n throw new Error(\"Failed to parse content as either JSON or YAML\");\n }\n }\n}\n\n/**\n * Parse content with a known format\n */\n// biome-ignore lint/suspicious/noExplicitAny: Generic document parsing\nexport function parseContent(content: string, format: FileFormat): any {\n if (format === \"json\") {\n return JSON.parse(content);\n }\n return yaml.load(content);\n}\n\n/**\n * Parse content with flexible format detection\n * If format is provided, uses that. Otherwise attempts to detect from content.\n */\n\nexport function parseFlexible(\n content: string,\n knownFormat?: FileFormat\n // biome-ignore lint/suspicious/noExplicitAny: Generic document parsing\n): { document: any; detectedFormat: FileFormat } {\n if (knownFormat) {\n return {\n document: parseContent(content, knownFormat),\n detectedFormat: knownFormat,\n };\n }\n\n // Try JSON first (faster)\n try {\n const document = JSON.parse(content);\n return { document, detectedFormat: \"json\" };\n } catch {\n // Try YAML\n try {\n const document = yaml.load(content);\n return { document, detectedFormat: \"yaml\" };\n } catch (err) {\n throw new Error(\"Failed to parse content as either JSON or YAML\", {\n cause: err,\n });\n }\n }\n}\n\n/**\n * Serialize document to string based on format\n */\n// biome-ignore lint/suspicious/noExplicitAny: Generic document serialization\nexport function serializeContent(document: any, format: FileFormat): string {\n if (format === \"json\") {\n return `${JSON.stringify(document, null, 2)}\\n`;\n }\n return yaml.dump(document, { lineWidth: -1, noRefs: false });\n}\n\n/**\n * Parse file content with automatic format detection from extension\n * Falls back to trying both formats if extension is unknown\n */\nexport function parseFile(\n content: string,\n filePath: string\n // biome-ignore lint/suspicious/noExplicitAny: Generic document parsing\n): { document: any; detectedFormat: FileFormat } {\n const formatFromExt = detectFormatFromExtension(filePath);\n\n if (formatFromExt) {\n // Use the format indicated by extension\n return {\n document: parseContent(content, formatFromExt),\n detectedFormat: formatFromExt,\n };\n }\n\n // No known extension, try both formats\n return parseFlexible(content);\n}\n"]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"runner.d.ts","sourceRoot":"","sources":["../../src/common/runner.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,mBAAmB;CAAG;AAEvC,MAAM,MAAM,aAAa,GAAG,OAAO,GAAG,SAAS,GAAG,MAAM,CAAC;AAEzD,MAAM,WAAW,WAAW;IAC1B,UAAU,EAAE,MAAM,CAAC;IACnB,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,aAAa,CAAC;CACzB;AAED,qBAAa,gBAAiB,SAAQ,KAAK;aAEvB,KAAK,EAAE,WAAW;aAClB,UAAU,CAAC,EAAE,MAAM;gBADnB,KAAK,EAAE,WAAW,EAClB,UAAU,CAAC,EAAE,MAAM,YAAA;CAKtC;AAED,qBAAa,YAAY;IAChB,KAAK,EAAE,MAAM,EAAE,CAAM;IACrB,MAAM,EAAE,WAAW,EAAE,CAAM;IAC3B,QAAQ,EAAE,WAAW,EAAE,CAAM;gBAExB,GAAG,CAAC,EAAE,WAAW;CAK9B;AAED,MAAM,WAAW,eAAe,CAC9B,KAAK,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC;IAE/D,IAAI,EAAE,KAAK,CAAC;IACZ,KAAK,EAAE,MAAM,EAAE,CAAC;IAChB,MAAM,EAAE,WAAW,EAAE,CAAC;IACtB,QAAQ,EAAE,WAAW,EAAE,CAAC;CACzB;AAED,MAAM,WAAW,MAAM,CACrB,OAAO,SAAS,mBAAmB,GAAG,mBAAmB,EACzD,KAAK,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC;IAE/D,CAAC,MAAM,EAAE,OAAO,EAAE,OAAO,EAAE,eAAe,CAAC,KAAK,CAAC,GAAG,OAAO,CAAC,YAAY,CAAC,CAAC;CAC3E;AAED,wBAAsB,UAAU,CAC9B,CAAC,SAAS,mBAAmB,GAAG,mBAAmB,EACnD,KAAK,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAE/D,UAAU,EAAE,MAAM,CAAC,CAAC,EAAE,KAAK,CAAC,EAAE,EAC9B,MAAM,EAAE,CAAC,EACT,OAAO,CAAC,EAAE;IAAE,gBAAgB,EAAE,OAAO,CAAA;CAAE,GACtC,OAAO,CAAC,eAAe,CAAC,KAAK,CAAC,CAAC,CAmDjC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"runner.js","sourceRoot":"","sources":["../../src/common/runner.ts"],"names":[],"mappings":"AAUA,MAAM,OAAO,gBAAiB,SAAQ,KAAK;IAEvB;IACA;IAFlB,YACkB,KAAkB,EAClB,UAAmB;QAEnC,KAAK,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;QAHL,UAAK,GAAL,KAAK,CAAa;QAClB,eAAU,GAAV,UAAU,CAAS;QAGnC,IAAI,CAAC,IAAI,GAAG,kBAAkB,CAAC;IACjC,CAAC;CACF;AAED,MAAM,OAAO,YAAY;IAChB,KAAK,GAAa,EAAE,CAAC;IACrB,MAAM,GAAkB,EAAE,CAAC;IAC3B,QAAQ,GAAkB,EAAE,CAAC;IAEpC,YAAY,GAAiB;QAC3B,IAAI,GAAG,EAAE,CAAC;YACR,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;QACxB,CAAC;IACH,CAAC;CACF;AAkBD,MAAM,CAAC,KAAK,UAAU,UAAU,CAI9B,UAA8B,EAC9B,MAAS,EACT,OAAuC;IAEvC,MAAM,QAAQ,GAAkB,EAAE,CAAC;IACnC,MAAM,MAAM,GAAkB,EAAE,CAAC;IACjC,MAAM,KAAK,GAAa,EAAE,CAAC;IAC3B,MAAM,IAAI,GAAG,EAAW,CAAC;IAEzB,IAAI,KAAK,EAAE,MAAM,MAAM,IAAI,UAAU,EAAE,CAAC;QACtC,IAAI,CAAC;YACH,MAAM,YAAY,GAAG,MAAM,MAAM,CAAC,MAAM,EAAE;gBACxC,IAAI;gBACJ,KAAK;gBACL,MAAM;gBACN,QAAQ;aACT,CAAC,CAAC;YACH,MAAM,CAAC,IAAI,CACT,GAAG,YAAY,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE;gBACjC,IAAI,GAAG,CAAC,UAAU,KAAK,EAAE,EAAE,CAAC;oBAC1B,GAAG,CAAC,UAAU,GAAG,MAAM,CAAC,IAAI,CAAC;gBAC/B,CAAC;gBACD,OAAO,GAAG,CAAC;YACb,CAAC,CAAC,CACH,CAAC;YACF,KAAK,CAAC,IAAI,CAAC,GAAG,YAAY,CAAC,KAAK,CAAC,CAAC;YAClC,QAAQ,CAAC,IAAI,CAAC,GAAG,YAAY,CAAC,QAAQ,CAAC,CAAC;YACxC,IAAI,YAAY,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;gBAGnC,MAAM;YACR,CAAC;QACH,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,IAAI,GAAG,YAAY,gBAAgB,EAAE,CAAC;gBACpC,MAAM,CAAC,IAAI,CAAC,EAAE,GAAG,GAAG,CAAC,KAAK,EAAE,UAAU,EAAE,GAAG,CAAC,UAAU,IAAI,SAAS,EAAE,CAAC,CAAC;YACzE,CAAC;iBAAM,CAAC;gBAEN,MAAM,CAAC,IAAI,CAAC;oBACV,UAAU,EAAE,MAAM,CAAC,IAAI,IAAI,SAAS;oBACpC,OAAO,EAAE,GAAG,YAAY,KAAK,CAAC,CAAC,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,GAAG,CAAC;oBACzD,QAAQ,EAAE,OAAO;iBAClB,CAAC,CAAC;YACL,CAAC;YAED,IAAI,OAAO,EAAE,gBAAgB,EAAE,CAAC;gBAC9B,MAAM,GAAG,CAAC;YACZ,CAAC;YAGD,MAAM;QACR,CAAC;IACH,CAAC;IAED,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,IAAI,EAAE,KAAK,EAAE,CAAC;AAC3C,CAAC","sourcesContent":["export interface PluginConfiguration {}\n\nexport type IssueSeverity = \"error\" | \"warning\" | \"note\";\n\nexport interface PluginIssue {\n pluginName: string;\n message: string;\n severity: IssueSeverity;\n}\n\nexport class PluginIssueError extends Error {\n constructor(\n public readonly issue: PluginIssue,\n public readonly pluginName?: string\n ) {\n super(issue.message);\n this.name = \"PluginIssueError\";\n }\n}\n\nexport class PluginResult {\n public notes: string[] = [];\n public errors: PluginIssue[] = [];\n public warnings: PluginIssue[] = [];\n\n constructor(err?: PluginIssue) {\n if (err) {\n this.errors.push(err);\n }\n }\n}\n\nexport interface PluginRunResult<\n TData extends Record<string, unknown> = Record<string, unknown>,\n> {\n data: TData;\n notes: string[];\n errors: PluginIssue[];\n warnings: PluginIssue[];\n}\n\nexport interface Plugin<\n TConfig extends PluginConfiguration = PluginConfiguration,\n TData extends Record<string, unknown> = Record<string, unknown>,\n> {\n (config: TConfig, results: PluginRunResult<TData>): Promise<PluginResult>;\n}\n\nexport async function runPlugins<\n T extends PluginConfiguration = PluginConfiguration,\n TData extends Record<string, unknown> = Record<string, unknown>,\n>(\n tasksToRun: Plugin<T, TData>[],\n config: T,\n options?: { throwOnException: boolean }\n): Promise<PluginRunResult<TData>> {\n const warnings: PluginIssue[] = [];\n const errors: PluginIssue[] = [];\n const notes: string[] = [];\n const data = {} as TData;\n\n for await (const plugin of tasksToRun) {\n try {\n const pluginResult = await plugin(config, {\n data,\n notes,\n errors,\n warnings,\n });\n errors.push(\n ...pluginResult.errors.map((err) => {\n if (err.pluginName === \"\") {\n err.pluginName = plugin.name;\n }\n return err;\n })\n );\n notes.push(...pluginResult.notes);\n warnings.push(...pluginResult.warnings);\n if (pluginResult.errors.length > 0) {\n // Don't continue the build if any of the plugins fail\n // it will just create more errors that aren't useful\n break;\n }\n } catch (err) {\n if (err instanceof PluginIssueError) {\n errors.push({ ...err.issue, pluginName: err.pluginName ?? \"unknown\" });\n } else {\n // Handle generic errors by converting them to PluginIssue\n errors.push({\n pluginName: plugin.name || \"unknown\",\n message: err instanceof Error ? err.message : String(err),\n severity: \"error\",\n });\n }\n\n if (options?.throwOnException) {\n throw err;\n }\n // Don't continue the build if there is an exception\n // it will just create more errors that aren't useful\n break;\n }\n }\n\n return { errors, warnings, data, notes };\n}\n"]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"stringify-config.d.ts","sourceRoot":"","sources":["../../../src/common/utils/stringify-config.ts"],"names":[],"mappings":"AAyBA,eAAO,MAAM,eAAe,GAAI,KAAK,OAAO,uBAAgC,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"stringify-config.js","sourceRoot":"","sources":["../../../src/common/utils/stringify-config.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,sBAAsB,CAAC;AAIjD,MAAM,SAAS,GAAG,0BAA0B,CAAC;AAM7C,MAAM,QAAQ,GAAe,CAAC,KAAK,EAAE,OAAO,EAAE,SAAS,EAAE,EAAE;IACzD,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,SAAS,CAAC,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC;QACvD,OAAO,KAAK;aACT,KAAK,CAAC,IAAI,MAAM,CAAC,SAAS,EAAE,GAAG,CAAC,CAAC;aACjC,GAAG,CAAC,CAAC,OAAO,EAAE,CAAC,EAAE,EAAE,CAElB,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,eAAe,OAAO,EAAE,CAAC,CAAC,CAAC,OAAO,IAAI,IAAI,CAAC,SAAS,CAAC,OAAO,CAAC,CACtE;aACA,MAAM,CAAC,OAAO,CAAC;aACf,IAAI,CAAC,KAAK,CAAC,CAAC;IACjB,CAAC;IAED,OAAO,SAAS,CAAC,KAAK,CAAC,CAAC;AAC1B,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,eAAe,GAAG,CAAC,GAAY,EAAE,EAAE,CAAC,SAAS,CAAC,GAAG,EAAE,QAAQ,EAAE,CAAC,CAAC,CAAC","sourcesContent":["import { stringify } from \"javascript-stringify\";\n\ntype ReplacerFn = NonNullable<Parameters<typeof stringify>[1]>;\n\nconst ENV_REGEX = /\\$env\\(([a-zA-Z0-9_]+)\\)/;\n\n/**\n * Turn \"prefix $env(NAME) suffix\"\n * into `\"prefix \" + process.env.NAME + \" suffix\"`\n */\nconst replacer: ReplacerFn = (value, _indent, stringify) => {\n if (typeof value === \"string\" && ENV_REGEX.test(value)) {\n return value\n .split(new RegExp(ENV_REGEX, \"g\"))\n .map((varName, i) =>\n // even indices → literal text, odd → env name\n i % 2 ? `process.env.${varName}` : varName && JSON.stringify(varName)\n )\n .filter(Boolean)\n .join(\" + \");\n }\n\n return stringify(value);\n};\n\nexport const stringifyConfig = (val: unknown) => stringify(val, replacer, 2);\n"]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"stringify-config.test.d.ts","sourceRoot":"","sources":["../../../src/common/utils/stringify-config.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"stringify-config.test.js","sourceRoot":"","sources":["../../../src/common/utils/stringify-config.test.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,EAAE,EAAE,MAAM,WAAW,CAAC;AACzC,OAAO,EAAE,WAAW,EAAE,MAAM,aAAa,CAAC;AAC1C,OAAO,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAExD,QAAQ,CAAC,iBAAiB,EAAE,GAAG,EAAE;IAC/B,EAAE,CAAC,gCAAgC,EAAE,GAAG,EAAE;QACxC,MAAM,MAAM,GAAG;YAEb,OAAO,EAAE,IAAI;YACb,KAAK,EAAE,EAAE;YACT,KAAK,EAAE,IAAI;YACX,KAAK,EAAE,IAAI;YACX,UAAU,EAAE,SAAS;YACrB,YAAY,EAAE,gBAAgB;YAG9B,MAAM,EAAE,eAAe;YACvB,KAAK,EAAE,oBAAoB;YAG3B,KAAK,EAAE,wBAAwB;YAC/B,OAAO,EAAE,sBAAsB;YAC/B,OAAO,EAAE,mCAAmC;YAG5C,OAAO,EAAE,sCAAsC;YAG/C,MAAM,EAAE,0BAA0B;YAGlC,WAAW,EAAE,kCAAkC;YAC/C,SAAS,EAAE,wBAAwB;YAGnC,QAAQ,EAAE;gBACR,OAAO,EAAE,mBAAmB;gBAC5B,KAAK,EAAE,4BAA4B;aACpC;YAGD,UAAU,EAAE;gBACV,iBAAiB;gBACjB,aAAa;gBACb,2BAA2B;gBAC3B,uBAAuB;aACxB;YAGD,cAAc,EAAE;gBACd,KAAK,EAAE;oBACL,QAAQ,EAAE,uBAAuB;oBACjC,MAAM,EAAE,yBAAyB;oBACjC,MAAM,EAAE,CAAC,MAAM,EAAE,mBAAmB,CAAC;iBACtC;aACF;SACF,CAAC;QAEF,MAAM,QAAQ,GAAG;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EAoCnB,CAAC;QAEC,WAAW,CAAC,eAAe,CAAC,MAAM,CAAC,EAAE,QAAQ,CAAC,CAAC;IACjD,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC","sourcesContent":["import { describe, it } from \"node:test\";\nimport { strictEqual } from \"node:assert\";\nimport { stringifyConfig } from \"./stringify-config.js\";\n\ndescribe(\"stringifyConfig\", () => {\n it(\"should handle env var patterns\", () => {\n const config = {\n // Simple values without env vars\n enabled: true,\n count: 42,\n ratio: 3.14,\n empty: null,\n notDefined: undefined,\n normalString: \"regular string\",\n\n // Env vars - complete replacement\n apiKey: \"$env(API_KEY)\",\n dbUrl: \"$env(DATABASE_URL)\",\n\n // Env vars with prefixes, suffixes, and both\n title: \"$env(APP_TITLE) Portal\",\n baseUrl: \"https://$env(DOMAIN)\",\n fullUrl: \"https://$env(HOST):$env(PORT)/api\",\n\n // Multiple env vars in one string\n message: \"$env(APP_NAME) version $env(VERSION)\",\n\n // Env vars with underscores and numbers\n secret: \"$env(JWT_SECRET_KEY_123)\",\n\n // Special characters in non-env parts\n description: 'App \"with quotes\" $env(APP_NAME)',\n multiline: \"Line1\\nLine2 $env(VAR)\",\n\n // Nested objects\n metadata: {\n favicon: \"$env(FAVICON_URL)\",\n title: \"Welcome to $env(SITE_NAME)\",\n },\n\n // Arrays with mixed content\n navigation: [\n \"$env(HOME_PATH)\",\n \"static/path\",\n \"prefix $env(DYNAMIC_PATH)\",\n \"$env(API_PATH) suffix\",\n ],\n\n // Deep nesting\n authentication: {\n oauth: {\n clientId: \"$env(OAUTH_CLIENT_ID)\",\n issuer: \"$env(OAUTH_ISSUER)/auth\",\n scopes: [\"read\", \"$env(OAUTH_SCOPE)\"],\n },\n },\n };\n\n const expected = `{\n enabled: true,\n count: 42,\n ratio: 3.14,\n empty: null,\n notDefined: undefined,\n normalString: 'regular string',\n apiKey: process.env.API_KEY,\n dbUrl: process.env.DATABASE_URL,\n title: process.env.APP_TITLE + \" Portal\",\n baseUrl: \"https://\" + process.env.DOMAIN,\n fullUrl: \"https://\" + process.env.HOST + \":\" + process.env.PORT + \"/api\",\n message: process.env.APP_NAME + \" version \" + process.env.VERSION,\n secret: process.env.JWT_SECRET_KEY_123,\n description: \"App \\\\\"with quotes\\\\\" \" + process.env.APP_NAME,\n multiline: \"Line1\\\\nLine2 \" + process.env.VAR,\n metadata: {\n favicon: process.env.FAVICON_URL,\n title: \"Welcome to \" + process.env.SITE_NAME\n },\n navigation: [\n process.env.HOME_PATH,\n 'static/path',\n \"prefix \" + process.env.DYNAMIC_PATH,\n process.env.API_PATH + \" suffix\"\n ],\n authentication: {\n oauth: {\n clientId: process.env.OAUTH_CLIENT_ID,\n issuer: process.env.OAUTH_ISSUER + \"/auth\",\n scopes: [\n 'read',\n process.env.OAUTH_SCOPE\n ]\n }\n }\n}`;\n\n strictEqual(stringifyConfig(config), expected);\n });\n});\n"]}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import {
|
|
2
|
+
detectFormatFromExtension,
|
|
3
|
+
parseContent,
|
|
4
|
+
serializeContent,
|
|
5
|
+
type FileFormat,
|
|
6
|
+
} from "../../common/file-format.js";
|
|
7
|
+
export type { FileFormat };
|
|
8
|
+
export {
|
|
9
|
+
detectFormatFromExtension as detectFormat,
|
|
10
|
+
parseContent,
|
|
11
|
+
serializeContent,
|
|
12
|
+
};
|
|
13
|
+
export interface ConversionResult {
|
|
14
|
+
content: string;
|
|
15
|
+
format: FileFormat;
|
|
16
|
+
}
|
|
17
|
+
export declare function convertDocument(
|
|
18
|
+
content: string,
|
|
19
|
+
inputFormat: FileFormat,
|
|
20
|
+
outputFormat: FileFormat
|
|
21
|
+
): ConversionResult;
|
|
22
|
+
export declare function generateOutputPath(
|
|
23
|
+
inputPath: string,
|
|
24
|
+
outputFormat: FileFormat
|
|
25
|
+
): string;
|
|
26
|
+
//# sourceMappingURL=convert-engine.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"convert-engine.d.ts","sourceRoot":"","sources":["../../../src/open-api/convert/convert-engine.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,yBAAyB,EACzB,YAAY,EACZ,gBAAgB,EAChB,KAAK,UAAU,EAChB,MAAM,6BAA6B,CAAC;AAGrC,YAAY,EAAE,UAAU,EAAE,CAAC;AAC3B,OAAO,EACL,yBAAyB,IAAI,YAAY,EACzC,YAAY,EACZ,gBAAgB,GACjB,CAAC;AAEF,MAAM,WAAW,gBAAgB;IAC/B,OAAO,EAAE,MAAM,CAAC;IAChB,MAAM,EAAE,UAAU,CAAC;CACpB;AASD,wBAAgB,eAAe,CAC7B,OAAO,EAAE,MAAM,EACf,WAAW,EAAE,UAAU,EACvB,YAAY,EAAE,UAAU,GACvB,gBAAgB,CAWlB;AAKD,wBAAgB,kBAAkB,CAChC,SAAS,EAAE,MAAM,EACjB,YAAY,EAAE,UAAU,GACvB,MAAM,CAYR"}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { detectFormatFromExtension, parseContent, serializeContent, } from "../../common/file-format.js";
|
|
2
|
+
export { detectFormatFromExtension as detectFormat, parseContent, serializeContent, };
|
|
3
|
+
export function convertDocument(content, inputFormat, outputFormat) {
|
|
4
|
+
const document = parseContent(content, inputFormat);
|
|
5
|
+
const outputContent = serializeContent(document, outputFormat);
|
|
6
|
+
return {
|
|
7
|
+
content: outputContent,
|
|
8
|
+
format: outputFormat,
|
|
9
|
+
};
|
|
10
|
+
}
|
|
11
|
+
export function generateOutputPath(inputPath, outputFormat) {
|
|
12
|
+
const lastDotIndex = inputPath.lastIndexOf(".");
|
|
13
|
+
if (lastDotIndex === -1) {
|
|
14
|
+
return `${inputPath}.${outputFormat === "yaml" ? "yaml" : "json"}`;
|
|
15
|
+
}
|
|
16
|
+
const basePath = inputPath.substring(0, lastDotIndex);
|
|
17
|
+
const newExtension = outputFormat === "yaml" ? "yaml" : "json";
|
|
18
|
+
return `${basePath}.${newExtension}`;
|
|
19
|
+
}
|
|
20
|
+
//# sourceMappingURL=convert-engine.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"convert-engine.js","sourceRoot":"","sources":["../../../src/open-api/convert/convert-engine.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,yBAAyB,EACzB,YAAY,EACZ,gBAAgB,GAEjB,MAAM,6BAA6B,CAAC;AAIrC,OAAO,EACL,yBAAyB,IAAI,YAAY,EACzC,YAAY,EACZ,gBAAgB,GACjB,CAAC;AAcF,MAAM,UAAU,eAAe,CAC7B,OAAe,EACf,WAAuB,EACvB,YAAwB;IAGxB,MAAM,QAAQ,GAAG,YAAY,CAAC,OAAO,EAAE,WAAW,CAAC,CAAC;IAGpD,MAAM,aAAa,GAAG,gBAAgB,CAAC,QAAQ,EAAE,YAAY,CAAC,CAAC;IAE/D,OAAO;QACL,OAAO,EAAE,aAAa;QACtB,MAAM,EAAE,YAAY;KACrB,CAAC;AACJ,CAAC;AAKD,MAAM,UAAU,kBAAkB,CAChC,SAAiB,EACjB,YAAwB;IAGxB,MAAM,YAAY,GAAG,SAAS,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC;IAChD,IAAI,YAAY,KAAK,CAAC,CAAC,EAAE,CAAC;QAExB,OAAO,GAAG,SAAS,IAAI,YAAY,KAAK,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC;IACrE,CAAC;IAGD,MAAM,QAAQ,GAAG,SAAS,CAAC,SAAS,CAAC,CAAC,EAAE,YAAY,CAAC,CAAC;IACtD,MAAM,YAAY,GAAG,YAAY,KAAK,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC;IAC/D,OAAO,GAAG,QAAQ,IAAI,YAAY,EAAE,CAAC;AACvC,CAAC","sourcesContent":["import {\n detectFormatFromExtension,\n parseContent,\n serializeContent,\n type FileFormat,\n} from \"../../common/file-format.js\";\n\n// Re-export common types and functions\nexport type { FileFormat };\nexport {\n detectFormatFromExtension as detectFormat,\n parseContent,\n serializeContent,\n};\n\nexport interface ConversionResult {\n content: string;\n format: FileFormat;\n}\n\n/**\n * Convert document from one format to another\n * @param content The input content as a string\n * @param inputFormat The format of the input content\n * @param outputFormat The desired output format\n * @returns The converted content\n */\nexport function convertDocument(\n content: string,\n inputFormat: FileFormat,\n outputFormat: FileFormat\n): ConversionResult {\n // Parse the input\n const document = parseContent(content, inputFormat);\n\n // Serialize to output format\n const outputContent = serializeContent(document, outputFormat);\n\n return {\n content: outputContent,\n format: outputFormat,\n };\n}\n\n/**\n * Generate output file path by replacing the extension\n */\nexport function generateOutputPath(\n inputPath: string,\n outputFormat: FileFormat\n): string {\n // Find the last dot in the path\n const lastDotIndex = inputPath.lastIndexOf(\".\");\n if (lastDotIndex === -1) {\n // No extension, just append\n return `${inputPath}.${outputFormat === \"yaml\" ? \"yaml\" : \"json\"}`;\n }\n\n // Replace extension\n const basePath = inputPath.substring(0, lastDotIndex);\n const newExtension = outputFormat === \"yaml\" ? \"yaml\" : \"json\";\n return `${basePath}.${newExtension}`;\n}\n"]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"convert-engine.spec.d.ts","sourceRoot":"","sources":["../../../src/open-api/convert/convert-engine.spec.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,268 @@
|
|
|
1
|
+
import { describe, it } from "node:test";
|
|
2
|
+
import assert from "node:assert";
|
|
3
|
+
import { detectFormat, parseContent, serializeContent, convertDocument, generateOutputPath, } from "./convert-engine.js";
|
|
4
|
+
describe("OpenAPI Convert Engine", () => {
|
|
5
|
+
describe("detectFormat", () => {
|
|
6
|
+
it("should detect JSON format from .json extension", () => {
|
|
7
|
+
assert.strictEqual(detectFormat("api.json"), "json");
|
|
8
|
+
assert.strictEqual(detectFormat("/path/to/openapi.json"), "json");
|
|
9
|
+
assert.strictEqual(detectFormat("FILE.JSON"), "json");
|
|
10
|
+
});
|
|
11
|
+
it("should detect YAML format from .yaml extension", () => {
|
|
12
|
+
assert.strictEqual(detectFormat("api.yaml"), "yaml");
|
|
13
|
+
assert.strictEqual(detectFormat("/path/to/openapi.yaml"), "yaml");
|
|
14
|
+
assert.strictEqual(detectFormat("FILE.YAML"), "yaml");
|
|
15
|
+
});
|
|
16
|
+
it("should detect YAML format from .yml extension", () => {
|
|
17
|
+
assert.strictEqual(detectFormat("api.yml"), "yaml");
|
|
18
|
+
assert.strictEqual(detectFormat("/path/to/openapi.yml"), "yaml");
|
|
19
|
+
assert.strictEqual(detectFormat("FILE.YML"), "yaml");
|
|
20
|
+
});
|
|
21
|
+
it("should return null for unknown extensions", () => {
|
|
22
|
+
assert.strictEqual(detectFormat("api.txt"), null);
|
|
23
|
+
assert.strictEqual(detectFormat("api"), null);
|
|
24
|
+
assert.strictEqual(detectFormat("api.xml"), null);
|
|
25
|
+
});
|
|
26
|
+
});
|
|
27
|
+
describe("parseContent", () => {
|
|
28
|
+
it("should parse JSON content", () => {
|
|
29
|
+
const content = '{"openapi": "3.1.0", "info": {"title": "Test"}}';
|
|
30
|
+
const result = parseContent(content, "json");
|
|
31
|
+
assert.deepStrictEqual(result, {
|
|
32
|
+
openapi: "3.1.0",
|
|
33
|
+
info: { title: "Test" },
|
|
34
|
+
});
|
|
35
|
+
});
|
|
36
|
+
it("should parse YAML content", () => {
|
|
37
|
+
const content = `openapi: 3.1.0
|
|
38
|
+
info:
|
|
39
|
+
title: Test
|
|
40
|
+
version: 1.0.0`;
|
|
41
|
+
const result = parseContent(content, "yaml");
|
|
42
|
+
assert.deepStrictEqual(result, {
|
|
43
|
+
openapi: "3.1.0",
|
|
44
|
+
info: { title: "Test", version: "1.0.0" },
|
|
45
|
+
});
|
|
46
|
+
});
|
|
47
|
+
it("should throw error for invalid JSON", () => {
|
|
48
|
+
const content = "{invalid json}";
|
|
49
|
+
assert.throws(() => parseContent(content, "json"), {
|
|
50
|
+
name: "SyntaxError",
|
|
51
|
+
});
|
|
52
|
+
});
|
|
53
|
+
it("should throw error for invalid YAML", () => {
|
|
54
|
+
const content = ":\ninvalid: : yaml";
|
|
55
|
+
assert.throws(() => parseContent(content, "yaml"));
|
|
56
|
+
});
|
|
57
|
+
it("should handle arrays", () => {
|
|
58
|
+
const jsonContent = "[1, 2, 3]";
|
|
59
|
+
const yamlContent = "- 1\n- 2\n- 3";
|
|
60
|
+
assert.deepStrictEqual(parseContent(jsonContent, "json"), [1, 2, 3]);
|
|
61
|
+
assert.deepStrictEqual(parseContent(yamlContent, "yaml"), [1, 2, 3]);
|
|
62
|
+
});
|
|
63
|
+
it("should handle nested structures", () => {
|
|
64
|
+
const content = {
|
|
65
|
+
openapi: "3.1.0",
|
|
66
|
+
paths: {
|
|
67
|
+
"/users": {
|
|
68
|
+
get: {
|
|
69
|
+
summary: "Get users",
|
|
70
|
+
parameters: [{ name: "limit", in: "query" }],
|
|
71
|
+
},
|
|
72
|
+
},
|
|
73
|
+
},
|
|
74
|
+
};
|
|
75
|
+
const jsonContent = JSON.stringify(content);
|
|
76
|
+
const result = parseContent(jsonContent, "json");
|
|
77
|
+
assert.deepStrictEqual(result, content);
|
|
78
|
+
});
|
|
79
|
+
});
|
|
80
|
+
describe("serializeContent", () => {
|
|
81
|
+
const testDocument = {
|
|
82
|
+
openapi: "3.1.0",
|
|
83
|
+
info: {
|
|
84
|
+
title: "Test API",
|
|
85
|
+
version: "1.0.0",
|
|
86
|
+
},
|
|
87
|
+
};
|
|
88
|
+
it("should serialize to JSON with proper formatting", () => {
|
|
89
|
+
const result = serializeContent(testDocument, "json");
|
|
90
|
+
assert.strictEqual(typeof result, "string");
|
|
91
|
+
assert.strictEqual(result.includes('"openapi": "3.1.0"'), true);
|
|
92
|
+
assert.strictEqual(result.includes('"title": "Test API"'), true);
|
|
93
|
+
assert.strictEqual(result.endsWith("\n"), true);
|
|
94
|
+
const parsed = JSON.parse(result);
|
|
95
|
+
assert.deepStrictEqual(parsed, testDocument);
|
|
96
|
+
});
|
|
97
|
+
it("should serialize to YAML with proper formatting", () => {
|
|
98
|
+
const result = serializeContent(testDocument, "yaml");
|
|
99
|
+
assert.strictEqual(typeof result, "string");
|
|
100
|
+
assert.strictEqual(result.includes("openapi: 3.1.0"), true);
|
|
101
|
+
assert.strictEqual(result.includes("title: Test API"), true);
|
|
102
|
+
assert.strictEqual(result.includes("version: 1.0.0"), true);
|
|
103
|
+
});
|
|
104
|
+
it("should handle arrays in JSON", () => {
|
|
105
|
+
const doc = { items: [1, 2, 3] };
|
|
106
|
+
const result = serializeContent(doc, "json");
|
|
107
|
+
assert.strictEqual(result.includes('"items": [\n'), true);
|
|
108
|
+
const parsed = JSON.parse(result);
|
|
109
|
+
assert.deepStrictEqual(parsed, doc);
|
|
110
|
+
});
|
|
111
|
+
it("should handle arrays in YAML", () => {
|
|
112
|
+
const doc = { items: [1, 2, 3] };
|
|
113
|
+
const result = serializeContent(doc, "yaml");
|
|
114
|
+
assert.strictEqual(result.includes("items:"), true);
|
|
115
|
+
assert.strictEqual(result.includes("- 1"), true);
|
|
116
|
+
});
|
|
117
|
+
it("should handle special characters in YAML", () => {
|
|
118
|
+
const doc = {
|
|
119
|
+
description: 'This has a colon: and quotes "test"',
|
|
120
|
+
};
|
|
121
|
+
const result = serializeContent(doc, "yaml");
|
|
122
|
+
assert.strictEqual(typeof result, "string");
|
|
123
|
+
assert.strictEqual(result.includes("description:"), true);
|
|
124
|
+
});
|
|
125
|
+
it("should handle null values", () => {
|
|
126
|
+
const doc = { value: null };
|
|
127
|
+
const jsonResult = serializeContent(doc, "json");
|
|
128
|
+
const yamlResult = serializeContent(doc, "yaml");
|
|
129
|
+
assert.strictEqual(jsonResult.includes('"value": null'), true);
|
|
130
|
+
assert.strictEqual(yamlResult.includes("value:"), true);
|
|
131
|
+
});
|
|
132
|
+
});
|
|
133
|
+
describe("convertDocument", () => {
|
|
134
|
+
const testDocument = {
|
|
135
|
+
openapi: "3.1.0",
|
|
136
|
+
info: {
|
|
137
|
+
title: "Test API",
|
|
138
|
+
version: "1.0.0",
|
|
139
|
+
},
|
|
140
|
+
paths: {},
|
|
141
|
+
};
|
|
142
|
+
it("should convert from JSON to YAML", () => {
|
|
143
|
+
const jsonContent = JSON.stringify(testDocument);
|
|
144
|
+
const result = convertDocument(jsonContent, "json", "yaml");
|
|
145
|
+
assert.strictEqual(result.format, "yaml");
|
|
146
|
+
assert.strictEqual(typeof result.content, "string");
|
|
147
|
+
assert.strictEqual(result.content.includes("openapi: 3.1.0"), true);
|
|
148
|
+
assert.strictEqual(result.content.includes("title: Test API"), true);
|
|
149
|
+
});
|
|
150
|
+
it("should convert from YAML to JSON", () => {
|
|
151
|
+
const yamlContent = `openapi: 3.1.0
|
|
152
|
+
info:
|
|
153
|
+
title: Test API
|
|
154
|
+
version: 1.0.0
|
|
155
|
+
paths: {}`;
|
|
156
|
+
const result = convertDocument(yamlContent, "yaml", "json");
|
|
157
|
+
assert.strictEqual(result.format, "json");
|
|
158
|
+
assert.strictEqual(typeof result.content, "string");
|
|
159
|
+
const parsed = JSON.parse(result.content);
|
|
160
|
+
assert.strictEqual(parsed.openapi, "3.1.0");
|
|
161
|
+
assert.strictEqual(parsed.info.title, "Test API");
|
|
162
|
+
});
|
|
163
|
+
it("should preserve data through JSON to YAML to JSON conversion", () => {
|
|
164
|
+
const originalJson = JSON.stringify(testDocument);
|
|
165
|
+
const yamlResult = convertDocument(originalJson, "json", "yaml");
|
|
166
|
+
const jsonResult = convertDocument(yamlResult.content, "yaml", "json");
|
|
167
|
+
const finalDocument = JSON.parse(jsonResult.content);
|
|
168
|
+
assert.deepStrictEqual(finalDocument, testDocument);
|
|
169
|
+
});
|
|
170
|
+
it("should preserve data through YAML to JSON to YAML conversion", () => {
|
|
171
|
+
const originalYaml = `openapi: 3.1.0
|
|
172
|
+
info:
|
|
173
|
+
title: Test API
|
|
174
|
+
version: 1.0.0
|
|
175
|
+
paths: {}`;
|
|
176
|
+
const originalDoc = parseContent(originalYaml, "yaml");
|
|
177
|
+
const jsonResult = convertDocument(originalYaml, "yaml", "json");
|
|
178
|
+
const yamlResult = convertDocument(jsonResult.content, "json", "yaml");
|
|
179
|
+
const finalDocument = parseContent(yamlResult.content, "yaml");
|
|
180
|
+
assert.deepStrictEqual(finalDocument, originalDoc);
|
|
181
|
+
});
|
|
182
|
+
it("should handle complex nested structures", () => {
|
|
183
|
+
const complexDoc = {
|
|
184
|
+
openapi: "3.1.0",
|
|
185
|
+
paths: {
|
|
186
|
+
"/users/{id}": {
|
|
187
|
+
get: {
|
|
188
|
+
parameters: [
|
|
189
|
+
{ name: "id", in: "path", required: true },
|
|
190
|
+
{ name: "fields", in: "query", required: false },
|
|
191
|
+
],
|
|
192
|
+
responses: {
|
|
193
|
+
"200": {
|
|
194
|
+
description: "Success",
|
|
195
|
+
content: {
|
|
196
|
+
"application/json": {
|
|
197
|
+
schema: {
|
|
198
|
+
type: "object",
|
|
199
|
+
properties: {
|
|
200
|
+
id: { type: "string" },
|
|
201
|
+
name: { type: "string" },
|
|
202
|
+
},
|
|
203
|
+
},
|
|
204
|
+
},
|
|
205
|
+
},
|
|
206
|
+
},
|
|
207
|
+
},
|
|
208
|
+
},
|
|
209
|
+
},
|
|
210
|
+
},
|
|
211
|
+
};
|
|
212
|
+
const jsonContent = JSON.stringify(complexDoc);
|
|
213
|
+
const yamlResult = convertDocument(jsonContent, "json", "yaml");
|
|
214
|
+
const backToJson = convertDocument(yamlResult.content, "yaml", "json");
|
|
215
|
+
const finalDoc = JSON.parse(backToJson.content);
|
|
216
|
+
assert.deepStrictEqual(finalDoc, complexDoc);
|
|
217
|
+
});
|
|
218
|
+
it("should handle empty objects and arrays", () => {
|
|
219
|
+
const doc = {
|
|
220
|
+
empty_object: {},
|
|
221
|
+
empty_array: [],
|
|
222
|
+
nested: {
|
|
223
|
+
also_empty: {},
|
|
224
|
+
},
|
|
225
|
+
};
|
|
226
|
+
const jsonContent = JSON.stringify(doc);
|
|
227
|
+
const yamlResult = convertDocument(jsonContent, "json", "yaml");
|
|
228
|
+
const backToJson = convertDocument(yamlResult.content, "yaml", "json");
|
|
229
|
+
const finalDoc = JSON.parse(backToJson.content);
|
|
230
|
+
assert.deepStrictEqual(finalDoc, doc);
|
|
231
|
+
});
|
|
232
|
+
});
|
|
233
|
+
describe("generateOutputPath", () => {
|
|
234
|
+
it("should replace .json with .yaml", () => {
|
|
235
|
+
assert.strictEqual(generateOutputPath("api.json", "yaml"), "api.yaml");
|
|
236
|
+
});
|
|
237
|
+
it("should replace .yaml with .json", () => {
|
|
238
|
+
assert.strictEqual(generateOutputPath("api.yaml", "json"), "api.json");
|
|
239
|
+
});
|
|
240
|
+
it("should replace .yml with .json", () => {
|
|
241
|
+
assert.strictEqual(generateOutputPath("api.yml", "json"), "api.json");
|
|
242
|
+
});
|
|
243
|
+
it("should handle paths with directories", () => {
|
|
244
|
+
assert.strictEqual(generateOutputPath("/path/to/api.json", "yaml"), "/path/to/api.yaml");
|
|
245
|
+
assert.strictEqual(generateOutputPath("/path/to/api.yaml", "json"), "/path/to/api.json");
|
|
246
|
+
});
|
|
247
|
+
it("should handle relative paths", () => {
|
|
248
|
+
assert.strictEqual(generateOutputPath("./docs/api.json", "yaml"), "./docs/api.yaml");
|
|
249
|
+
assert.strictEqual(generateOutputPath("../specs/api.yaml", "json"), "../specs/api.json");
|
|
250
|
+
});
|
|
251
|
+
it("should handle files with multiple dots in name", () => {
|
|
252
|
+
assert.strictEqual(generateOutputPath("api.v1.0.json", "yaml"), "api.v1.0.yaml");
|
|
253
|
+
assert.strictEqual(generateOutputPath("my.api.spec.yaml", "json"), "my.api.spec.json");
|
|
254
|
+
});
|
|
255
|
+
it("should append extension if file has no extension", () => {
|
|
256
|
+
assert.strictEqual(generateOutputPath("api", "json"), "api.json");
|
|
257
|
+
assert.strictEqual(generateOutputPath("openapi", "yaml"), "openapi.yaml");
|
|
258
|
+
});
|
|
259
|
+
it("should handle Windows-style paths", () => {
|
|
260
|
+
assert.strictEqual(generateOutputPath("C:\\Users\\docs\\api.json", "yaml"), "C:\\Users\\docs\\api.yaml");
|
|
261
|
+
});
|
|
262
|
+
it("should always use .yaml extension (not .yml) for yaml output", () => {
|
|
263
|
+
assert.strictEqual(generateOutputPath("api.yml", "yaml"), "api.yaml");
|
|
264
|
+
assert.strictEqual(generateOutputPath("api.json", "yaml"), "api.yaml");
|
|
265
|
+
});
|
|
266
|
+
});
|
|
267
|
+
});
|
|
268
|
+
//# sourceMappingURL=convert-engine.spec.js.map
|