silgi 0.30.5 → 0.31.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.
- package/dist/build.mjs +7 -78
- package/dist/cli/build.mjs +178 -298
- package/dist/cli/dev.mjs +83 -0
- package/dist/cli/index.mjs +1 -1
- package/dist/cli/init.mjs +0 -1
- package/dist/cli/install.mjs +0 -1
- package/dist/cli/watch.mjs +10 -54
- package/dist/types/index.d.mts +5 -3
- package/package.json +2 -3
- package/dist/cli/devServer.mjs +0 -8
package/dist/build.mjs
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
|
-
|
|
2
|
-
import
|
|
3
|
-
import
|
|
4
|
-
import
|
|
5
|
-
import
|
|
6
|
-
import
|
|
7
|
-
import { c as createSilgiCLI, b as build } from './cli/build.mjs';
|
|
1
|
+
export { p as prepareBuild, w as watchDev } from './cli/dev.mjs';
|
|
2
|
+
import 'chokidar';
|
|
3
|
+
import 'consola';
|
|
4
|
+
import 'pathe';
|
|
5
|
+
import 'perfect-debounce';
|
|
6
|
+
import './_chunks/silgiApp.mjs';
|
|
8
7
|
import 'unctx';
|
|
9
8
|
import 'silgi';
|
|
9
|
+
import './cli/build.mjs';
|
|
10
10
|
import 'hookable';
|
|
11
11
|
import 'silgi/kit';
|
|
12
12
|
import 'silgi/runtime/meta';
|
|
@@ -27,7 +27,6 @@ import 'exsolve';
|
|
|
27
27
|
import 'node:fs/promises';
|
|
28
28
|
import 'globby';
|
|
29
29
|
import 'ignore';
|
|
30
|
-
import '@oxc-parser/wasm';
|
|
31
30
|
import 'knitwork';
|
|
32
31
|
import 'klona';
|
|
33
32
|
import 'silgi/runtime';
|
|
@@ -44,73 +43,3 @@ import 'pkg-types';
|
|
|
44
43
|
import 'apiful/openapi';
|
|
45
44
|
import 'pathe/utils';
|
|
46
45
|
import 'untyped';
|
|
47
|
-
|
|
48
|
-
async function prepareBuild(config) {
|
|
49
|
-
const silgi = await createSilgiCLI({
|
|
50
|
-
commandType: config?.commandType || "prepare",
|
|
51
|
-
...config
|
|
52
|
-
});
|
|
53
|
-
await build(silgi);
|
|
54
|
-
return silgi;
|
|
55
|
-
}
|
|
56
|
-
|
|
57
|
-
async function watchDev() {
|
|
58
|
-
let watcher;
|
|
59
|
-
async function load() {
|
|
60
|
-
await prepareBuild({
|
|
61
|
-
commandType: "prepare",
|
|
62
|
-
activeEnvironment: ".env"
|
|
63
|
-
});
|
|
64
|
-
}
|
|
65
|
-
const reload = debounce(load);
|
|
66
|
-
const silgi = useSilgiCLI();
|
|
67
|
-
silgi.options.watchOptions.ignored ??= [];
|
|
68
|
-
silgi.options.watchOptions.ignoreInitial = true;
|
|
69
|
-
if (Array.isArray(silgi.options.watchOptions.ignored)) {
|
|
70
|
-
silgi.options.watchOptions.ignored.push(
|
|
71
|
-
`!${join(silgi.options.silgi.serverDir, "config")}`
|
|
72
|
-
);
|
|
73
|
-
}
|
|
74
|
-
silgi.options.devServer.watch.push(
|
|
75
|
-
join(silgi.options.serverDir, "services"),
|
|
76
|
-
join(silgi.options.serverDir, "schemas"),
|
|
77
|
-
join(silgi.options.serverDir, "shared"),
|
|
78
|
-
join(silgi.options.serverDir, "utils"),
|
|
79
|
-
join(silgi.options.serverDir, "types"),
|
|
80
|
-
join(silgi.options.silgi.serverDir, "config"),
|
|
81
|
-
join(silgi.options.rootDir, "silgi.config.ts")
|
|
82
|
-
);
|
|
83
|
-
const watchReloadEvents = /* @__PURE__ */ new Set(["add", "addDir", "unlink", "unlinkDir", "change"]);
|
|
84
|
-
if (silgi.options.devServer.watch.length > 0) {
|
|
85
|
-
silgi.options.devServer.watch = [...new Set(silgi.options.devServer.watch)];
|
|
86
|
-
watcher = watch(silgi.options.devServer.watch, silgi.options.watchOptions);
|
|
87
|
-
watcher.on("all", async (event, path, stats) => {
|
|
88
|
-
if (!watchReloadEvents.has(event)) {
|
|
89
|
-
return;
|
|
90
|
-
}
|
|
91
|
-
const startTime = performance.now();
|
|
92
|
-
silgi.errors = [];
|
|
93
|
-
try {
|
|
94
|
-
await reloadScan(path, stats);
|
|
95
|
-
await reload();
|
|
96
|
-
} catch (error) {
|
|
97
|
-
consola.withTag("silgi").error(error);
|
|
98
|
-
}
|
|
99
|
-
silgi.errors = [];
|
|
100
|
-
const endTime = performance.now();
|
|
101
|
-
const elapsedTime = Math.round(endTime - startTime);
|
|
102
|
-
silgi.logger.success(`${basename(path)} - ${elapsedTime}ms`);
|
|
103
|
-
}).on("error", (error) => {
|
|
104
|
-
consola.withTag("silgi").error(error);
|
|
105
|
-
});
|
|
106
|
-
}
|
|
107
|
-
async function close() {
|
|
108
|
-
await silgiCLIIClose();
|
|
109
|
-
}
|
|
110
|
-
return {
|
|
111
|
-
watcher,
|
|
112
|
-
close
|
|
113
|
-
};
|
|
114
|
-
}
|
|
115
|
-
|
|
116
|
-
export { prepareBuild, watchDev };
|
package/dist/cli/build.mjs
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
|
-
import
|
|
1
|
+
import { consola } from 'consola';
|
|
2
2
|
import { createHooks, createDebugger } from 'hookable';
|
|
3
|
-
import { resolve, join, relative,
|
|
3
|
+
import { resolve, join, relative, extname, basename, dirname, isAbsolute } from 'pathe';
|
|
4
4
|
import { useSilgiCLI, replaceRuntimeValues, silgiCLICtx, autoImportTypes } from 'silgi';
|
|
5
|
-
import { isPresents, addTemplate, addCoreFile, relativeWithDot, hash, resolveAlias, directoryToURL,
|
|
5
|
+
import { isPresents, addTemplate, addCoreFile, relativeWithDot, hash, resolveAlias, directoryToURL, removeExtension, addImports, baseHeaderBannerComment, writeFile, parseServices, normalizeTemplate, useLogger, resolveSilgiPath, hasSilgiModule, genEnsureSafeVar, toArray, isDirectory } from 'silgi/kit';
|
|
6
6
|
import { runtimeDir } from 'silgi/runtime/meta';
|
|
7
7
|
import { scanExports, createUnimport, toExports } from 'unimport';
|
|
8
8
|
import { c as createRouteRules } from '../_chunks/routeRules.mjs';
|
|
9
9
|
import * as p from '@clack/prompts';
|
|
10
|
-
import { existsSync, promises, readFileSync,
|
|
10
|
+
import { existsSync, promises, readFileSync, mkdirSync, writeFileSync } from 'node:fs';
|
|
11
11
|
import * as dotenv from 'dotenv';
|
|
12
12
|
import { findTypeExports, findExports, resolvePath, parseNodeModulePath, lookupNodeModuleSubpath } from 'mlly';
|
|
13
13
|
import { createJiti } from 'dev-jiti';
|
|
@@ -16,10 +16,9 @@ import { fileURLToPath } from 'node:url';
|
|
|
16
16
|
import { defu } from 'defu';
|
|
17
17
|
import { resolveModuleURL } from 'exsolve';
|
|
18
18
|
import { isRelative, withTrailingSlash } from 'ufo';
|
|
19
|
-
import {
|
|
19
|
+
import { readFile, readdir } from 'node:fs/promises';
|
|
20
20
|
import { globby } from 'globby';
|
|
21
21
|
import ignore from 'ignore';
|
|
22
|
-
import { parseSync } from '@oxc-parser/wasm';
|
|
23
22
|
import { genImport, genTypeImport, genObjectFromRawEntries, genObjectFromRaw, genObjectFromValues, genAugmentation } from 'knitwork';
|
|
24
23
|
import { klona } from 'klona';
|
|
25
24
|
import { useSilgiRuntimeConfig, initRuntimeConfig } from 'silgi/runtime';
|
|
@@ -757,312 +756,193 @@ function resolveGroupSyntax(group) {
|
|
|
757
756
|
return groups;
|
|
758
757
|
}
|
|
759
758
|
|
|
760
|
-
const
|
|
761
|
-
|
|
762
|
-
|
|
763
|
-
|
|
764
|
-
|
|
765
|
-
|
|
766
|
-
|
|
767
|
-
|
|
768
|
-
|
|
769
|
-
|
|
759
|
+
const TYPE_DECLARATION_EXPORT_REGEX = /\bexport\s+(?<declaration>(interface|type|declare (async function|function|let|const enum|const|enum|var|class)))\s+(?<name>[\w$]+)(?:\s+extends\s+(?<extends>[\w$, \t\n\r]+))?/g;
|
|
760
|
+
const FUNCTION_VARIABLE_EXPORT_REGEX = /\bexport\s+(?:const|let|var)\s+(?<name>[\w$]+)\s*=\s*(?<funcName>\w+)\s*\(/g;
|
|
761
|
+
function extractExportMatches(regex, fileContent, additionalMetadata = {}) {
|
|
762
|
+
const matchedExports = [];
|
|
763
|
+
for (const match of fileContent.matchAll(regex)) {
|
|
764
|
+
const name = match.groups?.name || "";
|
|
765
|
+
const declaration = match.groups?.declaration || "";
|
|
766
|
+
const funcName = match.groups?.funcName || "";
|
|
767
|
+
const extendsClause = match.groups?.extends || "";
|
|
768
|
+
const codeSnippet = funcName ? `export const ${name} = ${funcName}(` : `export ${declaration} ${name}`;
|
|
769
|
+
const extendedTypes = extendsClause ? extendsClause.split(",").map((typeName) => typeName.trim()) : [];
|
|
770
|
+
matchedExports.push({
|
|
771
|
+
...additionalMetadata,
|
|
772
|
+
name,
|
|
773
|
+
declaration,
|
|
774
|
+
funcName,
|
|
775
|
+
code: codeSnippet,
|
|
776
|
+
start: match.index,
|
|
777
|
+
end: (match.index || 0) + match[0].length,
|
|
778
|
+
extends: extendedTypes
|
|
779
|
+
});
|
|
780
|
+
}
|
|
781
|
+
return matchedExports;
|
|
782
|
+
}
|
|
783
|
+
function generateUniqueIdentifier(filePath, exportName) {
|
|
784
|
+
const fileBaseName = basename(filePath);
|
|
785
|
+
const uniqueString = `${fileBaseName}${exportName}`;
|
|
786
|
+
return hash(uniqueString);
|
|
787
|
+
}
|
|
788
|
+
function categorizeExports(exportedEntities, filePath) {
|
|
789
|
+
const runtimeExports = [];
|
|
790
|
+
const typeExports = [];
|
|
791
|
+
const functionExportCategories = {
|
|
792
|
+
createService: "service",
|
|
793
|
+
createSchema: "schema",
|
|
794
|
+
createShared: "shared"
|
|
770
795
|
};
|
|
771
|
-
|
|
772
|
-
|
|
773
|
-
|
|
774
|
-
|
|
775
|
-
|
|
776
|
-
|
|
777
|
-
|
|
778
|
-
|
|
796
|
+
for (const [functionName, category] of Object.entries(functionExportCategories)) {
|
|
797
|
+
const matchingExports = exportedEntities.filter((entity) => entity.funcName === functionName);
|
|
798
|
+
for (const exportEntity of matchingExports) {
|
|
799
|
+
if (!exportEntity.name)
|
|
800
|
+
continue;
|
|
801
|
+
runtimeExports.push({
|
|
802
|
+
exportName: exportEntity.name,
|
|
803
|
+
path: filePath,
|
|
804
|
+
uniqueId: generateUniqueIdentifier(filePath, exportEntity.name),
|
|
805
|
+
category
|
|
806
|
+
});
|
|
807
|
+
}
|
|
779
808
|
}
|
|
780
|
-
|
|
781
|
-
|
|
782
|
-
|
|
783
|
-
|
|
784
|
-
|
|
785
|
-
|
|
786
|
-
|
|
787
|
-
|
|
788
|
-
|
|
809
|
+
const interfaceExportCategories = {
|
|
810
|
+
ExtendShared: "shared",
|
|
811
|
+
ExtendContext: "context"
|
|
812
|
+
};
|
|
813
|
+
for (const [extensionName, category] of Object.entries(interfaceExportCategories)) {
|
|
814
|
+
const matchingExports = exportedEntities.filter(
|
|
815
|
+
(entity) => entity.declaration === "interface" && entity.extends?.includes(extensionName)
|
|
816
|
+
);
|
|
817
|
+
for (const exportEntity of matchingExports) {
|
|
818
|
+
if (!exportEntity.name)
|
|
819
|
+
continue;
|
|
820
|
+
typeExports.push({
|
|
821
|
+
exportName: exportEntity.name,
|
|
822
|
+
path: filePath,
|
|
823
|
+
uniqueId: generateUniqueIdentifier(filePath, exportEntity.name),
|
|
824
|
+
category
|
|
825
|
+
});
|
|
826
|
+
}
|
|
789
827
|
}
|
|
790
|
-
|
|
791
|
-
|
|
792
|
-
|
|
793
|
-
|
|
794
|
-
|
|
795
|
-
|
|
796
|
-
|
|
797
|
-
|
|
828
|
+
return { runtimeExports, typeExports };
|
|
829
|
+
}
|
|
830
|
+
function registerExportsWithHooks(silgiInstance, runtimeExports, typeExports) {
|
|
831
|
+
silgiInstance.hook("before:scan.ts", (options) => {
|
|
832
|
+
for (const { exportName, path, uniqueId, category } of runtimeExports) {
|
|
833
|
+
if (!path.includes("vfs")) {
|
|
834
|
+
silgiInstance.options.devServer.watch.push(path);
|
|
835
|
+
}
|
|
836
|
+
switch (category) {
|
|
837
|
+
case "service":
|
|
838
|
+
options.services.push(uniqueId);
|
|
839
|
+
break;
|
|
840
|
+
case "shared":
|
|
841
|
+
options.shareds.push(uniqueId);
|
|
842
|
+
break;
|
|
843
|
+
case "schema":
|
|
844
|
+
options.schemas.push(uniqueId);
|
|
845
|
+
break;
|
|
846
|
+
}
|
|
847
|
+
options.addImportItem({
|
|
848
|
+
specifier: removeExtension(relativeWithDot(silgiInstance.options.silgi.serverDir, path)),
|
|
849
|
+
imports: [{ name: exportName, as: uniqueId }]
|
|
798
850
|
});
|
|
799
|
-
consola.warn("This file has a problem:", path);
|
|
800
851
|
}
|
|
801
|
-
|
|
802
|
-
|
|
803
|
-
|
|
804
|
-
|
|
805
|
-
|
|
806
|
-
|
|
807
|
-
if (
|
|
808
|
-
|
|
809
|
-
|
|
810
|
-
|
|
811
|
-
|
|
852
|
+
});
|
|
853
|
+
silgiInstance.hook("before:schema.ts", (options) => {
|
|
854
|
+
for (const { exportName, path, uniqueId, category } of typeExports) {
|
|
855
|
+
if (!path.includes("vfs")) {
|
|
856
|
+
silgiInstance.options.devServer.watch.push(path);
|
|
857
|
+
}
|
|
858
|
+
if (category === "shared" || category === "context") {
|
|
859
|
+
const targetCollection = category === "shared" ? options.shareds : options.contexts;
|
|
860
|
+
targetCollection.push({ key: uniqueId, value: uniqueId });
|
|
861
|
+
}
|
|
862
|
+
options.addImportItem({
|
|
863
|
+
imports: [{ name: exportName, as: uniqueId }],
|
|
864
|
+
specifier: removeExtension(relativeWithDot(silgiInstance.options.build.typesDir, path))
|
|
812
865
|
});
|
|
813
|
-
consola.warn("This file has a problem:", path);
|
|
814
866
|
}
|
|
815
|
-
|
|
816
|
-
|
|
817
|
-
|
|
818
|
-
|
|
819
|
-
|
|
820
|
-
|
|
821
|
-
|
|
822
|
-
|
|
823
|
-
|
|
824
|
-
|
|
825
|
-
|
|
826
|
-
|
|
827
|
-
|
|
828
|
-
|
|
829
|
-
|
|
830
|
-
|
|
831
|
-
|
|
832
|
-
|
|
833
|
-
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
if (property.key.name === "options") {
|
|
837
|
-
for (const key2 in property.value.properties) {
|
|
838
|
-
const option = property.value.properties[key2];
|
|
839
|
-
if (option.type === "ObjectProperty") {
|
|
840
|
-
options[option.key.name] = option.value.value;
|
|
841
|
-
}
|
|
842
|
-
}
|
|
843
|
-
}
|
|
844
|
-
}
|
|
845
|
-
}
|
|
846
|
-
options.type = false;
|
|
847
|
-
data.push({
|
|
848
|
-
exportName: declaration.id.name,
|
|
849
|
-
options,
|
|
850
|
-
// object: declaration.init,
|
|
851
|
-
path
|
|
852
|
-
});
|
|
853
|
-
}
|
|
867
|
+
});
|
|
868
|
+
}
|
|
869
|
+
async function verifyDirectoryCaseSensitivity(directoryPath, rootDirectory) {
|
|
870
|
+
const directoryName = basename(directoryPath);
|
|
871
|
+
const parentDirectory = dirname(directoryPath);
|
|
872
|
+
try {
|
|
873
|
+
const siblingEntries = await readdir(parentDirectory);
|
|
874
|
+
if (!siblingEntries.includes(directoryName)) {
|
|
875
|
+
const directoryNameLowerCase = directoryName.toLowerCase();
|
|
876
|
+
const caseInsensitiveMatch = siblingEntries.find(
|
|
877
|
+
(sibling) => sibling.toLowerCase() === directoryNameLowerCase
|
|
878
|
+
);
|
|
879
|
+
if (caseInsensitiveMatch) {
|
|
880
|
+
const originalRelative = relative(rootDirectory, directoryPath);
|
|
881
|
+
const correctedRelative = relative(
|
|
882
|
+
rootDirectory,
|
|
883
|
+
join(parentDirectory, caseInsensitiveMatch)
|
|
884
|
+
);
|
|
885
|
+
consola.warn(
|
|
886
|
+
`Components not scanned from \`~/${correctedRelative}\`. Did you mean to name the directory \`~/${originalRelative}\` instead?`
|
|
887
|
+
);
|
|
854
888
|
}
|
|
855
889
|
}
|
|
856
|
-
|
|
890
|
+
} catch {
|
|
857
891
|
}
|
|
858
|
-
parseInterfaceDeclarations(ast, find = "", path = "") {
|
|
859
|
-
const data = [];
|
|
860
|
-
for (const item of this.parseTSInterfaceDeclaration(ast, path)) {
|
|
861
|
-
if (!item?.declaration?.extends)
|
|
862
|
-
continue;
|
|
863
|
-
for (const declaration of item?.declaration?.extends) {
|
|
864
|
-
if (declaration.expression.name === find) {
|
|
865
|
-
const options = {};
|
|
866
|
-
options.type = true;
|
|
867
|
-
data.push({
|
|
868
|
-
exportName: item.declaration.id.name,
|
|
869
|
-
options,
|
|
870
|
-
// object: declaration.init,
|
|
871
|
-
path
|
|
872
|
-
});
|
|
873
|
-
}
|
|
874
|
-
}
|
|
875
|
-
}
|
|
876
|
-
return data;
|
|
877
|
-
}
|
|
878
|
-
// private parsePlugin(ast: any, path: string = '') {
|
|
879
|
-
// const data = {
|
|
880
|
-
// export: [],
|
|
881
|
-
// name: '',
|
|
882
|
-
// path: '',
|
|
883
|
-
// } as DataTypePlugin
|
|
884
|
-
// for (const item of this.parseVariableDeclaration(ast)) {
|
|
885
|
-
// for (const declaration of item.declaration.declarations) {
|
|
886
|
-
// if (declaration.init.callee?.name === 'defineSilgiModule') {
|
|
887
|
-
// if (declaration.init.arguments) {
|
|
888
|
-
// for (const argument of declaration.init.arguments) {
|
|
889
|
-
// for (const propertie of argument.properties) {
|
|
890
|
-
// if (propertie.key.name === 'name')
|
|
891
|
-
// data.name = propertie.value.value
|
|
892
|
-
// }
|
|
893
|
-
// }
|
|
894
|
-
// }
|
|
895
|
-
// data.export.push({
|
|
896
|
-
// name: data.name,
|
|
897
|
-
// as: camelCase(`${data.name}DefineSilgiModule`),
|
|
898
|
-
// type: false,
|
|
899
|
-
// })
|
|
900
|
-
// }
|
|
901
|
-
// }
|
|
902
|
-
// }
|
|
903
|
-
// for (const item of this.parseTSInterfaceDeclaration(ast)) {
|
|
904
|
-
// if (!item?.declaration?.extends)
|
|
905
|
-
// continue
|
|
906
|
-
// for (const declaration of item?.declaration?.extends) {
|
|
907
|
-
// if (declaration.expression.name === 'ModuleOptions') {
|
|
908
|
-
// data.export.push({
|
|
909
|
-
// name: item.declaration.id.name,
|
|
910
|
-
// as: camelCase(`${data.name}ModuleOptions`),
|
|
911
|
-
// type: true,
|
|
912
|
-
// })
|
|
913
|
-
// }
|
|
914
|
-
// // TODO add other plugins
|
|
915
|
-
// }
|
|
916
|
-
// }
|
|
917
|
-
// data.path = path
|
|
918
|
-
// return data
|
|
919
|
-
// }
|
|
920
892
|
}
|
|
921
|
-
|
|
922
|
-
|
|
923
|
-
const
|
|
924
|
-
const
|
|
925
|
-
|
|
926
|
-
|
|
927
|
-
|
|
928
|
-
const siblings = await readdir(dirname(dir)).catch(() => []);
|
|
929
|
-
const directory = basename(dir);
|
|
930
|
-
if (!siblings.includes(directory)) {
|
|
931
|
-
const directoryLowerCase = directory.toLowerCase();
|
|
932
|
-
const caseCorrected = siblings.find((sibling) => sibling.toLowerCase() === directoryLowerCase);
|
|
933
|
-
if (caseCorrected) {
|
|
934
|
-
const original = relative(silgi.options.serverDir, dir);
|
|
935
|
-
const corrected = relative(silgi.options.serverDir, join(dirname(dir), caseCorrected));
|
|
936
|
-
consola$1.warn(`Components not scanned from \`~/${corrected}\`. Did you mean to name the directory \`~/${original}\` instead?`);
|
|
937
|
-
}
|
|
938
|
-
}
|
|
893
|
+
async function scanExportFile(silgiInstance) {
|
|
894
|
+
const processedFilePaths = /* @__PURE__ */ new Set();
|
|
895
|
+
const alreadyScannedPaths = [];
|
|
896
|
+
const serverDirectory = silgiInstance.options.serverDir;
|
|
897
|
+
if (!serverDirectory) {
|
|
898
|
+
consola.warn("No server directory specified for scanning");
|
|
899
|
+
return;
|
|
939
900
|
}
|
|
940
|
-
|
|
941
|
-
const
|
|
942
|
-
|
|
943
|
-
|
|
944
|
-
}
|
|
945
|
-
if (
|
|
946
|
-
|
|
901
|
+
try {
|
|
902
|
+
const matchedFiles = await globby(serverDirectory, {
|
|
903
|
+
cwd: silgiInstance.options.rootDir,
|
|
904
|
+
ignore: silgiInstance.options.ignore
|
|
905
|
+
});
|
|
906
|
+
if (matchedFiles.length) {
|
|
907
|
+
await verifyDirectoryCaseSensitivity(
|
|
908
|
+
serverDirectory,
|
|
909
|
+
silgiInstance.options.rootDir
|
|
910
|
+
);
|
|
947
911
|
}
|
|
948
|
-
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
|
|
952
|
-
});
|
|
953
|
-
const readfile = await readFile(filePath, "utf-8");
|
|
954
|
-
const { exportVariables, parseInterfaceDeclarations } = parser.parseExports(readfile, filePath);
|
|
955
|
-
const createServices = exportVariables("createService", filePath);
|
|
956
|
-
if (hasError("Parser", silgi)) {
|
|
957
|
-
return;
|
|
958
|
-
}
|
|
959
|
-
const scanTS = [];
|
|
960
|
-
const schemaTS = [];
|
|
961
|
-
if (createServices.length > 0) {
|
|
962
|
-
scanTS.push(...createServices.map(({ exportName, path }) => {
|
|
963
|
-
const randomString = hash(basename(path) + exportName);
|
|
964
|
-
const _name = `_v${randomString}`;
|
|
965
|
-
return { exportName, path, _name, type: "service" };
|
|
966
|
-
}));
|
|
967
|
-
}
|
|
968
|
-
const createSchemas = exportVariables("createSchema", filePath);
|
|
969
|
-
if (hasError("Parser", silgi)) {
|
|
970
|
-
return;
|
|
971
|
-
}
|
|
972
|
-
if (createSchemas.length > 0) {
|
|
973
|
-
scanTS.push(...createSchemas.map(({ exportName, path }) => {
|
|
974
|
-
const randomString = hash(basename(path) + exportName);
|
|
975
|
-
const _name = `_v${randomString}`;
|
|
976
|
-
return { exportName, path, _name, type: "schema" };
|
|
977
|
-
}));
|
|
978
|
-
}
|
|
979
|
-
const createShareds = exportVariables("createShared", filePath);
|
|
980
|
-
if (hasError("Parser", silgi)) {
|
|
981
|
-
return;
|
|
982
|
-
}
|
|
983
|
-
if (createShareds.length > 0) {
|
|
984
|
-
scanTS.push(...createShareds.map(({ exportName, path }) => {
|
|
985
|
-
const randomString = hash(basename(path) + exportName);
|
|
986
|
-
const _name = `_v${randomString}`;
|
|
987
|
-
return { exportName, path, _name, type: "shared" };
|
|
988
|
-
}));
|
|
989
|
-
}
|
|
990
|
-
const sharedsTypes = parseInterfaceDeclarations("ExtendShared", filePath);
|
|
991
|
-
if (hasError("Parser", silgi)) {
|
|
992
|
-
return;
|
|
912
|
+
for (const relativeFilePath of matchedFiles.sort()) {
|
|
913
|
+
const absoluteFilePath = resolve(silgiInstance.options.rootDir, relativeFilePath);
|
|
914
|
+
if (alreadyScannedPaths.find((path) => absoluteFilePath.startsWith(withTrailingSlash(path))) || isIgnored(absoluteFilePath, silgiInstance) || processedFilePaths.has(absoluteFilePath)) {
|
|
915
|
+
continue;
|
|
993
916
|
}
|
|
994
|
-
|
|
995
|
-
|
|
996
|
-
|
|
997
|
-
|
|
998
|
-
return { exportName, path, _name, type: "shared" };
|
|
999
|
-
}));
|
|
917
|
+
processedFilePaths.add(absoluteFilePath);
|
|
918
|
+
const fileExtension = extname(absoluteFilePath);
|
|
919
|
+
if (!silgiInstance.options.extensions?.includes(fileExtension)) {
|
|
920
|
+
continue;
|
|
1000
921
|
}
|
|
1001
|
-
|
|
1002
|
-
|
|
1003
|
-
|
|
922
|
+
try {
|
|
923
|
+
const fileContent = await readFile(absoluteFilePath, "utf-8");
|
|
924
|
+
const typeDeclarationExports = extractExportMatches(
|
|
925
|
+
TYPE_DECLARATION_EXPORT_REGEX,
|
|
926
|
+
fileContent,
|
|
927
|
+
{ type: "declaration" }
|
|
928
|
+
);
|
|
929
|
+
const functionVariableExports = extractExportMatches(
|
|
930
|
+
FUNCTION_VARIABLE_EXPORT_REGEX,
|
|
931
|
+
fileContent,
|
|
932
|
+
{ type: "variable" }
|
|
933
|
+
);
|
|
934
|
+
const allExportedEntities = [...typeDeclarationExports, ...functionVariableExports];
|
|
935
|
+
const { runtimeExports, typeExports } = categorizeExports(
|
|
936
|
+
allExportedEntities,
|
|
937
|
+
absoluteFilePath
|
|
938
|
+
);
|
|
939
|
+
registerExportsWithHooks(silgiInstance, runtimeExports, typeExports);
|
|
940
|
+
} catch (error) {
|
|
941
|
+
consola.error(`Error processing file ${absoluteFilePath}:`, error);
|
|
1004
942
|
}
|
|
1005
|
-
if (contextTypes.length > 0) {
|
|
1006
|
-
schemaTS.push(...contextTypes.map(({ exportName, path }) => {
|
|
1007
|
-
const randomString = hash(basename(path) + exportName);
|
|
1008
|
-
const _name = `_v${randomString}`;
|
|
1009
|
-
return { exportName, path, _name, type: "context" };
|
|
1010
|
-
}));
|
|
1011
|
-
}
|
|
1012
|
-
silgi.hook("before:scan.ts", (options) => {
|
|
1013
|
-
for (const { exportName, path, _name, type } of scanTS) {
|
|
1014
|
-
if (!path.includes("vfs")) {
|
|
1015
|
-
silgi.options.devServer.watch.push(path);
|
|
1016
|
-
}
|
|
1017
|
-
if (type === "service") {
|
|
1018
|
-
options.services.push(_name);
|
|
1019
|
-
}
|
|
1020
|
-
if (type === "shared") {
|
|
1021
|
-
options.shareds.push(_name);
|
|
1022
|
-
}
|
|
1023
|
-
if (type === "schema") {
|
|
1024
|
-
options.schemas.push(_name);
|
|
1025
|
-
}
|
|
1026
|
-
options.addImportItem({
|
|
1027
|
-
specifier: removeExtension(relativeWithDot(silgi.options.silgi.serverDir, path)),
|
|
1028
|
-
imports: [
|
|
1029
|
-
{
|
|
1030
|
-
name: exportName,
|
|
1031
|
-
as: _name
|
|
1032
|
-
}
|
|
1033
|
-
]
|
|
1034
|
-
});
|
|
1035
|
-
}
|
|
1036
|
-
});
|
|
1037
|
-
silgi.hook("before:schema.ts", (options) => {
|
|
1038
|
-
for (const { exportName, path, _name, type } of schemaTS) {
|
|
1039
|
-
if (!path.includes("vfs")) {
|
|
1040
|
-
silgi.options.devServer.watch.push(path);
|
|
1041
|
-
}
|
|
1042
|
-
if (type === "shared") {
|
|
1043
|
-
options.shareds.push({
|
|
1044
|
-
key: _name,
|
|
1045
|
-
value: _name
|
|
1046
|
-
});
|
|
1047
|
-
}
|
|
1048
|
-
if (type === "context") {
|
|
1049
|
-
options.contexts.push({
|
|
1050
|
-
key: _name,
|
|
1051
|
-
value: _name
|
|
1052
|
-
});
|
|
1053
|
-
}
|
|
1054
|
-
options.addImportItem({
|
|
1055
|
-
imports: [
|
|
1056
|
-
{
|
|
1057
|
-
name: exportName,
|
|
1058
|
-
as: _name
|
|
1059
|
-
}
|
|
1060
|
-
],
|
|
1061
|
-
specifier: removeExtension(relativeWithDot(silgi.options.build.typesDir, path))
|
|
1062
|
-
});
|
|
1063
|
-
}
|
|
1064
|
-
});
|
|
1065
943
|
}
|
|
944
|
+
} catch (error) {
|
|
945
|
+
consola.error("Error scanning export files:", error);
|
|
1066
946
|
}
|
|
1067
947
|
}
|
|
1068
948
|
|
|
@@ -1153,7 +1033,7 @@ ${injectedResult.code}`;
|
|
|
1153
1033
|
if (silgi.options.debug) {
|
|
1154
1034
|
console.error("Failed to read scan.ts file:", error);
|
|
1155
1035
|
} else {
|
|
1156
|
-
consola
|
|
1036
|
+
consola.withTag("silgi").error(error);
|
|
1157
1037
|
}
|
|
1158
1038
|
return {
|
|
1159
1039
|
context,
|
|
@@ -1572,7 +1452,7 @@ async function createSilgiCLI(config = {}, opts = {}) {
|
|
|
1572
1452
|
hooks,
|
|
1573
1453
|
errors: [],
|
|
1574
1454
|
_requiredModules: {},
|
|
1575
|
-
logger: opts.consola || consola
|
|
1455
|
+
logger: opts.consola || consola.withTag("silgi"),
|
|
1576
1456
|
close: () => silgi.hooks.callHook("close", silgi),
|
|
1577
1457
|
storage: void 0,
|
|
1578
1458
|
scanModules: [],
|
|
@@ -1680,7 +1560,7 @@ async function generateApiFul(silgi) {
|
|
|
1680
1560
|
Object.entries(config?.services ?? {}).filter(([, service]) => Boolean(service.schema))
|
|
1681
1561
|
);
|
|
1682
1562
|
if (Object.keys(resolvedOpenAPIServices).length === 0) {
|
|
1683
|
-
consola
|
|
1563
|
+
consola.info("No OpenAPI schemas found, skipping generation");
|
|
1684
1564
|
return;
|
|
1685
1565
|
}
|
|
1686
1566
|
for (const service of Object.values(resolvedOpenAPIServices)) {
|
package/dist/cli/dev.mjs
ADDED
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
import { watch } from 'chokidar';
|
|
2
|
+
import consola from 'consola';
|
|
3
|
+
import { join, basename } from 'pathe';
|
|
4
|
+
import { debounce } from 'perfect-debounce';
|
|
5
|
+
import { u as useSilgiCLI$1, a as silgiCLIIClose } from '../_chunks/silgiApp.mjs';
|
|
6
|
+
import { useSilgiCLI } from 'silgi';
|
|
7
|
+
import { c as createSilgiCLI, b as build } from './build.mjs';
|
|
8
|
+
|
|
9
|
+
async function reloadScan(path, _stats) {
|
|
10
|
+
const silgi = useSilgiCLI();
|
|
11
|
+
await silgi.callHook("reload:scan", path, _stats);
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
async function prepareBuild(config) {
|
|
15
|
+
const silgi = await createSilgiCLI({
|
|
16
|
+
commandType: config?.commandType || "prepare",
|
|
17
|
+
...config
|
|
18
|
+
});
|
|
19
|
+
await build(silgi);
|
|
20
|
+
return silgi;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
async function watchDev() {
|
|
24
|
+
let watcher;
|
|
25
|
+
async function load() {
|
|
26
|
+
await prepareBuild({
|
|
27
|
+
commandType: "prepare",
|
|
28
|
+
activeEnvironment: ".env"
|
|
29
|
+
});
|
|
30
|
+
}
|
|
31
|
+
const reload = debounce(load);
|
|
32
|
+
const silgi = useSilgiCLI$1();
|
|
33
|
+
silgi.options.watchOptions.ignored ??= [];
|
|
34
|
+
silgi.options.watchOptions.ignoreInitial = true;
|
|
35
|
+
if (Array.isArray(silgi.options.watchOptions.ignored)) {
|
|
36
|
+
silgi.options.watchOptions.ignored.push(
|
|
37
|
+
`!${join(silgi.options.silgi.serverDir, "config")}`
|
|
38
|
+
);
|
|
39
|
+
}
|
|
40
|
+
silgi.options.devServer.watch.push(
|
|
41
|
+
join(silgi.options.serverDir, "services"),
|
|
42
|
+
join(silgi.options.serverDir, "schemas"),
|
|
43
|
+
join(silgi.options.serverDir, "shared"),
|
|
44
|
+
join(silgi.options.serverDir, "utils"),
|
|
45
|
+
join(silgi.options.serverDir, "types"),
|
|
46
|
+
join(silgi.options.silgi.serverDir, "config"),
|
|
47
|
+
join(silgi.options.silgi.serverDir, "modules"),
|
|
48
|
+
join(silgi.options.rootDir, "silgi.config.ts")
|
|
49
|
+
);
|
|
50
|
+
const watchReloadEvents = /* @__PURE__ */ new Set(["add", "addDir", "unlink", "unlinkDir", "change"]);
|
|
51
|
+
if (silgi.options.devServer.watch.length > 0) {
|
|
52
|
+
silgi.options.devServer.watch = [...new Set(silgi.options.devServer.watch)];
|
|
53
|
+
watcher = watch(silgi.options.devServer.watch, silgi.options.watchOptions);
|
|
54
|
+
watcher.on("all", async (event, path, stats) => {
|
|
55
|
+
if (!watchReloadEvents.has(event)) {
|
|
56
|
+
return;
|
|
57
|
+
}
|
|
58
|
+
const startTime = performance.now();
|
|
59
|
+
silgi.errors = [];
|
|
60
|
+
try {
|
|
61
|
+
await reloadScan(path, stats);
|
|
62
|
+
await reload();
|
|
63
|
+
} catch (error) {
|
|
64
|
+
consola.withTag("silgi").error(error);
|
|
65
|
+
}
|
|
66
|
+
silgi.errors = [];
|
|
67
|
+
const endTime = performance.now();
|
|
68
|
+
const elapsedTime = Math.round(endTime - startTime);
|
|
69
|
+
silgi.logger.success(`${basename(path)} - ${elapsedTime}ms`);
|
|
70
|
+
}).on("error", (error) => {
|
|
71
|
+
consola.withTag("silgi").error(error);
|
|
72
|
+
});
|
|
73
|
+
}
|
|
74
|
+
async function close() {
|
|
75
|
+
await silgiCLIIClose();
|
|
76
|
+
}
|
|
77
|
+
return {
|
|
78
|
+
watcher,
|
|
79
|
+
close
|
|
80
|
+
};
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
export { prepareBuild as p, watchDev as w };
|
package/dist/cli/index.mjs
CHANGED
package/dist/cli/init.mjs
CHANGED
package/dist/cli/install.mjs
CHANGED
package/dist/cli/watch.mjs
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
|
-
import { basename } from 'node:path';
|
|
2
|
-
import { watch } from 'chokidar';
|
|
3
1
|
import { defineCommand, runCommand } from 'citty';
|
|
4
2
|
import consola from 'consola';
|
|
5
|
-
import { join } from 'pathe';
|
|
6
|
-
import { useSilgiCLI } from 'silgi';
|
|
7
3
|
import { version } from 'silgi/meta';
|
|
8
|
-
import {
|
|
9
|
-
import { r as reloadScan } from './devServer.mjs';
|
|
4
|
+
import { w as watchDev } from './dev.mjs';
|
|
10
5
|
import { b as commonArgs, a as command$1 } from './prepare.mjs';
|
|
6
|
+
import 'chokidar';
|
|
7
|
+
import 'pathe';
|
|
8
|
+
import 'perfect-debounce';
|
|
9
|
+
import '../_chunks/silgiApp.mjs';
|
|
11
10
|
import 'unctx';
|
|
11
|
+
import 'silgi';
|
|
12
12
|
import './build.mjs';
|
|
13
13
|
import 'hookable';
|
|
14
14
|
import 'silgi/kit';
|
|
@@ -29,7 +29,6 @@ import 'exsolve';
|
|
|
29
29
|
import 'node:fs/promises';
|
|
30
30
|
import 'globby';
|
|
31
31
|
import 'ignore';
|
|
32
|
-
import '@oxc-parser/wasm';
|
|
33
32
|
import 'knitwork';
|
|
34
33
|
import 'klona';
|
|
35
34
|
import 'silgi/runtime';
|
|
@@ -69,56 +68,13 @@ const command = defineCommand({
|
|
|
69
68
|
await runCommand(command$1, {
|
|
70
69
|
rawArgs: ["--commandType", "dev", "--dev", "true"]
|
|
71
70
|
});
|
|
72
|
-
const
|
|
73
|
-
silgi.options.watchOptions.ignored ??= [];
|
|
74
|
-
silgi.options.watchOptions.ignoreInitial = true;
|
|
75
|
-
if (Array.isArray(silgi.options.watchOptions.ignored)) {
|
|
76
|
-
silgi.options.watchOptions.ignored.push(
|
|
77
|
-
`!${join(silgi.options.silgi.serverDir, "config")}`
|
|
78
|
-
);
|
|
79
|
-
}
|
|
80
|
-
silgi.options.devServer.watch.push(
|
|
81
|
-
join(silgi.options.serverDir, "services"),
|
|
82
|
-
join(silgi.options.serverDir, "schemas"),
|
|
83
|
-
join(silgi.options.serverDir, "shared"),
|
|
84
|
-
join(silgi.options.serverDir, "utils"),
|
|
85
|
-
join(silgi.options.serverDir, "types"),
|
|
86
|
-
join(silgi.options.silgi.serverDir, "config"),
|
|
87
|
-
join(silgi.options.rootDir, "silgi.config.ts")
|
|
88
|
-
);
|
|
89
|
-
const watchReloadEvents = /* @__PURE__ */ new Set(["add", "addDir", "unlink", "unlinkDir", "change"]);
|
|
90
|
-
let watcher;
|
|
91
|
-
if (silgi.options.devServer.watch.length > 0) {
|
|
92
|
-
silgi.options.devServer.watch = [...new Set(silgi.options.devServer.watch)];
|
|
93
|
-
watcher = watch(silgi.options.devServer.watch, silgi.options.watchOptions);
|
|
94
|
-
watcher.on("all", async (event, path, stats) => {
|
|
95
|
-
if (!watchReloadEvents.has(event)) {
|
|
96
|
-
return;
|
|
97
|
-
}
|
|
98
|
-
const startTime = performance.now();
|
|
99
|
-
silgi.errors = [];
|
|
100
|
-
try {
|
|
101
|
-
await reloadScan(path, stats);
|
|
102
|
-
await runCommand(command$1, {
|
|
103
|
-
rawArgs: ["--commands", "run", "--dev", "true"]
|
|
104
|
-
});
|
|
105
|
-
} catch (error) {
|
|
106
|
-
consola.withTag("silgi").error(error);
|
|
107
|
-
}
|
|
108
|
-
silgi.errors = [];
|
|
109
|
-
const endTime = performance.now();
|
|
110
|
-
const elapsedTime = Math.round(endTime - startTime);
|
|
111
|
-
silgi.logger.success(`${basename(path)} - ${elapsedTime}ms`);
|
|
112
|
-
}).on("error", (error) => {
|
|
113
|
-
consola.withTag("silgi").error(error);
|
|
114
|
-
});
|
|
115
|
-
}
|
|
71
|
+
const watch = await watchDev();
|
|
116
72
|
process.on("SIGINT", async () => {
|
|
117
73
|
consola.withTag("silgi").info("Shutting down...");
|
|
118
|
-
if (
|
|
119
|
-
|
|
74
|
+
if (watch) {
|
|
75
|
+
watch.close();
|
|
120
76
|
}
|
|
121
|
-
await
|
|
77
|
+
await watch.close();
|
|
122
78
|
process.exit(0);
|
|
123
79
|
});
|
|
124
80
|
consola.withTag("silgi").success("Prepare completed");
|
package/dist/types/index.d.mts
CHANGED
|
@@ -10,8 +10,10 @@ import { PresetName, PresetOptions, PresetNameInput } from 'silgi/presets';
|
|
|
10
10
|
import { ResolvedServiceType as ResolvedServiceType$1, SilgiRuntimeShareds as SilgiRuntimeShareds$1, SilgiRuntimeOptions as SilgiRuntimeOptions$1, RouteRules as RouteRules$1, ModuleMeta as ModuleMeta$1, SilgiModule as SilgiModule$1, BuildSilgi as BuildSilgi$1, Commands as Commands$1, SilgiRouteRules as SilgiRouteRules$1, DotenvOptions as DotenvOptions$1, EnvOptions as EnvOptions$1, SilgiRuntimeConfig as SilgiRuntimeConfig$1, ServiceParseModule as ServiceParseModule$1, SilgiCLIHooks as SilgiCLIHooks$1, StorageMounts as StorageMounts$1, SilgiTemplate as SilgiTemplate$1, SilgiFrameworkInfo as SilgiFrameworkInfo$1 } from 'silgi/types';
|
|
11
11
|
import { Adapter, TablesSchema, InferModelTypes } from 'unadapter/types';
|
|
12
12
|
import { UnimportPluginOptions } from 'unimport/unplugin';
|
|
13
|
-
import
|
|
14
|
-
import {
|
|
13
|
+
import * as h3 from 'h3';
|
|
14
|
+
import { H3Event } from 'h3';
|
|
15
|
+
import * as nitropack_types from 'nitropack/types';
|
|
16
|
+
import { NitroRuntimeConfig } from 'nitropack/types';
|
|
15
17
|
import { Defu } from 'defu';
|
|
16
18
|
import { Stats } from 'node:fs';
|
|
17
19
|
import { ESMImport, ESMCodeGenOptions } from 'knitwork';
|
|
@@ -153,7 +155,7 @@ interface GenImport {
|
|
|
153
155
|
imports: ESMImport | ESMImport[];
|
|
154
156
|
options?: ESMCodeGenOptions;
|
|
155
157
|
}
|
|
156
|
-
type Framework<T extends PresetName> = T extends 'nitro' ? NitroApp : T extends 'nuxt' ? NitroApp : T extends 'h3' ? Router : never;
|
|
158
|
+
type Framework<T extends PresetName> = T extends 'nitro' ? nitropack_types.NitroApp : T extends 'nuxt' ? nitropack_types.NitroApp : T extends 'h3' ? h3.Router : never;
|
|
157
159
|
interface DefineFrameworkOptions<T extends PresetName> extends Omit<BuildSilgi$1, 'framework'> {
|
|
158
160
|
framework: Framework<T>;
|
|
159
161
|
}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "silgi",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "0.
|
|
4
|
+
"version": "0.31.0",
|
|
5
5
|
"private": false,
|
|
6
6
|
"sideEffects": false,
|
|
7
7
|
"exports": {
|
|
@@ -81,7 +81,6 @@
|
|
|
81
81
|
"dependencies": {
|
|
82
82
|
"@clack/prompts": "^0.10.1",
|
|
83
83
|
"@fastify/deepmerge": "^3.1.0",
|
|
84
|
-
"@oxc-parser/wasm": "^0.60.0",
|
|
85
84
|
"@standard-schema/spec": "^1.0.0",
|
|
86
85
|
"apiful": "^2.1.0",
|
|
87
86
|
"c12": "^3.0.3",
|
|
@@ -124,7 +123,7 @@
|
|
|
124
123
|
"@antfu/eslint-config": "^4.12.0",
|
|
125
124
|
"@nuxt/kit": "^3.16.2",
|
|
126
125
|
"@nuxt/schema": "^3.16.2",
|
|
127
|
-
"@silgi/ecosystem": "^0.6.
|
|
126
|
+
"@silgi/ecosystem": "^0.6.2",
|
|
128
127
|
"@types/node": "^22.15.2",
|
|
129
128
|
"@types/semver": "^7.7.0",
|
|
130
129
|
"@vitest/coverage-v8": "3.0.5",
|