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
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
{
|
|
2
|
+
"template": {
|
|
3
|
+
"title": "Template Management",
|
|
4
|
+
"fields": {
|
|
5
|
+
"id": "ID",
|
|
6
|
+
"name": "Name",
|
|
7
|
+
"actions": "Actions"
|
|
8
|
+
},
|
|
9
|
+
"buttons": {
|
|
10
|
+
"add": "Add",
|
|
11
|
+
"edit": "Edit",
|
|
12
|
+
"delete": "Delete",
|
|
13
|
+
"search": "Search",
|
|
14
|
+
"export": "Export",
|
|
15
|
+
"import": "Import",
|
|
16
|
+
"batchDelete": "Batch Delete",
|
|
17
|
+
"confirm": "Confirm",
|
|
18
|
+
"cancel": "Cancel"
|
|
19
|
+
},
|
|
20
|
+
"placeholders": {
|
|
21
|
+
"enterName": "Enter name to search",
|
|
22
|
+
"inputName": "Enter name"
|
|
23
|
+
},
|
|
24
|
+
"messages": {
|
|
25
|
+
"confirmDelete": "Are you sure to delete?",
|
|
26
|
+
"confirmBatchDelete": "Are you sure to batch delete?",
|
|
27
|
+
"uploadSuccess": "File uploaded successfully",
|
|
28
|
+
"uploadFailed": "File upload failed",
|
|
29
|
+
"onlyExcel": "Only Excel files are allowed!",
|
|
30
|
+
"fileSizeLimit": "File size cannot exceed 2MB!",
|
|
31
|
+
"noData": "No data to export",
|
|
32
|
+
"noDataBatchDelete": "No data to batch delete"
|
|
33
|
+
},
|
|
34
|
+
"modal": {
|
|
35
|
+
"addTitle": "Add Template",
|
|
36
|
+
"editTitle": "Edit Template"
|
|
37
|
+
},
|
|
38
|
+
"pagination": {
|
|
39
|
+
"total": "Total {{total}} records"
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
}
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
{
|
|
2
|
+
"common": {
|
|
3
|
+
"confirm": "確認",
|
|
4
|
+
"cancel": "キャンセル",
|
|
5
|
+
"save": "保存",
|
|
6
|
+
"edit": "編集",
|
|
7
|
+
"delete": "削除",
|
|
8
|
+
"add": "追加",
|
|
9
|
+
"search": "検索",
|
|
10
|
+
"reset": "リセット",
|
|
11
|
+
"submit": "送信",
|
|
12
|
+
"back": "戻る",
|
|
13
|
+
"next": "次へ",
|
|
14
|
+
"previous": "前へ",
|
|
15
|
+
"loading": "読み込み中...",
|
|
16
|
+
"success": "成功",
|
|
17
|
+
"error": "エラー",
|
|
18
|
+
"warning": "警告",
|
|
19
|
+
"info": "情報",
|
|
20
|
+
"yes": "はい",
|
|
21
|
+
"no": "いいえ",
|
|
22
|
+
"close": "閉じる",
|
|
23
|
+
"refresh": "更新"
|
|
24
|
+
},
|
|
25
|
+
"navigation": {
|
|
26
|
+
"home": "ホーム",
|
|
27
|
+
"dashboard": "ダッシュボード",
|
|
28
|
+
"settings": "設定",
|
|
29
|
+
"profile": "プロフィール",
|
|
30
|
+
"logout": "ログアウト"
|
|
31
|
+
},
|
|
32
|
+
"form": {
|
|
33
|
+
"required": "この項目は必須です",
|
|
34
|
+
"invalidEmail": "有効なメールアドレスを入力してください",
|
|
35
|
+
"invalidPhone": "有効な電話番号を入力してください",
|
|
36
|
+
"passwordTooShort": "パスワードは8文字以上で入力してください",
|
|
37
|
+
"confirmPassword": "パスワード確認",
|
|
38
|
+
"passwordMismatch": "パスワードが一致しません"
|
|
39
|
+
},
|
|
40
|
+
"messages": {
|
|
41
|
+
"saveSuccess": "保存が完了しました",
|
|
42
|
+
"deleteSuccess": "削除が完了しました",
|
|
43
|
+
"updateSuccess": "更新が完了しました",
|
|
44
|
+
"createSuccess": "作成が完了しました",
|
|
45
|
+
"operationFailed": "操作に失敗しました",
|
|
46
|
+
"networkError": "ネットワークエラーが発生しました。後でもう一度お試しください"
|
|
47
|
+
}
|
|
48
|
+
}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
{
|
|
2
|
+
"page": {
|
|
3
|
+
"title": "NSGM CLI",
|
|
4
|
+
"description": "フルスタックアーキテクチャ、コードテンプレート生成、迅速な開発",
|
|
5
|
+
"sections": {
|
|
6
|
+
"database": {
|
|
7
|
+
"title": "データベース設定",
|
|
8
|
+
"description": "データベースはMysqlを使用、設定はmysql.config.jsを参照"
|
|
9
|
+
},
|
|
10
|
+
"project": {
|
|
11
|
+
"title": "プロジェクト設定",
|
|
12
|
+
"description": "プロジェクト設定はproject.config.jsを参照"
|
|
13
|
+
},
|
|
14
|
+
"framework": {
|
|
15
|
+
"title": "フレームワーク設定",
|
|
16
|
+
"description": "Nextフレームワーク設定はnext.config.jsを参照"
|
|
17
|
+
}
|
|
18
|
+
},
|
|
19
|
+
"commands": {
|
|
20
|
+
"title": "コマンド",
|
|
21
|
+
"categories": {
|
|
22
|
+
"projectManagement": {
|
|
23
|
+
"title": "プロジェクト管理",
|
|
24
|
+
"items": {
|
|
25
|
+
"init": "プロジェクトを初期化",
|
|
26
|
+
"upgrade": "プロジェクト基盤ファイルをアップグレード"
|
|
27
|
+
}
|
|
28
|
+
},
|
|
29
|
+
"templateOperations": {
|
|
30
|
+
"title": "テンプレート操作",
|
|
31
|
+
"items": {
|
|
32
|
+
"create": "テンプレートページを作成",
|
|
33
|
+
"delete": "テンプレートページを削除",
|
|
34
|
+
"deletedb": "テンプレートページとデータベーステーブルを削除"
|
|
35
|
+
}
|
|
36
|
+
},
|
|
37
|
+
"runBuild": {
|
|
38
|
+
"title": "実行とビルド",
|
|
39
|
+
"items": {
|
|
40
|
+
"dev": "開発モード",
|
|
41
|
+
"start": "本番モード",
|
|
42
|
+
"build": "ビルド",
|
|
43
|
+
"export": "静的ページをエクスポート"
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
},
|
|
48
|
+
"parameters": {
|
|
49
|
+
"title": "パラメータ",
|
|
50
|
+
"items": {
|
|
51
|
+
"dictionary": "export/initで使用、デフォルトはwebapp",
|
|
52
|
+
"controller": "create/deleteで使用時は必須",
|
|
53
|
+
"action": "create/deleteで使用、デフォルトはmanage"
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
{
|
|
2
|
+
"layout": {
|
|
3
|
+
"userActions": {
|
|
4
|
+
"logout": "ログアウト",
|
|
5
|
+
"profile": "プロフィール",
|
|
6
|
+
"settings": "アカウント設定",
|
|
7
|
+
"notifications": "通知",
|
|
8
|
+
"user": "ユーザー"
|
|
9
|
+
},
|
|
10
|
+
"navigation": {
|
|
11
|
+
"home": "ホーム",
|
|
12
|
+
"dashboard": "ダッシュボード",
|
|
13
|
+
"management": "管理",
|
|
14
|
+
"system": "システム"
|
|
15
|
+
},
|
|
16
|
+
"menu": {
|
|
17
|
+
"introduction": "紹介",
|
|
18
|
+
"template": "テンプレート",
|
|
19
|
+
"template1": "テンプレート1"
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
}
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
{
|
|
2
|
+
"template": {
|
|
3
|
+
"title": "テンプレート管理",
|
|
4
|
+
"fields": {
|
|
5
|
+
"id": "ID",
|
|
6
|
+
"name": "名前",
|
|
7
|
+
"actions": "操作"
|
|
8
|
+
},
|
|
9
|
+
"buttons": {
|
|
10
|
+
"add": "追加",
|
|
11
|
+
"edit": "編集",
|
|
12
|
+
"delete": "削除",
|
|
13
|
+
"search": "検索",
|
|
14
|
+
"export": "エクスポート",
|
|
15
|
+
"import": "インポート",
|
|
16
|
+
"batchDelete": "一括削除",
|
|
17
|
+
"confirm": "確認",
|
|
18
|
+
"cancel": "キャンセル"
|
|
19
|
+
},
|
|
20
|
+
"placeholders": {
|
|
21
|
+
"enterName": "名前を入力して検索",
|
|
22
|
+
"inputName": "名前を入力"
|
|
23
|
+
},
|
|
24
|
+
"messages": {
|
|
25
|
+
"confirmDelete": "削除してもよろしいですか?",
|
|
26
|
+
"confirmBatchDelete": "一括削除してもよろしいですか?",
|
|
27
|
+
"uploadSuccess": "ファイルのアップロードが成功しました",
|
|
28
|
+
"uploadFailed": "ファイルのアップロードに失敗しました",
|
|
29
|
+
"onlyExcel": "Excelファイルのみアップロード可能です!",
|
|
30
|
+
"fileSizeLimit": "ファイルサイズは2MBを超えることはできません!",
|
|
31
|
+
"noData": "エクスポートするデータがありません",
|
|
32
|
+
"noDataBatchDelete": "一括削除するデータがありません"
|
|
33
|
+
},
|
|
34
|
+
"modal": {
|
|
35
|
+
"addTitle": "テンプレート追加",
|
|
36
|
+
"editTitle": "テンプレート編集"
|
|
37
|
+
},
|
|
38
|
+
"pagination": {
|
|
39
|
+
"total": "合計 {{total}} 件"
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
}
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
{
|
|
2
|
+
"common": {
|
|
3
|
+
"confirm": "确认",
|
|
4
|
+
"cancel": "取消",
|
|
5
|
+
"save": "保存",
|
|
6
|
+
"edit": "编辑",
|
|
7
|
+
"delete": "删除",
|
|
8
|
+
"add": "添加",
|
|
9
|
+
"search": "搜索",
|
|
10
|
+
"reset": "重置",
|
|
11
|
+
"submit": "提交",
|
|
12
|
+
"back": "返回",
|
|
13
|
+
"next": "下一步",
|
|
14
|
+
"previous": "上一步",
|
|
15
|
+
"loading": "加载中...",
|
|
16
|
+
"success": "成功",
|
|
17
|
+
"error": "错误",
|
|
18
|
+
"warning": "警告",
|
|
19
|
+
"info": "信息",
|
|
20
|
+
"yes": "是",
|
|
21
|
+
"no": "否",
|
|
22
|
+
"close": "关闭",
|
|
23
|
+
"refresh": "刷新"
|
|
24
|
+
},
|
|
25
|
+
"navigation": {
|
|
26
|
+
"home": "首页",
|
|
27
|
+
"dashboard": "仪表板",
|
|
28
|
+
"settings": "设置",
|
|
29
|
+
"profile": "个人资料",
|
|
30
|
+
"logout": "退出登录"
|
|
31
|
+
},
|
|
32
|
+
"form": {
|
|
33
|
+
"required": "此字段为必填项",
|
|
34
|
+
"invalidEmail": "请输入有效的邮箱地址",
|
|
35
|
+
"invalidPhone": "请输入有效的手机号码",
|
|
36
|
+
"passwordTooShort": "密码至少需要8个字符",
|
|
37
|
+
"confirmPassword": "确认密码",
|
|
38
|
+
"passwordMismatch": "密码不匹配"
|
|
39
|
+
},
|
|
40
|
+
"messages": {
|
|
41
|
+
"saveSuccess": "保存成功",
|
|
42
|
+
"deleteSuccess": "删除成功",
|
|
43
|
+
"updateSuccess": "更新成功",
|
|
44
|
+
"createSuccess": "创建成功",
|
|
45
|
+
"operationFailed": "操作失败",
|
|
46
|
+
"networkError": "网络错误,请稍后重试"
|
|
47
|
+
}
|
|
48
|
+
}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
{
|
|
2
|
+
"page": {
|
|
3
|
+
"title": "NSGM CLI",
|
|
4
|
+
"description": "全栈架构,代码模板生成,快速开发",
|
|
5
|
+
"sections": {
|
|
6
|
+
"database": {
|
|
7
|
+
"title": "数据库配置",
|
|
8
|
+
"description": "数据库采用 Mysql, 配置见 mysql.config.js"
|
|
9
|
+
},
|
|
10
|
+
"project": {
|
|
11
|
+
"title": "项目配置",
|
|
12
|
+
"description": "项目配置见 project.config.js"
|
|
13
|
+
},
|
|
14
|
+
"framework": {
|
|
15
|
+
"title": "框架配置",
|
|
16
|
+
"description": "Next 框架配置见 next.config.js"
|
|
17
|
+
}
|
|
18
|
+
},
|
|
19
|
+
"commands": {
|
|
20
|
+
"title": "命令",
|
|
21
|
+
"categories": {
|
|
22
|
+
"projectManagement": {
|
|
23
|
+
"title": "项目管理",
|
|
24
|
+
"items": {
|
|
25
|
+
"init": "初始化项目",
|
|
26
|
+
"upgrade": "升级项目基础文件"
|
|
27
|
+
}
|
|
28
|
+
},
|
|
29
|
+
"templateOperations": {
|
|
30
|
+
"title": "模板操作",
|
|
31
|
+
"items": {
|
|
32
|
+
"create": "创建模板页面",
|
|
33
|
+
"delete": "删除模板页面",
|
|
34
|
+
"deletedb": "删除模板页面及数据库表"
|
|
35
|
+
}
|
|
36
|
+
},
|
|
37
|
+
"runBuild": {
|
|
38
|
+
"title": "运行与构建",
|
|
39
|
+
"items": {
|
|
40
|
+
"dev": "开发模式",
|
|
41
|
+
"start": "生产模式",
|
|
42
|
+
"build": "编译",
|
|
43
|
+
"export": "导出静态页面"
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
},
|
|
48
|
+
"parameters": {
|
|
49
|
+
"title": "参数",
|
|
50
|
+
"items": {
|
|
51
|
+
"dictionary": "在 export/init 的时候使用, 默认 webapp",
|
|
52
|
+
"controller": "在 create/delete 的时候使用,必须有",
|
|
53
|
+
"action": "在 create/delete 的时候使用,默认 manage"
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
{
|
|
2
|
+
"layout": {
|
|
3
|
+
"userActions": {
|
|
4
|
+
"logout": "退出登录",
|
|
5
|
+
"profile": "个人中心",
|
|
6
|
+
"settings": "账户设置",
|
|
7
|
+
"notifications": "通知",
|
|
8
|
+
"user": "用户"
|
|
9
|
+
},
|
|
10
|
+
"navigation": {
|
|
11
|
+
"home": "首页",
|
|
12
|
+
"dashboard": "仪表板",
|
|
13
|
+
"management": "管理",
|
|
14
|
+
"system": "系统"
|
|
15
|
+
},
|
|
16
|
+
"menu": {
|
|
17
|
+
"introduction": "介绍",
|
|
18
|
+
"template": "模板",
|
|
19
|
+
"template1": "模板1"
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
}
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
{
|
|
2
|
+
"template": {
|
|
3
|
+
"title": "Template 管理",
|
|
4
|
+
"fields": {
|
|
5
|
+
"id": "ID",
|
|
6
|
+
"name": "名称",
|
|
7
|
+
"actions": "操作"
|
|
8
|
+
},
|
|
9
|
+
"buttons": {
|
|
10
|
+
"add": "新增",
|
|
11
|
+
"edit": "修改",
|
|
12
|
+
"delete": "删除",
|
|
13
|
+
"search": "搜索",
|
|
14
|
+
"export": "导出",
|
|
15
|
+
"import": "导入",
|
|
16
|
+
"batchDelete": "批量删除",
|
|
17
|
+
"confirm": "确认",
|
|
18
|
+
"cancel": "取消"
|
|
19
|
+
},
|
|
20
|
+
"placeholders": {
|
|
21
|
+
"enterName": "请输入名称搜索",
|
|
22
|
+
"inputName": "请输入名称"
|
|
23
|
+
},
|
|
24
|
+
"messages": {
|
|
25
|
+
"confirmDelete": "确认删除吗",
|
|
26
|
+
"confirmBatchDelete": "确认批量删除吗",
|
|
27
|
+
"uploadSuccess": "文件上传成功",
|
|
28
|
+
"uploadFailed": "文件上传失败",
|
|
29
|
+
"onlyExcel": "只能上传 Excel 文件!",
|
|
30
|
+
"fileSizeLimit": "文件大小不能超过 2MB!",
|
|
31
|
+
"noData": "没有数据无需导出",
|
|
32
|
+
"noDataBatchDelete": "没有数据不能批量删除"
|
|
33
|
+
},
|
|
34
|
+
"modal": {
|
|
35
|
+
"addTitle": "新增 Template",
|
|
36
|
+
"editTitle": "修改 Template"
|
|
37
|
+
},
|
|
38
|
+
"pagination": {
|
|
39
|
+
"total": "共 {{total}} 条记录"
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
}
|
|
@@ -0,0 +1,163 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 通用验证工具
|
|
3
|
+
*/
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* 验证并转换整数值
|
|
7
|
+
* @param {*} value - 要验证的值
|
|
8
|
+
* @param {string} fieldName - 字段名称,用于错误信息
|
|
9
|
+
* @param {Object} options - 验证选项
|
|
10
|
+
* @param {number} options.min - 最小值
|
|
11
|
+
* @param {number} options.max - 最大值
|
|
12
|
+
* @param {boolean} options.required - 是否必填
|
|
13
|
+
* @returns {number|undefined} 验证后的整数值
|
|
14
|
+
*/
|
|
15
|
+
const validateInteger = (value, fieldName = 'value', options = {}) => {
|
|
16
|
+
const { min = Number.MIN_SAFE_INTEGER, max = Number.MAX_SAFE_INTEGER, required = false } = options
|
|
17
|
+
|
|
18
|
+
// 如果值为空或未定义
|
|
19
|
+
if (value === undefined || value === null || value === '') {
|
|
20
|
+
if (required) {
|
|
21
|
+
throw new Error(`${fieldName}是必填字段`)
|
|
22
|
+
}
|
|
23
|
+
return undefined
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
let numericValue = value
|
|
27
|
+
|
|
28
|
+
// 如果是字符串,尝试转换为数字
|
|
29
|
+
if (typeof value === 'string') {
|
|
30
|
+
numericValue = parseInt(value.trim(), 10)
|
|
31
|
+
if (isNaN(numericValue)) {
|
|
32
|
+
throw new Error(`${fieldName}必须是数字,收到的值: "${value}"`)
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
// 验证是否为整数
|
|
37
|
+
if (!Number.isInteger(numericValue)) {
|
|
38
|
+
throw new Error(`${fieldName}必须是整数,收到的值: ${value}`)
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
// 验证范围
|
|
42
|
+
if (numericValue < min || numericValue > max) {
|
|
43
|
+
throw new Error(`${fieldName}必须在${min}-${max}之间,收到的值: ${value}`)
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
return numericValue
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* 验证并转换浮点数值
|
|
51
|
+
* @param {*} value - 要验证的值
|
|
52
|
+
* @param {string} fieldName - 字段名称,用于错误信息
|
|
53
|
+
* @param {Object} options - 验证选项
|
|
54
|
+
* @param {number} options.min - 最小值
|
|
55
|
+
* @param {number} options.max - 最大值
|
|
56
|
+
* @param {boolean} options.required - 是否必填
|
|
57
|
+
* @returns {number|undefined} 验证后的浮点数值
|
|
58
|
+
*/
|
|
59
|
+
const validateFloat = (value, fieldName = 'value', options = {}) => {
|
|
60
|
+
const { min = Number.MIN_SAFE_INTEGER, max = Number.MAX_SAFE_INTEGER, required = false } = options
|
|
61
|
+
|
|
62
|
+
// 如果值为空或未定义
|
|
63
|
+
if (value === undefined || value === null || value === '') {
|
|
64
|
+
if (required) {
|
|
65
|
+
throw new Error(`${fieldName}是必填字段`)
|
|
66
|
+
}
|
|
67
|
+
return undefined
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
let numericValue = value
|
|
71
|
+
|
|
72
|
+
// 如果是字符串,尝试转换为数字
|
|
73
|
+
if (typeof value === 'string') {
|
|
74
|
+
numericValue = parseFloat(value.trim())
|
|
75
|
+
if (isNaN(numericValue)) {
|
|
76
|
+
throw new Error(`${fieldName}必须是数字,收到的值: "${value}"`)
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
// 验证是否为有效数字
|
|
81
|
+
if (!Number.isFinite(numericValue)) {
|
|
82
|
+
throw new Error(`${fieldName}必须是有效数字,收到的值: ${value}`)
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
// 验证范围
|
|
86
|
+
if (numericValue < min || numericValue > max) {
|
|
87
|
+
throw new Error(`${fieldName}必须在${min}-${max}之间,收到的值: ${value}`)
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
return numericValue
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
/**
|
|
94
|
+
* 验证字符串
|
|
95
|
+
* @param {*} value - 要验证的值
|
|
96
|
+
* @param {string} fieldName - 字段名称,用于错误信息
|
|
97
|
+
* @param {Object} options - 验证选项
|
|
98
|
+
* @param {number} options.minLength - 最小长度
|
|
99
|
+
* @param {number} options.maxLength - 最大长度
|
|
100
|
+
* @param {boolean} options.required - 是否必填
|
|
101
|
+
* @param {RegExp} options.pattern - 正则表达式模式
|
|
102
|
+
* @returns {string|undefined} 验证后的字符串值
|
|
103
|
+
*/
|
|
104
|
+
const validateString = (value, fieldName = 'value', options = {}) => {
|
|
105
|
+
const { minLength = 0, maxLength = Infinity, required = false, pattern } = options
|
|
106
|
+
|
|
107
|
+
// 如果值为空或未定义
|
|
108
|
+
if (value === undefined || value === null || value === '') {
|
|
109
|
+
if (required) {
|
|
110
|
+
throw new Error(`${fieldName}是必填字段`)
|
|
111
|
+
}
|
|
112
|
+
return undefined
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
const stringValue = String(value).trim()
|
|
116
|
+
|
|
117
|
+
// 验证长度
|
|
118
|
+
if (stringValue.length < minLength) {
|
|
119
|
+
throw new Error(`${fieldName}长度不能少于${minLength}个字符`)
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
if (stringValue.length > maxLength) {
|
|
123
|
+
throw new Error(`${fieldName}长度不能超过${maxLength}个字符`)
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
// 验证正则表达式
|
|
127
|
+
if (pattern && !pattern.test(stringValue)) {
|
|
128
|
+
throw new Error(`${fieldName}格式不正确`)
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
return stringValue
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
/**
|
|
135
|
+
* 验证分页参数
|
|
136
|
+
* @param {*} page - 页码
|
|
137
|
+
* @param {*} pageSize - 页面大小
|
|
138
|
+
* @returns {Object} 验证后的分页参数
|
|
139
|
+
*/
|
|
140
|
+
const validatePagination = (page, pageSize) => {
|
|
141
|
+
const validPage = validateInteger(page, 'page', { min: 0, max: 999999 }) || 0
|
|
142
|
+
const validPageSize = validateInteger(pageSize, 'pageSize', { min: 1, max: 100 }) || 10
|
|
143
|
+
|
|
144
|
+
return { page: validPage, pageSize: validPageSize }
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
/**
|
|
148
|
+
* 验证 ID 参数
|
|
149
|
+
* @param {*} id - ID值
|
|
150
|
+
* @param {string} fieldName - 字段名称
|
|
151
|
+
* @returns {number} 验证后的ID
|
|
152
|
+
*/
|
|
153
|
+
const validateId = (id, fieldName = 'ID') => {
|
|
154
|
+
return validateInteger(id, fieldName, { min: 1, required: true })
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
module.exports = {
|
|
158
|
+
validateInteger,
|
|
159
|
+
validateFloat,
|
|
160
|
+
validateString,
|
|
161
|
+
validatePagination,
|
|
162
|
+
validateId
|
|
163
|
+
}
|