利用npm bin创建可执行命令实现项目代码规范自动化

项目仓库:https://github.com/kaqiinono/scripts

安装依赖

代码规范需要用到的依赖

npm install cz-customizable commitizen @commitlint/{cli,config-conventional} husky lint-staged standard-version prettier eslint-config-prettier eslint-plugin-prettier --save-dev

各依赖性的作用

  • @commitlint/{cli,config-conventional} 进行代码提交约束,制定提交规则
  • lint-staged 进行代码格式化和代码格式化校验
  • standard-version 自动提升版本号,打tag,生成changelog
  • commitizen 命令式提交commit,提交代码更直观
  • cz-customizable 可自定义commitizen内容
  • husky 进行提交校验
  • prettier 代码格式化

@commitlint/{cli,config-conventional}

  • .commitlintrc.json
{
  "extends": [ "@commitlint/config-conventional" ],
  "rules": {
    "header-max-length": [
      0,
      "always",
      100
    ],
    "type-enum": [
      2,
      "always",
      [
        "feat",
        "fix",
        "docs",
        "style",
        "refactor",
        "test",
        "revert",
        "perf",
        "chore",
        "conflict",
        "release",
        "merge",
        "repair"
      ]
    ]
  }
}

lint-staged

  • 文件名:.lintstagedrc.json
{
  "{src,apps,packages,libs,test}/**/*..{js,ts,jsx,tsx}": ["eslint --fix"],
  "./**/*.{ts,js,jsx,tsx,json,*rc}": ["prettier --write"]
}

standard-version

  • 文件名:.versionrc.json
{
  "changelogHeader": "# Change Log", // change log title
  "releaseCommitMessageFormat": "release: 发布 v{{currentTag}}",
  "issueUrlFormat": "http://jagile.jd.com/test-manage/jbug/{{id}}",
  "types": [
    {
      "type": "feat",
      "section": "需求列表"
    },
    {
      "type": "fix",
      "section": "Bug修复"
    },
    {
      "type": "perf",
      "section": "优化列表"
    },
    {
      "type": "chore",
      "hidden": true,  // hide==true的提交记录不显示在changelog中
      "section": "构建过程或辅助工具的变动"
    },
    {
      "type": "docs",
      "hidden": true,
      "section": "文档"
    },
    {
      "type": "style",
      "hidden": true,
      "section": "格式(不影响代码运行的变动)"
    },
    {
      "type": "refactor",
      "hidden": true,
      "section": "重构(即不是新增功能,也不是修改bug的代码变动)"
    },
    {
      "type": "test",
      "hidden": true,
      "section": "测试用例"
    },
    {
      "type": "conflict",
      "hidden": true,
      "section": "解决冲突"
    },
    {
      "type": "revert",
      "hidden": true,
      "section": "回退"
    },
    {
      "type": "release",
      "hidden": true,
      "section": "发布"
    },
    {
      "type": "merge",
      "hidden": true,
      "section": "合并"
    },
    {
      "type": "repair",
      "hidden": true,
      "section": "修补"
    }
  ]
}

commitizen、cz-customizable

  • 文件名:.czrc
{
  "path": "cz-customizable"
}
  • 文件名:.cz-config.js
    • 代码提示需要跟代码约束保持一致
// https://github.com/leoforfree/cz-customizable/edit/master/cz-config-EXAMPLE.js
const standard = require('./.versionrc.json');
module.exports = {
  types: standard.types.map(st => ({
    value: st.type,
    name: st.section,
  })),
  scopes: [{ name: 'dm' }, { name: 'ge' }, { name: 'jsf' }],
  allowTicketNumber: false,
  isTicketNumberRequired: false,
  ticketNumberPrefix: 'TICKET-',
  ticketNumberRegExp: '\\d{1,5}',
  messages: {
    type: "Select the type of change that you're committing:",
    scope: '\nDenote the SCOPE of this change (optional):',
    // used if allowCustomScopes is true
    customScope: 'Denote the SCOPE of this change:',
    subject: 'Write a SHORT, IMPERATIVE tense description of the change:\n',
    body: 'Provide a LONGER description of the change (optional). Use "|" to break new line:\n',
    breaking: 'List any BREAKING CHANGES (optional):\n',
    footer: 'List any ISSUES CLOSED by this change (optional). E.g.: #31, #34:\n',
    confirmCommit: 'Are you sure you want to proceed with the commit above?',
  },

  allowCustomScopes: true,
  allowBreakingChanges: ['feat', 'fix'],
  skipQuestions: ['body'],
  subjectLimit: 100,
};

