nsgm-cli 2.1.14 → 2.1.15
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 +49 -26
- package/client/components/ClientProviders.tsx +29 -0
- package/client/components/LanguageSwitcher.tsx +59 -0
- package/client/components/SSRSafeAntdProvider.tsx +24 -0
- package/client/components/SuppressHydrationWarnings.tsx +55 -0
- package/client/layout/index.tsx +82 -126
- package/client/styled/common.ts +0 -1
- package/client/styled/layout/index.ts +218 -104
- package/client/styled/template/manage.ts +88 -1
- package/client/utils/i18n.ts +68 -0
- package/client/utils/menu.tsx +42 -36
- package/client/utils/navigation.ts +58 -0
- package/client/utils/suppressWarnings.ts +32 -0
- package/eslint.config.js +17 -20
- package/generation/client/redux/reducers.ts +1 -1
- package/generation/client/utils/menu.tsx +36 -30
- package/generation/env +3 -0
- package/generation/next.config.js +7 -3
- package/generation/package.json +5 -2
- package/generation/tsconfig.json +6 -19
- package/lib/cli/commands/create.js +1 -1
- package/lib/cli/commands/delete.js +1 -1
- package/lib/cli/commands/init.js +6 -6
- package/lib/cli/utils/prompt.d.ts +1 -1
- package/lib/cli/utils/prompt.js +76 -117
- package/lib/constants.d.ts +8 -1
- package/lib/constants.js +17 -2
- package/lib/generate.js +1 -0
- package/lib/generate_create.js +14 -11
- package/lib/generate_delete.js +86 -9
- package/lib/generate_init.d.ts +6 -0
- package/lib/generate_init.js +125 -5
- package/lib/generators/file-generator.d.ts +48 -0
- package/lib/generators/file-generator.js +455 -0
- package/lib/generators/i18n-generator.d.ts +51 -0
- package/lib/generators/i18n-generator.js +320 -0
- package/lib/generators/page-generator.d.ts +6 -2
- package/lib/generators/page-generator.js +182 -156
- package/lib/generators/resolver-generator.d.ts +6 -4
- package/lib/generators/resolver-generator.js +114 -75
- package/lib/generators/service-generator.d.ts +4 -0
- package/lib/generators/service-generator.js +120 -6
- package/lib/tsconfig.build.tsbuildinfo +1 -1
- package/next-i18next.config.js +18 -0
- package/next.config.js +55 -16
- package/package.json +7 -2
- package/pages/_app.tsx +84 -35
- package/pages/_document.tsx +39 -2
- package/pages/_error.tsx +66 -0
- package/pages/index.tsx +46 -29
- package/pages/login.tsx +58 -33
- package/pages/template/manage.tsx +95 -109
- package/public/locales/en-US/common.json +48 -0
- package/public/locales/en-US/home.json +57 -0
- package/public/locales/en-US/layout.json +22 -0
- package/public/locales/en-US/login.json +13 -0
- package/public/locales/en-US/template.json +42 -0
- package/public/locales/ja-JP/common.json +48 -0
- package/public/locales/ja-JP/home.json +57 -0
- package/public/locales/ja-JP/layout.json +22 -0
- package/public/locales/ja-JP/login.json +13 -0
- package/public/locales/ja-JP/template.json +42 -0
- package/public/locales/zh-CN/common.json +48 -0
- package/public/locales/zh-CN/home.json +57 -0
- package/public/locales/zh-CN/layout.json +22 -0
- package/public/locales/zh-CN/login.json +13 -0
- package/public/locales/zh-CN/template.json +42 -0
- package/server/utils/validation.js +163 -0
- package/types/i18next.d.ts +10 -0
package/lib/constants.js
CHANGED
|
@@ -36,8 +36,8 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
36
36
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
37
37
|
};
|
|
38
38
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
39
|
-
exports.
|
|
40
|
-
exports.mysqlDatabase = exports.mysqlPort = exports.mysqlHost = exports.mysqlPassword = exports.mysqlUser = exports.destServerRestPath = exports.destPackagePath = exports.destPublicHealthCheckPath = exports.destClientReduxReducersAllPath = exports.destClientUtilsMenuPath = exports.destScriptsPath = void 0;
|
|
39
|
+
exports.destServerPath = exports.destClientLayoutPath = exports.destClientUtilsPath = exports.destClientStyledLayoutPath = exports.destClientStyledPath = exports.destClientServicePath = exports.destClientReduxPath = exports.destClientPath = exports.projectPublicPath = exports.projectClientPath = exports.sourceTypesPath = exports.sourceScriptsPath = exports.sourcePublicPath = exports.sourcePagesPath = exports.sourceServerPathGeneration = exports.sourceServerPath = exports.sourceClientPathGeneration = exports.sourceClientPath = exports.sourceGenerationPath = exports.restPath = exports.packagePath = exports.slbHealthCheckPath = exports.reduxReducersPath = exports.utilsMenuPath = exports.sqlPath = exports.apisPath = exports.modulesPath = exports.componentsPath = exports.layoutPath = exports.utilsPath = exports.styledLayoutPath = exports.styledPath = exports.servicePath = exports.reduxPath = exports.typesPath = exports.typesPathSource = exports.scriptsPath = exports.scriptsPathSource = exports.publicPath = exports.publicPathSource = exports.pagesPath = exports.pagesPathSource = exports.serverPath = exports.serverPathSource = exports.clientPath = exports.clientPathSource = exports.generationPath = exports.isLocal = exports.destFolder = exports.sourceFolder = void 0;
|
|
40
|
+
exports.mysqlDatabase = exports.mysqlPort = exports.mysqlHost = exports.mysqlPassword = exports.mysqlUser = exports.destServerRestPath = exports.destPackagePath = exports.destPublicHealthCheckPath = exports.destClientReduxReducersAllPath = exports.destClientUtilsMenuPath = exports.destTypesPath = exports.destScriptsPath = exports.destPublicPath = exports.destPagesPath = exports.destServerUtilsPath = exports.destServerSqlPath = exports.destServerApisPath = exports.destServerModulesPath = void 0;
|
|
41
41
|
const path_1 = __importStar(require("path"));
|
|
42
42
|
const db_1 = __importDefault(require("./server/db"));
|
|
43
43
|
const sourceFolder = __dirname;
|
|
@@ -76,6 +76,10 @@ const scriptsPathSource = '../scripts';
|
|
|
76
76
|
exports.scriptsPathSource = scriptsPathSource;
|
|
77
77
|
const scriptsPath = './scripts';
|
|
78
78
|
exports.scriptsPath = scriptsPath;
|
|
79
|
+
const typesPathSource = '../types';
|
|
80
|
+
exports.typesPathSource = typesPathSource;
|
|
81
|
+
const typesPath = './types';
|
|
82
|
+
exports.typesPath = typesPath;
|
|
79
83
|
const reduxPath = '/redux';
|
|
80
84
|
exports.reduxPath = reduxPath;
|
|
81
85
|
const servicePath = '/service';
|
|
@@ -88,6 +92,8 @@ const utilsPath = '/utils';
|
|
|
88
92
|
exports.utilsPath = utilsPath;
|
|
89
93
|
const layoutPath = '/layout';
|
|
90
94
|
exports.layoutPath = layoutPath;
|
|
95
|
+
const componentsPath = '/components';
|
|
96
|
+
exports.componentsPath = componentsPath;
|
|
91
97
|
const modulesPath = '/modules';
|
|
92
98
|
exports.modulesPath = modulesPath;
|
|
93
99
|
const apisPath = '/apis';
|
|
@@ -120,6 +126,13 @@ const sourcePublicPath = path_1.default.join(sourceFolder, publicPathSource);
|
|
|
120
126
|
exports.sourcePublicPath = sourcePublicPath;
|
|
121
127
|
const sourceScriptsPath = path_1.default.join(sourceFolder, scriptsPathSource);
|
|
122
128
|
exports.sourceScriptsPath = sourceScriptsPath;
|
|
129
|
+
const sourceTypesPath = path_1.default.join(sourceFolder, typesPathSource);
|
|
130
|
+
exports.sourceTypesPath = sourceTypesPath;
|
|
131
|
+
// 当前项目的实际文件路径(用于复制现有文件)
|
|
132
|
+
const projectClientPath = path_1.default.join(destFolder, clientPath);
|
|
133
|
+
exports.projectClientPath = projectClientPath;
|
|
134
|
+
const projectPublicPath = path_1.default.join(destFolder, publicPath);
|
|
135
|
+
exports.projectPublicPath = projectPublicPath;
|
|
123
136
|
const destClientPath = path_1.default.join(destFolder, clientPath);
|
|
124
137
|
exports.destClientPath = destClientPath;
|
|
125
138
|
const destClientReduxPath = (0, path_1.resolve)(destClientPath + reduxPath);
|
|
@@ -150,6 +163,8 @@ const destPublicPath = path_1.default.join(destFolder, publicPath);
|
|
|
150
163
|
exports.destPublicPath = destPublicPath;
|
|
151
164
|
const destScriptsPath = path_1.default.join(destFolder, scriptsPath);
|
|
152
165
|
exports.destScriptsPath = destScriptsPath;
|
|
166
|
+
const destTypesPath = path_1.default.join(destFolder, typesPath);
|
|
167
|
+
exports.destTypesPath = destTypesPath;
|
|
153
168
|
const destClientUtilsMenuPath = (0, path_1.resolve)(destClientUtilsPath + utilsMenuPath);
|
|
154
169
|
exports.destClientUtilsMenuPath = destClientUtilsMenuPath;
|
|
155
170
|
const destClientReduxReducersAllPath = (0, path_1.resolve)(destClientReduxPath + reduxReducersPath);
|
package/lib/generate.js
CHANGED
|
@@ -73,6 +73,7 @@ const initFiles = (dictionary, upgradeFlag = false, projectConfig) => {
|
|
|
73
73
|
(0, generate_init_1.initScriptsFiles)(normalizedDictionary, newDestFolder);
|
|
74
74
|
const { destPackagePath } = (0, generate_init_1.initRootFiles)(normalizedDictionary, newDestFolder);
|
|
75
75
|
(0, generate_init_1.initTestFiles)(normalizedDictionary, newDestFolder);
|
|
76
|
+
(0, generate_init_1.initTypesFiles)(normalizedDictionary, newDestFolder);
|
|
76
77
|
// 如果提供了项目配置,应用到生成的文件中
|
|
77
78
|
if (projectConfig) {
|
|
78
79
|
console.log('应用项目配置...');
|
package/lib/generate_create.js
CHANGED
|
@@ -47,6 +47,7 @@ const schema_generator_1 = require("./generators/schema-generator");
|
|
|
47
47
|
const resolver_generator_1 = require("./generators/resolver-generator");
|
|
48
48
|
const service_generator_1 = require("./generators/service-generator");
|
|
49
49
|
const page_generator_1 = require("./generators/page-generator");
|
|
50
|
+
const file_generator_1 = require("./generators/file-generator");
|
|
50
51
|
// 常量定义
|
|
51
52
|
const TEMPLATE_FILES = {
|
|
52
53
|
reduxActions: 'redux/template/manage/actions.ts',
|
|
@@ -163,7 +164,7 @@ const performAdvancedReplacements = (controller, action, paths) => {
|
|
|
163
164
|
},
|
|
164
165
|
{
|
|
165
166
|
from: /Reducer,?\s*\n/,
|
|
166
|
-
to: `Reducer,\n ${controller}${(0, utils_1.firstUpperCase)(action)}: ${controller}${(0, utils_1.firstUpperCase)(action)}Reducer
|
|
167
|
+
to: `Reducer,\n ${controller}${(0, utils_1.firstUpperCase)(action)}: ${controller}${(0, utils_1.firstUpperCase)(action)}Reducer,\n`,
|
|
167
168
|
files: [paths.destClientReduxReducersAllPath],
|
|
168
169
|
},
|
|
169
170
|
{
|
|
@@ -199,22 +200,24 @@ const performAdvancedReplacements = (controller, action, paths) => {
|
|
|
199
200
|
});
|
|
200
201
|
}, MYSQL_TIMEOUT);
|
|
201
202
|
};
|
|
202
|
-
|
|
203
|
-
* 生成动态文件内容 - 使用专门的生成器
|
|
204
|
-
*/
|
|
205
|
-
const generateDynamicFiles = (controller, _action, paths, fields) => {
|
|
203
|
+
const generateDynamicFiles = (controller, action, paths, fields, dictionary) => {
|
|
206
204
|
// 创建生成器实例
|
|
207
|
-
const sqlGenerator = new sql_generator_1.SQLGenerator(controller,
|
|
208
|
-
const schemaGenerator = new schema_generator_1.SchemaGenerator(controller,
|
|
209
|
-
const resolverGenerator = new resolver_generator_1.ResolverGenerator(controller,
|
|
210
|
-
const serviceGenerator = new service_generator_1.ServiceGenerator(controller,
|
|
211
|
-
const pageGenerator = new page_generator_1.PageGenerator(controller,
|
|
205
|
+
const sqlGenerator = new sql_generator_1.SQLGenerator(controller, action, fields);
|
|
206
|
+
const schemaGenerator = new schema_generator_1.SchemaGenerator(controller, action, fields);
|
|
207
|
+
const resolverGenerator = new resolver_generator_1.ResolverGenerator(controller, action, fields);
|
|
208
|
+
const serviceGenerator = new service_generator_1.ServiceGenerator(controller, action, fields);
|
|
209
|
+
const pageGenerator = new page_generator_1.PageGenerator(controller, action, fields);
|
|
210
|
+
// 根据 dictionary 确定文件生成器的项目路径
|
|
211
|
+
const projectPath = !dictionary || dictionary === '.' ? '.' : path_1.default.join(constants_1.destFolder, dictionary);
|
|
212
|
+
const fileGenerator = new file_generator_1.FileGenerator(projectPath);
|
|
212
213
|
// 生成并写入文件
|
|
213
214
|
fs_1.default.writeFileSync(paths.destServerSqlController, sqlGenerator.generate());
|
|
214
215
|
fs_1.default.writeFileSync(paths.destServerModulesSchema, schemaGenerator.generate());
|
|
215
216
|
fs_1.default.writeFileSync(paths.destServerModulesResolver, resolverGenerator.generate());
|
|
216
217
|
fs_1.default.writeFileSync(paths.destClientAction, serviceGenerator.generate());
|
|
217
218
|
fs_1.default.writeFileSync(paths.destPagesAction, pageGenerator.generate());
|
|
219
|
+
// 生成多语言文件
|
|
220
|
+
fileGenerator.generateI18nFiles(controller, action, fields);
|
|
218
221
|
};
|
|
219
222
|
/**
|
|
220
223
|
* 复制并自定义模板文件
|
|
@@ -303,7 +306,7 @@ const createFiles = (controller, action, dictionary, fields) => {
|
|
|
303
306
|
createDirectoryStructure(basePaths);
|
|
304
307
|
console.log('Directory structure created');
|
|
305
308
|
// 4. 生成动态文件内容
|
|
306
|
-
generateDynamicFiles(controller, action, paths, finalFields);
|
|
309
|
+
generateDynamicFiles(controller, action, paths, finalFields, dictionary);
|
|
307
310
|
console.log('Dynamic files generated');
|
|
308
311
|
// 5. 复制并自定义模板文件
|
|
309
312
|
copyAndCustomizeTemplateFiles(paths, finalFields);
|
package/lib/generate_delete.js
CHANGED
|
@@ -25,6 +25,10 @@ const generateDeletePaths = (controller, action, dictionary) => {
|
|
|
25
25
|
destClientReduxReducersAllPath: path_1.default.join(basePath, 'client', 'redux', 'reducers.ts'),
|
|
26
26
|
destClientUtilsMenuPath: path_1.default.join(basePath, 'client', 'utils', 'menu.tsx'),
|
|
27
27
|
destServerRestPath: path_1.default.join(basePath, 'server', 'rest.js'),
|
|
28
|
+
// 多语言文件路径
|
|
29
|
+
destI18nZhCN: path_1.default.join(basePath, 'public', 'locales', 'zh-CN', `${controller}.json`),
|
|
30
|
+
destI18nEnUS: path_1.default.join(basePath, 'public', 'locales', 'en-US', `${controller}.json`),
|
|
31
|
+
destI18nJaJP: path_1.default.join(basePath, 'public', 'locales', 'ja-JP', `${controller}.json`),
|
|
28
32
|
...(action && {
|
|
29
33
|
destPagesAction: path_1.default.join(basePath, 'pages', controller, `${action}.tsx`),
|
|
30
34
|
destClientReduxControllerAction: path_1.default.join(basePath, 'client', 'redux', controller, action),
|
|
@@ -59,15 +63,38 @@ const deleteSpecificActionFiles = (paths) => {
|
|
|
59
63
|
(0, utils_1.rmFileSync)(paths.destClientStyledAction);
|
|
60
64
|
}
|
|
61
65
|
};
|
|
66
|
+
const deleteI18nFiles = (paths) => {
|
|
67
|
+
console.log('Deleting i18n files...');
|
|
68
|
+
const i18nFilesToDelete = [paths.destI18nZhCN, paths.destI18nEnUS, paths.destI18nJaJP];
|
|
69
|
+
i18nFilesToDelete.forEach((filePath) => {
|
|
70
|
+
(0, utils_1.rmFileSync)(filePath);
|
|
71
|
+
console.log(`✅ 删除多语言文件: ${filePath}`);
|
|
72
|
+
});
|
|
73
|
+
};
|
|
62
74
|
const cleanupConfigurationFiles = (controller, action, paths) => {
|
|
63
75
|
if (action === 'all') {
|
|
64
76
|
// 清理所有控制器相关的配置
|
|
65
|
-
|
|
77
|
+
// 1. 删除 import 语句
|
|
78
|
+
shelljs_1.default.sed('-i', new RegExp(`^.*import.*${controller}.*Reducer.*from.*$`, 'gm'), '', paths.destClientReduxReducersAllPath);
|
|
79
|
+
// 2. 删除 export 对象中的属性行
|
|
80
|
+
shelljs_1.default.sed('-i', new RegExp(`^\\s*${controller}[^:]*:\\s*${controller}.*Reducer,?\\s*$`, 'gm'), '', paths.destClientReduxReducersAllPath);
|
|
81
|
+
// 3. 修复可能出现的语法问题
|
|
82
|
+
// 移除空行
|
|
83
|
+
shelljs_1.default.sed('-i', /^\s*$/g, '', paths.destClientReduxReducersAllPath);
|
|
84
|
+
shelljs_1.default.sed('-i', /\n\n\n/g, '\n\n', paths.destClientReduxReducersAllPath);
|
|
85
|
+
// 4. 修复对象末尾的逗号问题
|
|
86
|
+
// 如果对象只剩一个属性,移除末尾逗号
|
|
87
|
+
shelljs_1.default.sed('-i', /,(\s*\n\s*\})/, '$1', paths.destClientReduxReducersAllPath);
|
|
88
|
+
// 5. 清理服务器端配置
|
|
66
89
|
shelljs_1.default.sed('-i', new RegExp(`.*${controller}.*`, 'g'), '', paths.destServerRestPath);
|
|
67
90
|
}
|
|
68
91
|
else {
|
|
69
92
|
// 清理特定动作的配置
|
|
70
|
-
shelljs_1.default.sed('-i', new RegExp(
|
|
93
|
+
shelljs_1.default.sed('-i', new RegExp(`^.*import.*${controller}${(0, utils_1.firstUpperCase)(action)}Reducer.*from.*$`, 'gm'), '', paths.destClientReduxReducersAllPath);
|
|
94
|
+
shelljs_1.default.sed('-i', new RegExp(`^\\s*${controller}${(0, utils_1.firstUpperCase)(action)}[^:]*:\\s*${controller}${(0, utils_1.firstUpperCase)(action)}.*Reducer,?\\s*$`, 'gm'), '', paths.destClientReduxReducersAllPath);
|
|
95
|
+
// 修复语法问题
|
|
96
|
+
shelljs_1.default.sed('-i', /^\s*$/g, '', paths.destClientReduxReducersAllPath);
|
|
97
|
+
shelljs_1.default.sed('-i', /,(\s*\n\s*\})/, '$1', paths.destClientReduxReducersAllPath);
|
|
71
98
|
}
|
|
72
99
|
};
|
|
73
100
|
const performDatabaseCleanup = (controller, paths) => {
|
|
@@ -84,19 +111,23 @@ const performDatabaseCleanup = (controller, paths) => {
|
|
|
84
111
|
};
|
|
85
112
|
const performAdvancedCleanup = (controller, action, paths) => {
|
|
86
113
|
const cleanupRules = [
|
|
114
|
+
// 标准化空行
|
|
87
115
|
{
|
|
88
|
-
from: /\n\s*\n
|
|
116
|
+
from: /\n\s*\n\s*\n/g,
|
|
89
117
|
to: '\n\n',
|
|
90
118
|
files: [paths.destClientReduxReducersAllPath],
|
|
91
119
|
},
|
|
120
|
+
// 修复 reducers.ts 中可能的语法问题
|
|
92
121
|
{
|
|
93
|
-
from: /Reducer,?\s*\n
|
|
94
|
-
to: '
|
|
122
|
+
from: /(\w+Reducer),?\s*\n\s*\}/g,
|
|
123
|
+
to: '$1,\n}',
|
|
95
124
|
files: [paths.destClientReduxReducersAllPath],
|
|
96
125
|
},
|
|
97
126
|
];
|
|
98
127
|
if (action === 'all') {
|
|
99
|
-
cleanupRules.push(
|
|
128
|
+
cleanupRules.push(
|
|
129
|
+
// 服务器端 REST 文件清理
|
|
130
|
+
{
|
|
100
131
|
from: /'(.\/apis\/template.*?)'\)\s*\n/,
|
|
101
132
|
to: "'./apis/template')\n\n",
|
|
102
133
|
files: [paths.destServerRestPath],
|
|
@@ -104,18 +135,62 @@ const performAdvancedCleanup = (controller, action, paths) => {
|
|
|
104
135
|
from: /template\)\s*\n/,
|
|
105
136
|
to: 'template)\n\n',
|
|
106
137
|
files: [paths.destServerRestPath],
|
|
107
|
-
},
|
|
108
|
-
|
|
109
|
-
|
|
138
|
+
},
|
|
139
|
+
// 菜单清理 - 改进版本,保持正确的缩进和逗号
|
|
140
|
+
{
|
|
141
|
+
from: new RegExp(`,?\\s*\\{\\s*//\\s*${controller}_.*_start[\\s\\S]*?//\\s*${controller}_.*_end\\s*\\}\\s*,?`, 'gm'),
|
|
142
|
+
to: ',', // 保留逗号,确保数组语法正确
|
|
110
143
|
files: [paths.destClientUtilsMenuPath],
|
|
111
144
|
});
|
|
112
145
|
}
|
|
113
146
|
setTimeout(() => {
|
|
114
147
|
(0, utils_1.replaceInFileAll)(cleanupRules, 0, () => {
|
|
115
148
|
console.log('Advanced cleanup completed');
|
|
149
|
+
// 执行额外的清理步骤
|
|
150
|
+
performFinalCleanup(paths);
|
|
151
|
+
// 如果是删除整个控制器,还需要清理菜单缩进
|
|
152
|
+
if (action === 'all') {
|
|
153
|
+
cleanupMenuIndentation(paths);
|
|
154
|
+
}
|
|
116
155
|
});
|
|
117
156
|
}, CLEANUP_TIMEOUT);
|
|
118
157
|
};
|
|
158
|
+
// 新增:智能菜单清理函数
|
|
159
|
+
const cleanupMenuIndentation = (paths) => {
|
|
160
|
+
// 读取菜单文件内容
|
|
161
|
+
const menuFile = paths.destClientUtilsMenuPath;
|
|
162
|
+
// 使用更智能的方式处理菜单清理,保持正确的缩进
|
|
163
|
+
setTimeout(() => {
|
|
164
|
+
// 清理可能出现的缩进问题,确保注释代码块有正确的缩进
|
|
165
|
+
shelljs_1.default.sed('-i', /^[ ]{0,2}\/\*\{/gm, ' /*{', menuFile);
|
|
166
|
+
shelljs_1.default.sed('-i', /^[ ]{0,4}key:/gm, ' key:', menuFile);
|
|
167
|
+
shelljs_1.default.sed('-i', /^[ ]{0,4}text:/gm, ' text:', menuFile);
|
|
168
|
+
shelljs_1.default.sed('-i', /^[ ]{0,4}url:/gm, ' url:', menuFile);
|
|
169
|
+
shelljs_1.default.sed('-i', /^[ ]{0,4}icon:/gm, ' icon:', menuFile);
|
|
170
|
+
shelljs_1.default.sed('-i', /^[ ]{0,4}subMenus:/gm, ' subMenus:', menuFile);
|
|
171
|
+
shelljs_1.default.sed('-i', /^[ ]{0,2}\}\*\//gm, ' }*/', menuFile);
|
|
172
|
+
// 修复可能出现的连续逗号问题
|
|
173
|
+
shelljs_1.default.sed('-i', /,,+/g, ',', menuFile);
|
|
174
|
+
// 修复数组末尾多余的逗号(在注释前)
|
|
175
|
+
shelljs_1.default.sed('-i', /,(\s*\/\*)/g, '$1', menuFile);
|
|
176
|
+
// 确保数组项之间有正确的逗号
|
|
177
|
+
shelljs_1.default.sed('-i', /(\})(\s*\/\*)/g, '$1,$2', menuFile);
|
|
178
|
+
console.log('Menu indentation cleanup completed');
|
|
179
|
+
}, 1500);
|
|
180
|
+
};
|
|
181
|
+
// 新增:最终清理函数
|
|
182
|
+
const performFinalCleanup = (paths) => {
|
|
183
|
+
// 修复 reducers.ts 的最终格式
|
|
184
|
+
setTimeout(() => {
|
|
185
|
+
// 确保最后一个属性有逗号(如果不是空对象)
|
|
186
|
+
shelljs_1.default.sed('-i', /(\w+Reducer)(\s*\n\s*\})/, '$1,$2', paths.destClientReduxReducersAllPath);
|
|
187
|
+
// 移除空对象中的逗号
|
|
188
|
+
shelljs_1.default.sed('-i', /\{\s*,\s*\}/, '{}', paths.destClientReduxReducersAllPath);
|
|
189
|
+
// 标准化缩进
|
|
190
|
+
shelljs_1.default.sed('-i', /^[ ]{2}/gm, ' ', paths.destClientReduxReducersAllPath);
|
|
191
|
+
console.log('Final cleanup completed');
|
|
192
|
+
}, 500);
|
|
193
|
+
};
|
|
119
194
|
/**
|
|
120
195
|
* 删除控制器相关的文件
|
|
121
196
|
* @param controller 控制器名称
|
|
@@ -132,6 +207,8 @@ const deleteFiles = (controller, action, deleteDBFlag = false, dictionary) => {
|
|
|
132
207
|
if (action === 'all') {
|
|
133
208
|
console.log('Deleting all controller files...');
|
|
134
209
|
deleteAllControllerFiles(paths);
|
|
210
|
+
// 删除多语言文件
|
|
211
|
+
deleteI18nFiles(paths);
|
|
135
212
|
}
|
|
136
213
|
else {
|
|
137
214
|
console.log(`Deleting specific action files for ${action}...`);
|
package/lib/generate_init.d.ts
CHANGED
|
@@ -41,6 +41,12 @@ export declare const initScriptsFiles: (dictionary: string, newDestFolder: strin
|
|
|
41
41
|
* @param newDestFolder 新的目标文件夹路径
|
|
42
42
|
*/
|
|
43
43
|
export declare const initRootFiles: (dictionary: string, newDestFolder: string) => InitResult;
|
|
44
|
+
/**
|
|
45
|
+
* 初始化类型定义文件
|
|
46
|
+
* @param dictionary 目标目录名称
|
|
47
|
+
* @param newDestFolder 新的目标文件夹路径
|
|
48
|
+
*/
|
|
49
|
+
export declare const initTypesFiles: (dictionary: string, newDestFolder: string) => void;
|
|
44
50
|
/**
|
|
45
51
|
* 初始化测试文件和目录
|
|
46
52
|
* @param dictionary 目标目录名称
|
package/lib/generate_init.js
CHANGED
|
@@ -33,10 +33,11 @@ var __importStar = (this && this.__importStar) || (function () {
|
|
|
33
33
|
};
|
|
34
34
|
})();
|
|
35
35
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
|
-
exports.initTestFiles = exports.initRootFiles = exports.initScriptsFiles = exports.initPublicFiles = exports.initServerFiles = exports.initPagesFiles = exports.initClientFiles = void 0;
|
|
36
|
+
exports.initTestFiles = exports.initTypesFiles = exports.initRootFiles = exports.initScriptsFiles = exports.initPublicFiles = exports.initServerFiles = exports.initPagesFiles = exports.initClientFiles = void 0;
|
|
37
37
|
const path_1 = __importStar(require("path"));
|
|
38
38
|
const constants_1 = require("./constants");
|
|
39
39
|
const utils_1 = require("./utils");
|
|
40
|
+
const fs_1 = require("fs");
|
|
40
41
|
// 常量定义
|
|
41
42
|
const CLIENT_FILES = {
|
|
42
43
|
reduxStore: '/store.ts',
|
|
@@ -46,7 +47,14 @@ const CLIENT_FILES = {
|
|
|
46
47
|
utilsFetch: '/fetch.ts',
|
|
47
48
|
utilsCookie: '/cookie.ts',
|
|
48
49
|
utilsSso: '/sso.ts',
|
|
50
|
+
utilsI18n: '/i18n.ts',
|
|
51
|
+
utilsNavigation: '/navigation.ts',
|
|
52
|
+
utilsSuppressWarnings: '/suppressWarnings.ts',
|
|
49
53
|
layoutIndex: '/index.tsx',
|
|
54
|
+
languageSwitcher: '/LanguageSwitcher.tsx',
|
|
55
|
+
clientProviders: '/ClientProviders.tsx',
|
|
56
|
+
ssrSafeAntdProvider: '/SSRSafeAntdProvider.tsx',
|
|
57
|
+
suppressHydrationWarnings: '/SuppressHydrationWarnings.tsx',
|
|
50
58
|
};
|
|
51
59
|
const PAGES_FILES = {
|
|
52
60
|
index: '/index.tsx',
|
|
@@ -58,10 +66,13 @@ const SERVER_FILES = {
|
|
|
58
66
|
apisSso: '/sso.js',
|
|
59
67
|
utilsCommon: '/common.js',
|
|
60
68
|
utilsDBPoolManager: '/db-pool-manager.js',
|
|
69
|
+
utilsValidation: '/validation.js',
|
|
61
70
|
};
|
|
62
71
|
const PUBLIC_FILES = {
|
|
63
72
|
images: '/images',
|
|
64
|
-
|
|
73
|
+
fonts: '/fonts',
|
|
74
|
+
favicon: '/favicon.ico',
|
|
75
|
+
locales: '/locales',
|
|
65
76
|
};
|
|
66
77
|
const SCRIPTS_FILES = {
|
|
67
78
|
startup: '/startup.sh',
|
|
@@ -70,6 +81,7 @@ const SCRIPTS_FILES = {
|
|
|
70
81
|
};
|
|
71
82
|
const ROOT_FILES = {
|
|
72
83
|
nextConfig: '/next.config.js',
|
|
84
|
+
nextI18nConfig: '/next-i18next.config.js',
|
|
73
85
|
mysqlConfig: '/mysql.config.js',
|
|
74
86
|
projectConfig: '/project.config.js',
|
|
75
87
|
tsconfig: '/tsconfig.json',
|
|
@@ -84,6 +96,8 @@ const ROOT_FILES = {
|
|
|
84
96
|
app: '/app.js',
|
|
85
97
|
envExampleSource: '/env.example',
|
|
86
98
|
envExample: '/.env.example',
|
|
99
|
+
envSource: '/env',
|
|
100
|
+
env: '/.env',
|
|
87
101
|
jestConfig: '/jest.config.js',
|
|
88
102
|
jestSetup: '/jest.setup.js',
|
|
89
103
|
jestSetupGlobals: '/jest.setup-globals.js',
|
|
@@ -124,6 +138,7 @@ const initClientFiles = (dictionary, newDestFolder, upgradeFlag) => {
|
|
|
124
138
|
destPaths.styledLayout,
|
|
125
139
|
destPaths.utils,
|
|
126
140
|
destPaths.layout,
|
|
141
|
+
(0, path_1.resolve)(baseDestPath + constants_1.componentsPath),
|
|
127
142
|
];
|
|
128
143
|
createDirectoryStructure(directoriesToCreate);
|
|
129
144
|
// 3. 定义文件映射
|
|
@@ -168,6 +183,41 @@ const initClientFiles = (dictionary, newDestFolder, upgradeFlag) => {
|
|
|
168
183
|
dest: (0, path_1.resolve)(destPaths.layout + CLIENT_FILES.layoutIndex),
|
|
169
184
|
upgradeFlag,
|
|
170
185
|
},
|
|
186
|
+
{
|
|
187
|
+
source: (0, path_1.resolve)(constants_1.projectClientPath + constants_1.utilsPath + CLIENT_FILES.utilsI18n),
|
|
188
|
+
dest: (0, path_1.resolve)(destPaths.utils + CLIENT_FILES.utilsI18n),
|
|
189
|
+
upgradeFlag,
|
|
190
|
+
},
|
|
191
|
+
{
|
|
192
|
+
source: (0, path_1.resolve)(constants_1.projectClientPath + constants_1.utilsPath + CLIENT_FILES.utilsNavigation),
|
|
193
|
+
dest: (0, path_1.resolve)(destPaths.utils + CLIENT_FILES.utilsNavigation),
|
|
194
|
+
upgradeFlag,
|
|
195
|
+
},
|
|
196
|
+
{
|
|
197
|
+
source: (0, path_1.resolve)(constants_1.projectClientPath + constants_1.componentsPath + CLIENT_FILES.languageSwitcher),
|
|
198
|
+
dest: (0, path_1.resolve)(baseDestPath + constants_1.componentsPath + CLIENT_FILES.languageSwitcher),
|
|
199
|
+
upgradeFlag,
|
|
200
|
+
},
|
|
201
|
+
{
|
|
202
|
+
source: (0, path_1.resolve)(constants_1.sourceClientPath + constants_1.componentsPath + CLIENT_FILES.clientProviders),
|
|
203
|
+
dest: (0, path_1.resolve)(baseDestPath + constants_1.componentsPath + CLIENT_FILES.clientProviders),
|
|
204
|
+
upgradeFlag,
|
|
205
|
+
},
|
|
206
|
+
{
|
|
207
|
+
source: (0, path_1.resolve)(constants_1.sourceClientPath + constants_1.componentsPath + CLIENT_FILES.ssrSafeAntdProvider),
|
|
208
|
+
dest: (0, path_1.resolve)(baseDestPath + constants_1.componentsPath + CLIENT_FILES.ssrSafeAntdProvider),
|
|
209
|
+
upgradeFlag,
|
|
210
|
+
},
|
|
211
|
+
{
|
|
212
|
+
source: (0, path_1.resolve)(constants_1.sourceClientPath + constants_1.componentsPath + CLIENT_FILES.suppressHydrationWarnings),
|
|
213
|
+
dest: (0, path_1.resolve)(baseDestPath + constants_1.componentsPath + CLIENT_FILES.suppressHydrationWarnings),
|
|
214
|
+
upgradeFlag,
|
|
215
|
+
},
|
|
216
|
+
{
|
|
217
|
+
source: (0, path_1.resolve)(constants_1.sourceClientPath + constants_1.utilsPath + CLIENT_FILES.utilsSuppressWarnings),
|
|
218
|
+
dest: (0, path_1.resolve)(baseDestPath + constants_1.utilsPath + CLIENT_FILES.utilsSuppressWarnings),
|
|
219
|
+
upgradeFlag,
|
|
220
|
+
},
|
|
171
221
|
// 这些文件不使用 upgradeFlag
|
|
172
222
|
{
|
|
173
223
|
source: (0, path_1.resolve)(constants_1.sourceClientPathGeneration + constants_1.reduxPath + constants_1.reduxReducersPath),
|
|
@@ -274,6 +324,11 @@ const initServerFiles = (dictionary, newDestFolder, upgradeFlag) => {
|
|
|
274
324
|
dest: (0, path_1.resolve)(destPaths.utils + SERVER_FILES.utilsDBPoolManager),
|
|
275
325
|
upgradeFlag,
|
|
276
326
|
},
|
|
327
|
+
{
|
|
328
|
+
source: (0, path_1.resolve)(constants_1.sourceServerPath + constants_1.utilsPath + SERVER_FILES.utilsValidation),
|
|
329
|
+
dest: (0, path_1.resolve)(destPaths.utils + SERVER_FILES.utilsValidation),
|
|
330
|
+
upgradeFlag,
|
|
331
|
+
},
|
|
277
332
|
// REST 文件不使用 upgradeFlag
|
|
278
333
|
{
|
|
279
334
|
source: (0, path_1.resolve)(constants_1.sourceServerPathGeneration + constants_1.restPath),
|
|
@@ -307,9 +362,11 @@ const initPublicFiles = (dictionary, newDestFolder, upgradeFlag) => {
|
|
|
307
362
|
const destPaths = {
|
|
308
363
|
public: baseDestPath,
|
|
309
364
|
images: (0, path_1.resolve)(baseDestPath + PUBLIC_FILES.images),
|
|
365
|
+
fonts: (0, path_1.resolve)(baseDestPath + PUBLIC_FILES.fonts),
|
|
366
|
+
locales: (0, path_1.resolve)(baseDestPath + PUBLIC_FILES.locales),
|
|
310
367
|
};
|
|
311
368
|
// 2. 创建目录结构
|
|
312
|
-
const directoriesToCreate = [destPaths.public, destPaths.images];
|
|
369
|
+
const directoriesToCreate = [destPaths.public, destPaths.images, destPaths.fonts, destPaths.locales];
|
|
313
370
|
createDirectoryStructure(directoriesToCreate);
|
|
314
371
|
// 3. 定义文件映射
|
|
315
372
|
const fileMappings = [
|
|
@@ -319,13 +376,42 @@ const initPublicFiles = (dictionary, newDestFolder, upgradeFlag) => {
|
|
|
319
376
|
upgradeFlag,
|
|
320
377
|
},
|
|
321
378
|
{
|
|
322
|
-
source: (0, path_1.resolve)(constants_1.sourcePublicPath + PUBLIC_FILES.
|
|
323
|
-
dest: (0, path_1.resolve)(destPaths.
|
|
379
|
+
source: (0, path_1.resolve)(constants_1.sourcePublicPath + PUBLIC_FILES.favicon),
|
|
380
|
+
dest: (0, path_1.resolve)(destPaths.public + PUBLIC_FILES.favicon),
|
|
324
381
|
upgradeFlag,
|
|
325
382
|
},
|
|
326
383
|
];
|
|
327
384
|
// 4. 复制文件
|
|
328
385
|
copyMultipleFiles(fileMappings);
|
|
386
|
+
// 5. 复制 fonts 目录下的所有文件
|
|
387
|
+
const sourceFontsDir = (0, path_1.resolve)(constants_1.sourcePublicPath + PUBLIC_FILES.fonts);
|
|
388
|
+
if ((0, fs_1.existsSync)(sourceFontsDir)) {
|
|
389
|
+
const fontFiles = (0, fs_1.readdirSync)(sourceFontsDir);
|
|
390
|
+
fontFiles.forEach((file) => {
|
|
391
|
+
const sourceFile = (0, path_1.resolve)(sourceFontsDir, file);
|
|
392
|
+
const destFile = (0, path_1.resolve)(destPaths.fonts, file);
|
|
393
|
+
(0, utils_1.copyFileSync)(sourceFile, destFile, upgradeFlag);
|
|
394
|
+
});
|
|
395
|
+
}
|
|
396
|
+
// 6. 复制 locales 目录下的所有文件(递归复制)
|
|
397
|
+
const sourceLocalesDir = (0, path_1.resolve)(constants_1.projectPublicPath + PUBLIC_FILES.locales);
|
|
398
|
+
if ((0, fs_1.existsSync)(sourceLocalesDir)) {
|
|
399
|
+
const copyLocalesRecursive = (sourceDir, destDir) => {
|
|
400
|
+
const items = (0, fs_1.readdirSync)(sourceDir, { withFileTypes: true });
|
|
401
|
+
items.forEach((item) => {
|
|
402
|
+
const sourcePath = (0, path_1.resolve)(sourceDir, item.name);
|
|
403
|
+
const destPath = (0, path_1.resolve)(destDir, item.name);
|
|
404
|
+
if (item.isDirectory()) {
|
|
405
|
+
(0, utils_1.mkdirSync)(destPath);
|
|
406
|
+
copyLocalesRecursive(sourcePath, destPath);
|
|
407
|
+
}
|
|
408
|
+
else {
|
|
409
|
+
(0, utils_1.copyFileSync)(sourcePath, destPath, upgradeFlag);
|
|
410
|
+
}
|
|
411
|
+
});
|
|
412
|
+
};
|
|
413
|
+
copyLocalesRecursive(sourceLocalesDir, destPaths.locales);
|
|
414
|
+
}
|
|
329
415
|
console.log('Public files initialization completed');
|
|
330
416
|
return {
|
|
331
417
|
destPublicHealthCheckPath: (0, path_1.resolve)(destPaths.public + constants_1.slbHealthCheckPath),
|
|
@@ -390,6 +476,10 @@ const initRootFiles = (dictionary, newDestFolder) => {
|
|
|
390
476
|
source: (0, path_1.resolve)(constants_1.sourceGenerationPath + ROOT_FILES.nextConfig),
|
|
391
477
|
dest: (0, path_1.resolve)(baseDestPath + ROOT_FILES.nextConfig),
|
|
392
478
|
},
|
|
479
|
+
{
|
|
480
|
+
source: (0, path_1.resolve)(constants_1.destFolder + ROOT_FILES.nextI18nConfig),
|
|
481
|
+
dest: (0, path_1.resolve)(baseDestPath + ROOT_FILES.nextI18nConfig),
|
|
482
|
+
},
|
|
393
483
|
{
|
|
394
484
|
source: (0, path_1.resolve)(constants_1.sourceGenerationPath + ROOT_FILES.mysqlConfig),
|
|
395
485
|
dest: (0, path_1.resolve)(baseDestPath + ROOT_FILES.mysqlConfig),
|
|
@@ -434,6 +524,10 @@ const initRootFiles = (dictionary, newDestFolder) => {
|
|
|
434
524
|
source: (0, path_1.resolve)(constants_1.sourceGenerationPath + ROOT_FILES.envExampleSource),
|
|
435
525
|
dest: (0, path_1.resolve)(baseDestPath + ROOT_FILES.envExample),
|
|
436
526
|
},
|
|
527
|
+
{
|
|
528
|
+
source: (0, path_1.resolve)(constants_1.sourceGenerationPath + ROOT_FILES.envSource),
|
|
529
|
+
dest: (0, path_1.resolve)(baseDestPath + ROOT_FILES.env),
|
|
530
|
+
},
|
|
437
531
|
{
|
|
438
532
|
source: (0, path_1.resolve)(constants_1.sourceGenerationPath + ROOT_FILES.jestConfig),
|
|
439
533
|
dest: (0, path_1.resolve)(baseDestPath + ROOT_FILES.jestConfig),
|
|
@@ -460,6 +554,32 @@ const initRootFiles = (dictionary, newDestFolder) => {
|
|
|
460
554
|
}
|
|
461
555
|
};
|
|
462
556
|
exports.initRootFiles = initRootFiles;
|
|
557
|
+
/**
|
|
558
|
+
* 初始化类型定义文件
|
|
559
|
+
* @param dictionary 目标目录名称
|
|
560
|
+
* @param newDestFolder 新的目标文件夹路径
|
|
561
|
+
*/
|
|
562
|
+
const initTypesFiles = (dictionary, newDestFolder) => {
|
|
563
|
+
console.log('Initializing types files...');
|
|
564
|
+
try {
|
|
565
|
+
// 1. 确定目标路径
|
|
566
|
+
const baseDestPath = dictionary === '' ? constants_1.destTypesPath : path_1.default.join(newDestFolder, constants_1.typesPath);
|
|
567
|
+
// 2. 创建目录
|
|
568
|
+
createDirectoryStructure([baseDestPath]);
|
|
569
|
+
// 3. 复制 i18next.d.ts 文件
|
|
570
|
+
const sourceI18nextFile = (0, path_1.resolve)(constants_1.destFolder, 'types', 'i18next.d.ts');
|
|
571
|
+
const destI18nextFile = (0, path_1.resolve)(baseDestPath, 'i18next.d.ts');
|
|
572
|
+
if ((0, fs_1.existsSync)(sourceI18nextFile)) {
|
|
573
|
+
(0, utils_1.copyFileSync)(sourceI18nextFile, destI18nextFile);
|
|
574
|
+
}
|
|
575
|
+
console.log('Types files initialization completed');
|
|
576
|
+
}
|
|
577
|
+
catch (error) {
|
|
578
|
+
console.error('Failed to initialize types files:', error);
|
|
579
|
+
throw error;
|
|
580
|
+
}
|
|
581
|
+
};
|
|
582
|
+
exports.initTypesFiles = initTypesFiles;
|
|
463
583
|
/**
|
|
464
584
|
* 初始化测试文件和目录
|
|
465
585
|
* @param dictionary 目标目录名称
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 文件生成器
|
|
3
|
+
* 负责将生成的内容写入到文件系统
|
|
4
|
+
*/
|
|
5
|
+
export declare class FileGenerator {
|
|
6
|
+
private projectPath;
|
|
7
|
+
constructor(projectPath?: string);
|
|
8
|
+
/**
|
|
9
|
+
* 生成多语言文件
|
|
10
|
+
*/
|
|
11
|
+
generateI18nFiles(controller: string, action: string, fields: any[]): void;
|
|
12
|
+
/**
|
|
13
|
+
* 生成页面组件文件
|
|
14
|
+
*/
|
|
15
|
+
generatePageFile(controller: string, action: string, _fields: any[], content: string): void;
|
|
16
|
+
/**
|
|
17
|
+
* 生成样式文件
|
|
18
|
+
*/
|
|
19
|
+
generateStyleFile(controller: string, action: string): void;
|
|
20
|
+
/**
|
|
21
|
+
* 生成Redux相关文件
|
|
22
|
+
*/
|
|
23
|
+
generateReduxFiles(controller: string, action: string, _fields: any[]): void;
|
|
24
|
+
/**
|
|
25
|
+
* 生成服务文件
|
|
26
|
+
*/
|
|
27
|
+
generateServiceFile(controller: string, action: string): void;
|
|
28
|
+
/**
|
|
29
|
+
* 确保目录存在
|
|
30
|
+
*/
|
|
31
|
+
private ensureDirectoryExists;
|
|
32
|
+
/**
|
|
33
|
+
* 生成样式组件内容
|
|
34
|
+
*/
|
|
35
|
+
private generateStyledComponentsContent;
|
|
36
|
+
/**
|
|
37
|
+
* 生成Actions内容
|
|
38
|
+
*/
|
|
39
|
+
private generateActionsContent;
|
|
40
|
+
/**
|
|
41
|
+
* 生成Reducer内容
|
|
42
|
+
*/
|
|
43
|
+
private generateReducerContent;
|
|
44
|
+
/**
|
|
45
|
+
* 生成Service内容
|
|
46
|
+
*/
|
|
47
|
+
private generateServiceContent;
|
|
48
|
+
}
|