Compare commits

...

20 Commits

Author SHA1 Message Date
Lyda f4d8dd91b4 docs: 在 JS/TS 基础规范的魔法数字检查规则中补充数量类型数字无需抽离的说明 2026-04-29 10:12:10 +08:00
Lyda 8ac6f10679 docs: 优化 JS/TS 基础规范中复杂逻辑注释规则的表述,将"超过 2 个"改为"大于等于 3 个"以更准确描述判断条件 2026-04-29 10:09:22 +08:00
Lyda 33fe74cb35 docs: 补充规则明细图表 2026-04-27 19:15:37 +08:00
Lyda 1e365bd99e feat: 在 JS/TS 基础规范的变量命名规则中补充私有属性可使用下划线开头的说明 2026-04-21 14:27:21 +08:00
Lyda 3ed06a5e6d docs: 在 JS/TS 基础规范的魔法数字检查规则中补充长度和高度作为可理解字面量的示例 2026-04-14 16:25:34 +08:00
Lyda ed66b1b256 feat: 在 JS/TS 基础规范的代码行数、函数长度和复杂逻辑注释规则示例中添加 includes 标记 2026-04-13 14:37:05 +08:00
Lyda f34b31f542 docs: 统一规范文档示例格式,使用三级标题 Example 和四级标题 Good/Bad 展示代码示例 2026-04-13 13:00:57 +08:00
Lyda dae54e90b6 feat: 在 JS/TS 基础规范中优化魔法数字检查规则,添加可理解字面量的判断说明并更新示例代码 2026-04-13 10:51:27 +08:00
Lyda fc6a0174b9 feat: 更新 JS/TS 基础规范,将魔法字符串检查规则重命名为仅检查魔法数字,并提升常量定义位置规则严重级别至 error,同时补充 constants 文件命名规则说明 2026-04-08 15:52:28 +08:00
Lyda 041b02c793 feat: 更新 JS/TS 基础规范中的命名规则标识符,并允许变量使用蛇形命名 2026-04-02 14:16:58 +08:00
liuhuan 89cc7d9152 feat: 更新 skills 2026-03-04 11:28:59 +08:00
Lyda 6a5006077b feat: 在 JS/TS 基础规范和 NestJS 规范中添加常量定义位置规则,要求常量放在对应模块的 constants 文件中 2026-03-04 10:52:17 +08:00
liuhuan ea4f4d41c8 更新 references/js.models.md 2026-03-03 14:06:26 +08:00
Lyda fb3962accd docs: 完善 README 文档,添加规范索引、接入步骤和使用说明 2026-03-02 10:37:04 +08:00
Lyda f6f87e0c47 feat: 在 NestJS 规范中添加注解和装饰器静态值的魔法值检查豁免说明 2026-02-04 18:37:33 +08:00
Lyda 74e796fe61 feat: 在 JS/TS 基础规范中统一严重级别格式,并添加复杂逻辑和函数注释规则 2026-02-04 10:13:42 +08:00
Lyda a6ee653388 feat: 在 mongoose 模型规范中添加覆盖基础规范的说明 2026-02-03 13:41:31 +08:00
Lyda 1f2abc7507 feat: 在 JS/TS 基础规范中添加严重级别标识和魔法字面量检查范围说明 2026-02-03 11:57:19 +08:00
Lyda 30ec00df9e feat: 在 NestJS 规范中添加 Model 文件匹配模式说明 2026-02-02 11:21:10 +08:00
Lyda 01049bc24a refactor: 更新 mongoose 模型规范中的文件匹配模式,支持多级目录结构 2026-01-31 19:21:43 +08:00
9 changed files with 455 additions and 106 deletions
+165 -2
View File
@@ -1,3 +1,166 @@
# Review Spec # Code Spec
该仓库是小管家代码规范仓库,规范基于 Gitea Flows Review Spec 协议编写。 该仓库是小管家代码规范仓库,规范基于 spaceflow [Review Spec](https://lydanne.github.io/spaceflow/reference/review-spec.html) 协议编写。
## 目标
- 统一 JS/TS、NestJS、Mongoose Model、Vue 的代码风格与结构约束。
- 提供可执行、可审查、可扩展的规则定义(含规则 ID、Good/Bad 示例、覆盖关系)。
- 为自动化 Review 与人工 Code Review 提供统一判断标准。
## 目录结构
```txt
.
├── README.md
└── references/
├── js&ts.base.md
├── js&ts.file-name.md
├── js&ts.nest.md
├── js&ts.test-code.md
├── js.models.md
├── vue.base.md
└── vue.file-name.md
```
## 接入步骤(`.spaceflowrc`
1. 在业务仓库根目录创建或修改 `.spaceflowrc`
2.`review.references` 中引入本仓库 `references` 地址。
3. 根据项目需要配置 `includes`、注释策略和重试策略。
```json
{
"review": {
"references": ["https://git.bjxgj.com/xgj-pub/code-spec/src/branch/main/references"],
"includes": [
"**/*.ts",
"**/*.js",
"!nest-src/errcode.ts",
"!nest-src/libs/entity/**",
"!**/dist/**",
"!**/*.spec.*",
"!**/*.config.*"
],
"generateDescription": true,
"lineComments": true,
"verifyFixes": true,
"autoUpdatePrTitle": true,
"analyzeDeletions": false,
"deletionAnalysisMode": "open-code",
"concurrency": 1,
"retries": 3,
"retryDelay": 1000
}
}
```
> 说明:如果你的 `.spaceflowrc` 已有其他配置,请仅合并 `review` 字段,不要覆盖现有配置。
### MCP 配置(spaceflow
如果你需要在支持 MCP 的客户端中接入 spaceflow,可加入以下配置:
```json
{
"mcpServers": {
"spaceflow": {
"args": [
"-y",
"@spaceflow/cli",
"mcp"
],
"command": "npx",
"disabled": false
}
}
}
```
然后我们就可以使用这样的提示词让AI去拉规则了.
```
请使用 spaceflow 工具去 review 代码。
```
## 规范索引
| 规范集 | 规则 ID 前缀 | 作用范围(includes | 说明 |
| --- | --- | --- | --- |
| JS/TS 基础规范 | `JsTs.Base` | 通用 JS/TS 文件 | 命名、复杂度、行数、魔法值等基础约束 |
| JS/TS 文件命名规范 | `JsTs.FileName` | 通用 JS/TS 文件 | class/interface 与函数文件命名规则 |
| NestJS 规范 | `JsTs.Nest` | `*.controller.ts` `*.service.ts` `*.module.ts` `*.dto.ts` `*.pipe.ts` `*.guard.ts` `*.interceptor.ts` `*.filter.ts` `*.exception-filter.ts` `*.proxy.ts` `*.model.ts` | 目录结构、分层职责、文件命名与模块组织 |
| 测试代码规范 | `JsTs.TestCode` | 测试文件(`.test.js` `.test.ts` `.spec.ts` | 测试文件命名与 `describe/it` 结构约束 |
| Mongoose Model 规范 | `Js.Model` | `*/models/*.js` | schema 字段、索引、钩子、方法、引用关系等 |
| Vue 基础规范 | `Vue.Base` | `*.vue` | 自定义组件命名规范 |
| Vue 文件命名规范 | `Vue.FileName` | `*.vue` | 组件文件命名规范 |
## 规则明细图表
| 规范集 | 规则 ID | 规则说明 | 文档 |
| --- | --- | --- | --- |
| JsTs.Base | `JsTs.Base.ConstUpperCase` | 常量名使用大写加下划线命名(UPPER_CASE),单词间以下划线分隔 | [js&ts.base.md](references/js&ts.base.md) |
| JsTs.Base | `JsTs.Base.FuncLowerCamel` | 函数名使用小驼峰命名 | [js&ts.base.md](references/js&ts.base.md) |
| JsTs.Base | `JsTs.Base.NoMagicVar` | 禁止使用字面量魔法数字 | [js&ts.base.md](references/js&ts.base.md) |
| JsTs.Base | `JsTs.Base.ConstantsDefinition` | 基于 JsTs.Base.NoMagicVar 抽离的静态常量需要放在对应文件里 | [js&ts.base.md](references/js&ts.base.md) |
| JsTs.Base | `JsTs.Base.ClassNaming` | class 和 interface 命名使用大驼峰命名 | [js&ts.base.md](references/js&ts.base.md) |
| JsTs.Base | `JsTs.Base.VarNaming` | 变量名使用小驼峰或者蛇形命名 | [js&ts.base.md](references/js&ts.base.md) |
| JsTs.Base | `JsTs.Base.CodeNotMoreThan700Lines` | 单文件代码不超过 700 行 | [js&ts.base.md](references/js&ts.base.md) |
| JsTs.Base | `JsTs.Base.FuncNotMoreThan200Lines` | 单个函数或方法不能超出 200 行 | [js&ts.base.md](references/js&ts.base.md) |
| JsTs.Base | `JsTs.Base.ComplexLogic` | 复杂的逻辑判断要添加注释 | [js&ts.base.md](references/js&ts.base.md) |
| JsTs.Base | `JsTs.Base.ComplexFunc` | 复杂的函数要添加注释 | [js&ts.base.md](references/js&ts.base.md) |
| JsTs.FileName | `JsTs.FileName.UpperCamel` | class 和 interface 文件使用大驼峰命名 | [js&ts.file-name.md](references/js&ts.file-name.md) |
| JsTs.FileName | `JsTs.FileName.LowerCamel` | 函数文件使用小驼峰命名 | [js&ts.file-name.md](references/js&ts.file-name.md) |
| JsTs.Nest | `JsTs.Nest.DirStructure` | 目录框架规范 | [js&ts.nest.md](references/js&ts.nest.md) |
| JsTs.Nest | `JsTs.Nest.ControllerDefinition` | 控制器命名规范 | [js&ts.nest.md](references/js&ts.nest.md) |
| JsTs.Nest | `JsTs.Nest.ServiceDefinition` | 服务命名规范 | [js&ts.nest.md](references/js&ts.nest.md) |
| JsTs.Nest | `JsTs.Nest.ModuleDefinition` | 模块命名规范 | [js&ts.nest.md](references/js&ts.nest.md) |
| JsTs.Nest | `JsTs.Nest.DtoDefinition` | Dto 命名规范 | [js&ts.nest.md](references/js&ts.nest.md) |
| JsTs.Nest | `JsTs.Nest.ProxyDefinition` | Proxy 编写规范 | [js&ts.nest.md](references/js&ts.nest.md) |
| JsTs.Nest | `JsTs.Nest.ModelDefinition` | Model 编写规范 | [js&ts.nest.md](references/js&ts.nest.md) |
| JsTs.Nest | `JsTs.Nest.BusinessDefinition` | 业务代码编写规范 | [js&ts.nest.md](references/js&ts.nest.md) |
| JsTs.Nest | `JsTs.Nest.ConstantsDefinition` | 基于 JsTs.Base.NoMagicStringsAndNumbers 抽离的静态常量需要放在对应文件里 | [js&ts.nest.md](references/js&ts.nest.md) |
| JsTs.TestCode | `JsTs.TestCode.FileName` | 测试文件命名 | [js&ts.test-code.md](references/js&ts.test-code.md) |
| JsTs.TestCode | `JsTs.TestCode.BlockName` | 测试代码块命名 | [js&ts.test-code.md](references/js&ts.test-code.md) |
| Js.Model | `Js.Model.FileName` | 模型文件命名规范 | [js.models.md](references/js.models.md) |
| Js.Model | `Js.Model.FieldName` | Schema 字段命名规范 | [js.models.md](references/js.models.md) |
| Js.Model | `Js.Model.SchemaDefinition` | Schema 定义规范 | [js.models.md](references/js.models.md) |
| Js.Model | `Js.Model.IndexDefinition` | 索引定义规范 | [js.models.md](references/js.models.md) |
| Js.Model | `Js.Model.VirtualField` | 虚拟字段规范 | [js.models.md](references/js.models.md) |
| Js.Model | `Js.Model.Middleware` | 中间件/钩子规范 | [js.models.md](references/js.models.md) |
| Js.Model | `Js.Model.StaticMethod` | 静态方法规范 | [js.models.md](references/js.models.md) |
| Js.Model | `Js.Model.InstanceMethod` | 实例方法规范 | [js.models.md](references/js.models.md) |
| Js.Model | `Js.Model.Reference` | 关联引用规范 | [js.models.md](references/js.models.md) |
| Js.Model | `Js.Model.FieldType` | 必须写明字段的类型 | [js.models.md](references/js.models.md) |
| Vue.Base | `Vue.Base.CustomComponentName` | Vue 自定义组件命名规则 | [vue.base.md](references/vue.base.md) |
| Vue.FileName | `Vue.FileName.UpperCamel` | Vue 组件文件使用大驼峰命名 | [vue.file-name.md](references/vue.file-name.md) |
## 规则覆盖关系(override
当多个规范同时命中同一文件时,按以下覆盖关系处理冲突:
1. `JsTs.Nest` 覆盖 `JsTs.FileName`
2. `JsTs.Nest.DtoDefinition``JsTs.Base.NoMagicStringsAndNumbers` 做规则级覆盖。
3. `Js.Model` 覆盖 `JsTs.Base`
4. `Js.Model.FileName` 覆盖 `JsTs.FileName`
> 建议:在实现自动化检查时,先按 `includes` 过滤命中文件,再按 `override` 解析最终生效规则。
## 使用建议
1. **按文件类型匹配规范集**:先判断文件路径与后缀,再应用对应规则。
2. **输出规则 ID**:Review 结果中保留规则 ID(如 `JsTs.Base.FuncLowerCamel`),便于追踪和整改。
3. **先基础后专项**:优先接入 `JsTs.Base``JsTs.FileName`,再逐步接入 Nest / Model / Vue / Test 专项规则。
4. **保持示例驱动**:新增规则时提供清晰的 Good/Bad 示例,降低理解成本。
## 维护约定
新增或修改规则时建议遵循以下格式:
- 一级标题:规范名称 + 规则前缀(如 ``[JsTs.Base]``
- 二级标题:单条规则描述 + 完整规则 ID(如 ``[JsTs.Base.ConstUpperCase]``
- 元信息:`includes` / `override` / `severity`(如适用)
- 示例:使用 `### Example:` 分组,`#### Good:` 展示推荐做法,`#### Bad:` 展示不推荐做法
这样可以保证规则文档在人工阅读和自动化解析两种场景下都保持一致性。
+16 -12
View File
@@ -1,5 +1,5 @@
--- ---
name: 代码规范技能 name: code-review
description: 当用户要求重构、审查或编写代码时,请参考此规范。 description: 当用户要求重构、审查或编写代码时,请参考此规范。
metadata: metadata:
spaceflow: true spaceflow: true
@@ -7,26 +7,26 @@ metadata:
## 功能 ## 功能
- 自动同步最新的代码规范 - 检查代码是否符合规范
- 自动检查代码是否符合规范
- 自动修复代码
## 代码规范
在 references 目录下
## 命令 ## 命令
### 同步最新代码规范 ### 同步最新代码规范
```bash ```bash
npx spaceflow install pnpm spaceflow install
```
### 审查当前未提交的代码
```bash
pnpm spaceflow review
``` ```
### 审查一个文件 ### 审查一个文件
```bash ```bash
npx spaceflow review -b main --head develop -f $CODE_PATH pnpm spaceflow review -b main --head develop -f $CODE_PATH
``` ```
- `$CODE_PATH`:需要检查的文件路径 - `$CODE_PATH`:需要检查的文件路径
@@ -36,7 +36,7 @@ npx spaceflow review -b main --head develop -f $CODE_PATH
### 审查一个Commit ### 审查一个Commit
```bash ```bash
npx spaceflow review -b main --head develop --commits $COMMIT_ID pnpm spaceflow review -b main --head develop --commits $COMMIT_ID
``` ```
- `$COMMIT_ID`:需要检查的Commit ID,可以是多个空格隔开 - `$COMMIT_ID`:需要检查的Commit ID,可以是多个空格隔开
@@ -46,7 +46,7 @@ npx spaceflow review -b main --head develop --commits $COMMIT_ID
### 审查两个分支的差异代码 ### 审查两个分支的差异代码
```bash ```bash
npx spaceflow review -b main --head develop pnpm spaceflow review -b main --head develop
``` ```
- `-b main`:指定基准分支 - `-b main`:指定基准分支
@@ -54,6 +54,10 @@ npx spaceflow review -b main --head develop
## 使用场景 ## 使用场景
### 当用户要求审查当前代码
首先需要同步最新的代码规范,然后直接执行上面的命令。
### 当用户要求审查代码时 ### 当用户要求审查代码时
首先需要同步最新的代码规范,然后用户有没有指定审查的文件路径,如果有则审查文件,否则审查两个分支的差异代码。 首先需要同步最新的代码规范,然后用户有没有指定审查的文件路径,如果有则审查文件,否则审查两个分支的差异代码。
+144 -41
View File
@@ -5,22 +5,29 @@
## 常量名使用大写加下划线命名(UPPER_CASE),单词间以下划线分隔 `[JsTs.Base.ConstUpperCase]` ## 常量名使用大写加下划线命名(UPPER_CASE),单词间以下划线分隔 `[JsTs.Base.ConstUpperCase]`
- 不检查 nodejs 的导包定义,比如 `const fs = require("fs")` - 不检查 nodejs 的导包定义,比如 `const fs = require("fs")`
- 常量检查只需检查 `const` 声明的静态值,但是不包含对象和函数
### Good ### Example: 常量命名
#### Good: 使用大写加下划线
```javascript ```javascript
const MAX_COUNT = 100; const ROLE_ADMIN = 1;
``` ```
### Bad #### Bad: 使用小驼峰
```javascript ```javascript
const maxCount = 100; const roleAdmin = 1;
``` ```
## 函数名使用小驼峰命名 `[JsTs.Base.FuncLowerCamel]` ## 函数名使用小驼峰命名 `[JsTs.Base.FuncLowerCamel]`
### Good > - severity `warn`
### Example: 函数命名
#### Good: 使用小驼峰
```javascript ```javascript
function getUserInfo() { function getUserInfo() {
@@ -28,7 +35,7 @@ function getUserInfo() {
} }
``` ```
### Bad #### Bad: 使用全小写
```javascript ```javascript
function getuserinfo() { function getuserinfo() {
@@ -36,40 +43,66 @@ function getuserinfo() {
} }
``` ```
## 禁止使用字面量魔法字符串和魔法数字 `[JsTs.Base.NoMagicStringsAndNumbers]` ## 禁止使用字面量魔法数字 `[JsTs.Base.NoMagicVar]`
- 只检查数字字面量和字符串字面量,不要检查其他(比如 布尔字面量) > - severity `warn`
- 无需检查单词是否完整拼写
- throw 的错误信息无需审查
- new Error 的错误信息无需审查
- console.log 的打印代码无需审查
- console.error 的错误信息无需审查
- console.warn 的错误信息无需审查
- console.info 的错误信息无需审查
- console.debug 的错误信息无需审查
- console.trace 的错误信息无需审查
- 无需考虑类型是否合理匹配
### Good - 仅检查**数字字面量**和**正则字面量**,不检查布尔、对象、函数、数组、字符串字面量
- 仅检查含义不明确的数字,如 `0``1``2` 等;
- `throw` / `new Error` 的错误信息无需审查
- `console.*``log` / `error` / `warn` / `info` / `debug` / `trace`)的内容无需审查
- 语义自明的数量类数字无需抽取常量,例如:时间戳、毫秒时长、元素数量、尺寸等一眼可理解的值
### Example: 魔法数字
#### Good: 使用常量替代魔法数字
```javascript ```javascript
const MAX_COUNT = 100; const ROLE_ADMIN = 1;
const USER_STATUS = {
ACTIVE: "active", if (user.role === ROLE_ADMIN) {
INACTIVE: "inactive", // ...
}; }
``` ```
### Bad #### Bad: 使用字面量魔法数字
```javascript ```javascript
const maxCount = 100; if (user.role === 1) {
const userStatus = "active"; // ...
}
``` ```
## class 和 interface 命名使用大驼峰命名 `[JsTs.Base.ClassUpperCamel]` ## 基于 JsTs.Base.NoMagicVar 抽离的静态常量需要放在对应文件里 `[JsTs.Base.ConstantsDefinition]`
### Good > - severity `error`
- 需要放在指定模块的 constants 文件里
- constants 命名规则: user.constants.js 或者 user.constants.ts
### Example: 常量定义位置
#### Good: 常量放在对应模块的 constants 文件
```javascript
// user.constants.js
const ROLE_ADMIN = 1; // 这是 user 模块需要的
```
#### Bad: 常量放在错误模块的 constants 文件
```javascript
// class.constants.js
const ROLE_ADMIN = 1; // 这是 user 模块需要的
```
## class 和 interface 命名使用大驼峰命名 `[JsTs.Base.ClassNaming]`
> - severity `warn`
### Example: 类和接口命名
#### Good: 使用大驼峰
```javascript ```javascript
class UserInfo { class UserInfo {
@@ -77,7 +110,7 @@ class UserInfo {
} }
``` ```
### Bad #### Bad: 使用全小写
```javascript ```javascript
class userinfo { class userinfo {
@@ -85,48 +118,118 @@ class userinfo {
} }
``` ```
## 变量名使用小驼峰命名 `[JsTs.Base.VarLowerCamel]` ## 变量名使用小驼峰或者蛇形命名 `[JsTs.Base.VarNaming]`
### Good > - severity `warn`
- 需要注意的是从 require 导入的变量不受检查
- 私有属性可以使用 `_` 开头,比如 `this._fromFeatureRecommendEntry`
### Example: 变量命名
#### Good: 使用小驼峰或蛇形命名
```javascript ```javascript
let userName = "John"; let userName = "John";
let user_name = "John";
``` ```
### Bad #### Bad: 使用大驼峰
```javascript ```javascript
let username = "John"; let Username = "John";
``` ```
## 单文件代码不超过 700 行 `[JsTs.Base.CodeNotMoreThan700Lines]` ## 单文件代码不超过 700 行 `[JsTs.Base.CodeNotMoreThan700Lines]`
### Good > - includes `added|*`
### Example: 文件行数
#### Good: 代码不超过 700 行
```javascript ```javascript
// 代码不超过 700 行 // 代码不超过 700 行
``` ```
### Bad #### Bad: 代码超过 700 行
```javascript ```javascript
// 代码超过 700 行 // 代码超过 700 行
``` ```
## 单个函数或方法不能超出 200 行 `[JsTs.Base.FuncNotMoreThan200Lines]` ## 单个函数或方法不能超出 300 行 `[JsTs.Base.FuncNotMoreThan300Lines]`
### Good ### Example: 函数行数
#### Good: 函数不超过 300 行
```javascript ```javascript
function getUserInfo() { function getUserInfo() {
// ... 小于等于 200 // ... 小于等于 300
} }
``` ```
### Bad #### Bad: 函数超过 300 行
> - includes `added|*`
```javascript ```javascript
function getUserInfo() { function getUserInfo() {
// ... 大于 200 // ... 大于 300
}
```
## 复杂的逻辑判断要添加注释 `[JsTs.Base.ComplexLogic]`
> - severity `warn`
- 逻辑判断的复杂度大于等于 3 个的要添加注释
### Example: 复杂逻辑注释
#### Good: 复杂逻辑添加注释
```javascript
// 逻辑判断复杂度大于等于 3 个
if (a && b || c) {
// ...
}
```
#### Bad: 复杂逻辑未添加注释
```javascript
if (a && b && c && d) {
// ...
}
```
## 复杂的函数要添加注释 `[JsTs.Base.ComplexFunc]`
> - severity `warn`
### Example: 复杂函数注释
#### Good: 复杂函数添加注释
> - includes `added|*`
```javascript
/**
* 复杂的算法逻辑
*/
function complexFunc() {
// ...
}
```
#### Bad: 复杂函数未添加注释
> - includes `added|*`
```javascript
function complexFunc() {
// ...
} }
``` ```
+8 -4
View File
@@ -7,7 +7,9 @@
- 文件名必须与主导类或接口名称完全一致。 - 文件名必须与主导类或接口名称完全一致。
- 适用于定义单一主要实体的文件。 - 适用于定义单一主要实体的文件。
### Good ### Example: class 和 interface 文件命名
#### Good: 使用大驼峰命名
```javascript ```javascript
// UserInfo.js // UserInfo.js
@@ -16,7 +18,7 @@ class UserInfo {
} }
``` ```
### Bad #### Bad: 使用全小写命名
```javascript ```javascript
// userinfo.js // userinfo.js
@@ -30,7 +32,9 @@ class userinfo {
- 适用于导出一个或多个工具函数的文件。 - 适用于导出一个或多个工具函数的文件。
- 文件名应反映其包含的核心功能。 - 文件名应反映其包含的核心功能。
### Good ### Example: 函数文件命名
#### Good: 使用小驼峰命名
```javascript ```javascript
// getUserInfo.js // getUserInfo.js
@@ -39,7 +43,7 @@ function getUserInfo() {
} }
``` ```
### Bad #### Bad: 使用全小写命名
```javascript ```javascript
// getuserinfo.js // getuserinfo.js
+61 -17
View File
@@ -1,6 +1,6 @@
# Nestjs 项目下的规范 `[JsTs.Nest]` # Nestjs 项目下的规范 `[JsTs.Nest]`
> - includes `*.controller.ts` `*.service.ts` `*.module.ts` `*.dto.ts` `*.pipe.ts` `*.guard.ts` `*.interceptor.ts` `*.filter.ts` `*.exception-filter.ts` `*.proxy.ts` `*.model.ts` > - includes `*.controller.ts` `*.service.ts` `*.module.ts` `*.dto.ts` `*.pipe.ts` `*.guard.ts` `*.interceptor.ts` `*.filter.ts` `*.exception-filter.ts` `*.proxy.ts` `*.model.ts` `*.constants.ts`
> - override `[JsTs.FileName]` > - override `[JsTs.FileName]`
## 目录框架规范 `[JsTs.Nest.DirStructure]` ## 目录框架规范 `[JsTs.Nest.DirStructure]`
@@ -16,7 +16,9 @@
- 每个模块的目录下可以包含 `interceptor` 目录,用于存放拦截器 - 每个模块的目录下可以包含 `interceptor` 目录,用于存放拦截器
- 每个模块的目录下可以包含 `filter` 目录,用于存放异常过滤器 - 每个模块的目录下可以包含 `filter` 目录,用于存放异常过滤器
### Good ### Example: 目录结构
#### Good: 按模块组织的目录结构
```txt ```txt
src/ src/
@@ -43,7 +45,7 @@ src/
└── main.ts # 应用入口 └── main.ts # 应用入口
``` ```
### Bad #### Bad: 扁平化的目录结构
```txt ```txt
src/ src/
@@ -61,14 +63,17 @@ src/
- 该文件不能写业务逻辑,只能写调用 service 的代码 - 该文件不能写业务逻辑,只能写调用 service 的代码
- 文件名使用小写加横线命名(如 `user-extends.controller.ts` - 文件名使用小写加横线命名(如 `user-extends.controller.ts`
- 文件名必须加 `.controller.ts` 后缀 - 文件名必须加 `.controller.ts` 后缀
- 注解和装饰器上的静态值无需进行魔法值的提炼 `[JsTs.Base.NoMagicStringsAndNumbers]`
### Good ### Example: 控制器文件命名
#### Good: 使用小写加横线命名
```txt ```txt
user-extends.controller.ts user-extends.controller.ts
``` ```
### Bad #### Bad: 使用大驼峰命名
```txt ```txt
userController.ts userController.ts
@@ -82,13 +87,15 @@ userController.ts
- 文件名使用小写加横线命名(如 `user-extends.service.ts` - 文件名使用小写加横线命名(如 `user-extends.service.ts`
- 文件名必须加 `.service.ts` 后缀 - 文件名必须加 `.service.ts` 后缀
### Good ### Example: 服务文件命名
#### Good: 使用小写加横线命名
```txt ```txt
user-extends.service.ts user-extends.service.ts
``` ```
### Bad #### Bad: 使用大驼峰命名
```txt ```txt
userService.ts userService.ts
@@ -99,13 +106,15 @@ userService.ts
- 文件名使用小写加横线命名(如 `user-extends.module.ts` - 文件名使用小写加横线命名(如 `user-extends.module.ts`
- 文件名必须加 `.module.ts` 后缀 - 文件名必须加 `.module.ts` 后缀
### Good ### Example: 模块文件命名
#### Good: 使用小写加横线命名
```txt ```txt
user-extends.module.ts user-extends.module.ts
``` ```
### Bad #### Bad: 使用大驼峰命名
```txt ```txt
userModule.ts userModule.ts
@@ -113,18 +122,22 @@ userModule.ts
## Dto 命名规范 `[JsTs.Nest.DtoDefinition]` ## Dto 命名规范 `[JsTs.Nest.DtoDefinition]`
> - override `[JsTs.Base.NoMagicStringsAndNumbers]`
- 文件名使用小写加横线命名(如 `user-extends.dto.ts` - 文件名使用小写加横线命名(如 `user-extends.dto.ts`
- 文件名必须加 `.dto.ts` 后缀 - 文件名必须加 `.dto.ts` 后缀
- dto 目录下必须包含 `dto.ts` 文件 - dto 目录下必须包含 `dto.ts` 文件
- dto 里的类的属性可以使用小驼峰或者下划线命名 - dto 里的类的属性可以使用小驼峰或者下划线命名
### Good ### Example: Dto 文件命名
#### Good: 使用小写加横线命名
```txt ```txt
user-extends.dto.ts user-extends.dto.ts
``` ```
### Bad #### Bad: 使用大驼峰命名
```txt ```txt
userDto.ts userDto.ts
@@ -138,7 +151,9 @@ userDto.ts
- 内部只能写使用 syncService 调用的逻辑 - 内部只能写使用 syncService 调用的逻辑
- SyncService 只能在 proxy.ts 中使用 - SyncService 只能在 proxy.ts 中使用
### Good ### Example: Proxy 编写
#### Good: Proxy 只使用 SyncService 调用旧业务
```typescript ```typescript
// user.proxy.ts // user.proxy.ts
@@ -156,7 +171,7 @@ export class UserProxy {
} }
``` ```
### Bad #### Bad: Proxy 中直接查询数据库
```typescript ```typescript
// user.proxy.ts // user.proxy.ts
@@ -178,11 +193,15 @@ export class UserProxy {
## Model 编写规范 `[JsTs.Nest.ModelDefinition]` ## Model 编写规范 `[JsTs.Nest.ModelDefinition]`
> - includes `*.model.ts`
- 内部只能写使用 model 数据库调用的逻辑 - 内部只能写使用 model 数据库调用的逻辑
- 文件名使用小写加横线命名(如 `user.model.ts` - 文件名使用小写加横线命名(如 `user.model.ts`
- 文件名必须加 `.model.ts` 后缀 - 文件名必须加 `.model.ts` 后缀
### Good ### Example: Model 编写
#### Good: Model 只使用数据库调用
```typescript ```typescript
// user.model.ts // user.model.ts
@@ -201,7 +220,7 @@ export class UserProxy {
} }
``` ```
### Bad #### Bad: Model 中使用 SyncService 调用旧业务
```typescript ```typescript
// user.model.ts // user.model.ts
@@ -224,7 +243,9 @@ export class UserProxy {
- 目前所有的新代码都应该写在 nest 里 - 目前所有的新代码都应该写在 nest 里
### Good ### Example: 业务代码位置
#### Good: 新代码写在 nest 目录下
```typescript ```typescript
// nest-src/apps/app/src/user/user.controller.ts // nest-src/apps/app/src/user/user.controller.ts
@@ -238,8 +259,31 @@ export class UserProxy {
// nest-src/apps/app/src/user/user.module.ts // nest-src/apps/app/src/user/user.module.ts
``` ```
### Bad #### Bad: 新代码写在旧目录下
```typescript ```typescript
// proxy/user.js // proxy/user.js
``` ```
## 基于 JsTs.Base.NoMagicStringsAndNumbers 抽离的静态常量需要放在对应文件里 `[JsTs.Nest.ConstantsDefinition]`
> - severity `warn`
> - override `[JsTs.Base.ConstantsDefinition]`
- 需要放在指定模块的 constants 文件里
### Example: 常量定义位置
#### Good: 常量放在对应模块的 constants 文件
```typescript
// user.constants.ts
const MAX_COUNT = 100; // 这是 user 模块需要的
```
#### Bad: 常量放在错误模块的 constants 文件
```typescript
// class.constants.ts
const MAX_COUNT = 100; // 这是 user 模块需要的
```
+8 -4
View File
@@ -7,7 +7,9 @@
- 必须以 `.test.js``.test.ts`(或 `.spec.ts`)结尾。 - 必须以 `.test.js``.test.ts`(或 `.spec.ts`)结尾。
- 前缀部分应与被测试源文件名保持一致。 - 前缀部分应与被测试源文件名保持一致。
### Good ### Example: 测试文件命名
#### Good: 测试文件名与源文件名一致
```javascript ```javascript
// userInfo.js // userInfo.js
@@ -17,7 +19,7 @@ describe("UserInfo", () => {
}); });
``` ```
### Bad #### Bad: 测试文件名与源文件名不一致
```javascript ```javascript
// userInfo.js // userInfo.js
@@ -32,7 +34,9 @@ describe("userinfo", () => {
- 测试代码命名结构:`describe(文件名)` -> `describe(函数名/类名.方法名)` -> `it(场景描述)` - 测试代码命名结构:`describe(文件名)` -> `describe(函数名/类名.方法名)` -> `it(场景描述)`
- 场景描述应使用 "should ..." 格式,描述预期行为。 - 场景描述应使用 "should ..." 格式,描述预期行为。
### Good ### Example: 测试代码块命名
#### Good: 使用 describe(文件名) -> describe(函数名/类名.方法名) -> it(场景描述)
```javascript ```javascript
// uUerInfo.js // uUerInfo.js
@@ -68,7 +72,7 @@ describe("userInfo", () => {
}); });
``` ```
### Bad #### Bad: 缺少 describe(函数名/类名.方法名) 层级
```javascript ```javascript
// userInfo.js // userInfo.js
+45 -22
View File
@@ -1,13 +1,18 @@
# mongoose 数据库模型 JS 规范 `[Js.Model]` # mongoose 数据库模型 JS 规范 `[Js.Model]`
> - includes `models/*.js` > - includes `*/models/*.js`
> - override `[JsTs.Base]`
## 模型文件命名规范 `[Js.Model.FileName]` ## 模型文件命名规范 `[Js.Model.FileName]`
> - override `[JsTs.FileName]`
- 文件名使用小写加下划线命名(如 `user_extends.js`,或者使用小写加横线命名(如 `user-extends.js` - 文件名使用小写加下划线命名(如 `user_extends.js`,或者使用小写加横线命名(如 `user-extends.js`
- 文件名应与模型名称对应 - 文件名应与模型名称对应
### Good ### Example: 模型文件命名
#### Good: 使用小写加下划线或横线命名
```txt ```txt
user.js user.js
@@ -15,7 +20,7 @@ user_extends.js
user-profile.js user-profile.js
``` ```
### Bad #### Bad: 使用大驼峰命名
```txt ```txt
User.js User.js
@@ -30,7 +35,9 @@ UserProfile.js
- 要补充字段注释 - 要补充字段注释
- 要补充字段类型 - 要补充字段类型
### Good ### Example: Schema 字段命名
#### Good: 字段名使用 snake_case
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
@@ -40,7 +47,7 @@ const userSchema = new Schema({
}); });
``` ```
### Bad #### Bad: 字段名使用驼峰命名
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
@@ -56,19 +63,21 @@ const userSchema = new Schema({
- 必要时添加 `required``default` 等属性 - 必要时添加 `required``default` 等属性
- 复杂类型应使用嵌套 Schema 或引用 - 复杂类型应使用嵌套 Schema 或引用
### Good ### Example: Schema 定义
#### Good: 完整的字段定义
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
user_name: { type: String, required: true }, user_name: { type: String, required: true },
email: { type: String, required: true, unique: true }, email: { type: String, required: true },
age: { type: Number, default: 0 }, age: { type: Number, default: 0 },
status: { type: String, enum: ["active", "inactive"], default: "active" }, status: { type: String, enum: ["active", "inactive"], default: "active" },
created_at: { type: Date, default: Date.now }, created_at: { type: Date, default: Date.now },
}); });
``` ```
### Bad #### Bad: 缺少 required/default 等属性
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
@@ -85,7 +94,9 @@ const userSchema = new Schema({
- 需要添加注释说明索引用途 - 需要添加注释说明索引用途
- 不能在 Schema 定义中直接添加索引,添加到索引要注释掉 - 不能在 Schema 定义中直接添加索引,添加到索引要注释掉
### Good ### Example: 索引定义
#### Good: 索引注释掉并添加用途说明
```javascript ```javascript
const orderSchema = new Schema({ const orderSchema = new Schema({
@@ -100,7 +111,7 @@ const orderSchema = new Schema({
// orderSchema.index({ order_no: 1 }, { unique: true }); // orderSchema.index({ order_no: 1 }, { unique: true });
``` ```
### Bad #### Bad: 在 Schema 定义中直接添加索引
```javascript ```javascript
const orderSchema = new Schema({ const orderSchema = new Schema({
@@ -116,7 +127,9 @@ const orderSchema = new Schema({
- 虚拟字段应在 Schema 定义后声明 - 虚拟字段应在 Schema 定义后声明
- 需要添加注释说明虚拟字段用途 - 需要添加注释说明虚拟字段用途
### Good ### Example: 虚拟字段
#### Good: 使用 virtual 定义可计算字段
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
@@ -130,7 +143,7 @@ userSchema.virtual("full_name").get(function () {
}); });
``` ```
### Bad #### Bad: 存储可计算的字段
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
@@ -146,7 +159,9 @@ const userSchema = new Schema({
- 需要添加注释说明中间件用途 - 需要添加注释说明中间件用途
- 避免在中间件中执行耗时操作 - 避免在中间件中执行耗时操作
### Good ### Example: 中间件/钩子
#### Good: 中间件添加注释说明用途
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
@@ -169,7 +184,7 @@ userSchema.pre("save", async function (next) {
}); });
``` ```
### Bad #### Bad: 中间件缺少注释且使用同步方法
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
@@ -189,7 +204,9 @@ userSchema.pre("save", function (next) {
- 静态方法应在 Schema 定义后声明 - 静态方法应在 Schema 定义后声明
- 需要添加注释说明方法用途 - 需要添加注释说明方法用途
### Good ### Example: 静态方法
#### Good: 静态方法使用小驼峰命名并添加注释
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
@@ -208,7 +225,7 @@ userSchema.statics.findActiveUsers = function () {
}; };
``` ```
### Bad #### Bad: 静态方法使用下划线命名且缺少注释
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
@@ -228,7 +245,9 @@ userSchema.statics.find_by_email = function (email) {
- 需要添加注释说明方法用途 - 需要添加注释说明方法用途
- 实例方法内部使用 `this` 访问文档属性 - 实例方法内部使用 `this` 访问文档属性
### Good ### Example: 实例方法
#### Good: 实例方法使用小驼峰命名并添加注释
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
@@ -248,7 +267,7 @@ userSchema.methods.incrementLoginCount = function () {
}; };
``` ```
### Bad #### Bad: 实例方法使用下划线命名且缺少注释
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
@@ -267,7 +286,9 @@ userSchema.methods.compare_password = function (candidatePassword) {
- 必须指定 `ref` 属性 - 必须指定 `ref` 属性
- 需要添加注释说明关联关系 - 需要添加注释说明关联关系
### Good ### Example: 关联引用
#### Good: 引用字段使用 _id 后缀并指定 ref
```javascript ```javascript
const orderSchema = new Schema({ const orderSchema = new Schema({
@@ -278,7 +299,7 @@ const orderSchema = new Schema({
}); });
``` ```
### Bad #### Bad: 引用字段缺少 ref 且命名不规范
```javascript ```javascript
const orderSchema = new Schema({ const orderSchema = new Schema({
@@ -293,7 +314,9 @@ const orderSchema = new Schema({
- 禁止使用简写形式(如 `field: String` - 禁止使用简写形式(如 `field: String`
- 不允许使用 Object 等模糊类型 - 不允许使用 Object 等模糊类型
### Good ### Example: 字段类型定义
#### Good: 字段定义使用对象形式明确指定 type
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
@@ -308,7 +331,7 @@ const userSchema = new Schema({
}); });
``` ```
### Bad #### Bad: 使用简写形式或模糊类型
```javascript ```javascript
const userSchema = new Schema({ const userSchema = new Schema({
+4 -2
View File
@@ -6,7 +6,9 @@
必须使用大驼峰命名并且使用的时候也是,并且至少两个单词。 必须使用大驼峰命名并且使用的时候也是,并且至少两个单词。
### Good ### Example: 自定义组件命名
#### Good: 使用大驼峰且至少两个单词
```vue ```vue
<!-- UserInfo.vue --> <!-- UserInfo.vue -->
@@ -22,7 +24,7 @@ export default {
</script> </script>
``` ```
### Bad #### Bad: 使用全小写或单词不足
```vue ```vue
<!-- userinfo.vue --> <!-- userinfo.vue -->
+4 -2
View File
@@ -4,7 +4,9 @@
## Vue 组件文件使用大驼峰命名 `[Vue.FileName.UpperCamel]` ## Vue 组件文件使用大驼峰命名 `[Vue.FileName.UpperCamel]`
### Good ### Example: Vue 组件文件命名
#### Good: 使用大驼峰命名
```vue ```vue
<!-- UserInfo.vue --> <!-- UserInfo.vue -->
@@ -20,7 +22,7 @@ export default {
</script> </script>
``` ```
### Bad #### Bad: 使用全小写命名
```vue ```vue
<!-- userinfo.vue --> <!-- userinfo.vue -->