husky

husky install # 安装git hook
# 进行提交校验
npx husky add .husky/prepare-commit-msg "exec < /dev/tty && git cz --hook || true"
npx husky add .husky/pre-commit "npx lint-staged --allow-empty $1"
npx husky add .husky/commit-msg "npx --no-install commitlint --edit $1"

  • .prettierrc
{
  "printWidth": 120,
  "singleQuote": true,
  "trailingComma": "es5",
  "arrowParens": "avoid",
  "endOfLine": "auto",
  "overrides": [
    {
      "files": "*.json",
      "options": {
        "singleQuote": false
      }
    },
    {
      "files": ".*rc",
      "options": {
        "singleQuote": false,
        "parser": "json"
      }
    }
  ]
}

脚本自动化

完整脚本示例

编写脚本

推荐使用shelljs进行shell命令的执行,以兼容windows环境

  • setEnv.js
#!/usr/bin/env node

#!/usr/bin/env node

const path = require('path');
const {excute} = require('../shelljs/excute');
const root = process.cwd();

// npm > 7 否则无法创建script
const {stdout} = excute(`npm --version`, {
    silent: true
});
if (stdout && stdout.split('.')[0] < 7) {
    console.log(`npm版本(${stdout.trim()})过低,需要安装最新版本!`)
    console.log('请输入您的开机密码进行授权===>')
    excute(`sudo npm install npm -g`);
}
excute(`npm set-script release "standard-version --dry-run"`);
excute(`npm set-script postinstall "dm-husky"`)

excute(`npm install cz-customizable commitizen @commitlint/{cli,config-conventional} husky lint-staged standard-version prettier eslint-config-prettier eslint-plugin-prettier --save-dev`);
excute(`dm-husky --force --cz`);
excute(`cp -rf ${path.join(__dirname, 'files')}/ ${root}`);
  • husky.js
#!/usr/bin/env node

const path = require('path');
const {excute} = require('../shelljs/excute');
const {existsSync} = require('fs');
const args = require('minimist')(process.argv.slice(2));

const root = process.cwd();

if (existsSync(path.resolve(root, '.husky/_')) && args.force !== true) {
    console.info('husky exists,jump to next step!');
} else {
    console.info('husky env begin to set:');
    // excute(`npm cache clear --force`);
    excute(`rm -rf ${path.resolve(root, '.husky')}`);
    excute('npx husky install');
    excute(`sh ${path.join(__dirname, 'husky.sh')}`);
    if (args.cz) {
        excute(`npx commitizen init cz-conventional-changelog --force --save-dev --save-exact`)
        excute(`echo 'exec < /dev/tty && node_modules/.bin/cz --hook || true' > .git/hooks/prepare-commit-msg`)
    }
}
  • husky.sh
#!/bin/bash

npx husky add .husky/prepare-commit-msg "exec < /dev/tty && git cz --hook || true"
npx husky add .husky/pre-commit "npx lint-staged --allow-empty $1"
npx husky add .husky/commit-msg "npx --no-install commitlint --edit $1"

  • …/shelljs/excute
#!/usr/bin/env node

const shell = require('shelljs');
const root = process.cwd();

function excute(cmd, opt) {
  const { stdout, stderr, code } = shell.exec(
    cmd, {
      cwd: root,
      ...opt
    } );
  if (code === 0) {
    console.log(stdout);
  } else {
    console.log(stdout);
    console.log(stderr);
    // process.exit(1);
  }
  return { stdout, stderr, code }
}


module.exports = {
  excute
};

创建命令

  • package.json
{
  "name": "kaqiinono-scripts",
  "version": "1.0.3",
  "description": "",
  "main": "index.js",
  "bin": {
    "dm-husky": "env/husky.js",
    "dm-rule": "rule/setEnv.js"
  },
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "keywords": [],
  "author": "",
  "license": "ISC",
  "dependencies": {
    "minimist": "^1.2.5",
    "shelljs": "^0.8.5",
    "walk": "^2.3.15"
  }
}

发布

npm publish

引入项目

# 安装可执行脚本
npm install kaqiinono-scripts -D 

# 执行命令
dm-rule

效果演示

在这里插入图片描述

  • 4
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值