From 8f0e3041beb1eea99b375032ce3f751a1648b3f7 Mon Sep 17 00:00:00 2001 From: CaoMeiYouRen <996881204@qq.com> Date: Fri, 17 Dec 2021 00:40:55 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E6=96=B0=E5=A2=9E=20=E8=B4=A1=E7=8C=AE?= =?UTF-8?q?=E6=8C=87=E5=8D=97=20=E5=88=9D=E5=A7=8B=E5=8C=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/interfaces.ts | 4 ++ src/plopfile.ts | 9 ++++ src/utils.ts | 106 +++++++++++++++++++++++++++++--------- templates/CONTRIBUTING.md | 78 ++++++++++++++++++++++++++++ templates/README.md | 7 ++- 5 files changed, 179 insertions(+), 25 deletions(-) create mode 100644 templates/CONTRIBUTING.md diff --git a/src/interfaces.ts b/src/interfaces.ts index 3b07985..a66ce63 100644 --- a/src/interfaces.ts +++ b/src/interfaces.ts @@ -50,4 +50,8 @@ export interface InitAnswers { * 是否初始化 README,仅开源的情况下初始化 */ isInitReadme: boolean + /** + * 是否初始化 贡献指南,仅开源的情况下初始化 + */ + isInitContributing: boolean } diff --git a/src/plopfile.ts b/src/plopfile.ts index b2f886b..a6bd2b6 100644 --- a/src/plopfile.ts +++ b/src/plopfile.ts @@ -124,6 +124,15 @@ module.exports = function (plop: NodePlopAPI) { return answers.isOpenSource }, }, + { + type: 'confirm', + name: 'isInitContributing', + message: '是否初始化 贡献指南(CONTRIBUTING.md) ?', + default: true, + when(answers: InitAnswers) { + return answers.isOpenSource + }, + }, { type: 'confirm', name: 'isRemoveDependabot', diff --git a/src/utils.ts b/src/utils.ts index 2fab7e6..380a85d 100644 --- a/src/utils.ts +++ b/src/utils.ts @@ -27,6 +27,7 @@ const REMOTES = [ 'https://github.com', 'https://hub.fastgit.org', 'https://github.com.cnpmjs.org', + 'https://download.fastgit.org', ] /** @@ -67,7 +68,6 @@ export async function getFastGitRepo(repository: string) { loading.start() try { const fast = await Promise.any(REMOTES.map((remote) => { - // const url = `${remote}/${repository}/.git` const url = `${remote}/${repository}/archive/refs/heads/master.zip` return axios({ url, @@ -108,7 +108,7 @@ export async function asyncExec(cmd: string, options?: ExecOptions) { } export async function init(projectPath: string, answers: InitAnswers) { - const { isOpenSource, isRemoveDependabot, gitRemoteUrl } = answers + const { isOpenSource, isRemoveDependabot, gitRemoteUrl, isInitReadme, isInitContributing } = answers try { await asyncExec('git --version', { @@ -141,7 +141,15 @@ export async function init(projectPath: string, answers: InitAnswers) { await initProjectJson(projectPath, answers) if (isOpenSource) { // 只有开源的时候才初始化 REAMD - await initReadme(projectPath, answers) + const info = await getProjectInfo(projectPath, answers) + if (info) { + if (isInitReadme) { + await initReadme(projectPath, info) + } + if (isInitContributing) { + await initContributing(projectPath, info) + } + } } await asyncExec('git add .', { @@ -234,19 +242,11 @@ export async function initProjectJson(projectPath: string, answers: InitAnswers) const cleanText = (text: string) => text.replace(/-/g, '--').replace(/_/g, '__') -/** - * 初始化 README.md - * @param projectPath - * @param answers - */ -export async function initReadme(projectPath: string, answers: InitAnswers) { - const loading = ora('正在初始化 README.md ……').start() +async function getProjectInfo(projectPath: string, answers: InitAnswers) { + const loading = ora('正在获取项目信息 ……').start() try { const { name, author, description, isOpenSource, isPublishToNpm } = answers const packageManager = 'npm' - const templatePath = path.join(__dirname, '../templates/README.md') - const template = (await fs.readFile(templatePath, 'utf8')).toString() - const newReadmePath = path.join(projectPath, 'README.md') const pkgPath = path.join(projectPath, 'package.json') const pkg: IPackage = await fs.readJSON(pkgPath) @@ -267,11 +267,12 @@ export async function initReadme(projectPath: string, answers: InitAnswers) { const demoUrl = `${repositoryUrl}#readme` const homepage = documentationUrl const githubUsername = author - const authorWebsite = isOpenSource ? await getAuthorWebsiteFromGithubAPI(githubUsername) : '' + const authorWebsite = await getAuthorWebsiteFromGithubAPI(githubUsername) const licenseUrl = `${repositoryUrl}/blob/master/LICENSE` + const discussionsUrl = `${repositoryUrl}/discussions` + const pullRequestsUrl = `${repositoryUrl}/pulls` const projectInfos = { - filename: templatePath, currentYear: new Date().getFullYear(), name, description, @@ -312,7 +313,31 @@ export async function initReadme(projectPath: string, answers: InitAnswers) { name: key, value: engines[key], })), + discussionsUrl, + pullRequestsUrl, } + loading.succeed('项目信息 初始化成功!') + return projectInfos + + } catch (error) { + loading.fail('项目信息 初始化失败!') + console.error(error) + return null + } +} + +/** + * 初始化 README.md + * @param projectPath + * @param projectInfos + */ +async function initReadme(projectPath: string, projectInfos: any) { + const loading = ora('正在初始化 README.md ……').start() + try { + + const templatePath = path.join(__dirname, '../templates/README.md') + const template = (await fs.readFile(templatePath, 'utf8')).toString() + const newReadmePath = path.join(projectPath, 'README.md') const readmeContent = await ejs.render( template, @@ -336,8 +361,42 @@ export async function initReadme(projectPath: string, answers: InitAnswers) { } /** - * 根据 github name 获取作者网站 + * 初始化 贡献指南(CONTRIBUTING.md) + * @param projectPath + * @param projectInfos */ +async function initContributing(projectPath: string, projectInfos: any) { + const loading = ora('正在初始化 贡献指南 ……').start() + try { + + const templatePath = path.join(__dirname, '../templates/CONTRIBUTING.md') + const template = (await fs.readFile(templatePath, 'utf8')).toString() + const newReadmePath = path.join(projectPath, 'CONTRIBUTING.md') + + const readmeContent = await ejs.render( + template, + projectInfos, + { + debug: false, + async: true, + }, + ) + + if (await fs.pathExists(newReadmePath)) { + await fs.remove(newReadmePath) + } + await fs.writeFile(newReadmePath, lintMd(unescape(readmeContent))) + + loading.succeed('贡献指南 初始化成功!') + } catch (error) { + loading.fail('贡献指南 初始化失败!') + console.error(error) + } +} + +/** + * 根据 github name 获取作者网站 + */ async function getAuthorWebsiteFromGithubAPI(githubUsername: string): Promise { try { const userData = (await axios.get(`${GITHUB_API_URL}/users/${githubUsername}`)).data @@ -350,8 +409,8 @@ async function getAuthorWebsiteFromGithubAPI(githubUsername: string): Promise { try { const html = (await axios.get(NODEJS_URL)).data as string @@ -364,10 +423,10 @@ async function getLtsNodeVersion(): Promise { } /** - * 修复 markdown 格式 - * @param markdown - * @returns - */ + * 修复 markdown 格式 + * @param markdown + * @returns + */ function lintMd(markdown: string) { const rules = { 'no-empty-code': 0, @@ -378,5 +437,4 @@ function lintMd(markdown: string) { } as const const fixed = fix(markdown, rules) return fixed -} - +} \ No newline at end of file diff --git a/templates/CONTRIBUTING.md b/templates/CONTRIBUTING.md new file mode 100644 index 0000000..cf3bca6 --- /dev/null +++ b/templates/CONTRIBUTING.md @@ -0,0 +1,78 @@ +# 贡献指南 + +在为此存储库做出贡献时,请首先通过 issue、电子邮件或任何其他方法与此存储库的所有者讨论您希望进行的更改,然后再进行更改。 + +## 开发环境设置 + +要设置开发环境,请按照以下步骤操作: + +1. Clone 本项目 + + ```sh + git clone <%= repositoryUrl %> + ``` + +2. 安装依赖 + + ```sh + npm i + # 或 yarn + # 或 pnpm i + ``` + +3. 运行开发环境 + +<% if (devCommand) { -%> +```sh +<%= devCommand %> +``` +<% } -%> + +## 问题和功能请求 + +你在源代码中发现了一个错误,文档中有一个错误,或者你想要一个新功能? 看看[GitHub 讨论](<%= discussionsUrl %>)看看它是否已经在讨论中。您可以通过[在 GitHub 上提交问题](<%= issuesUrl %>)来帮助我们。在创建问题之前,请确保搜索问题存档 - 您的问题可能已经得到解决! + +请尝试创建以下错误报告: + +- *可重现。*包括重现问题的步骤。 +- *具体的。*包括尽可能多的细节:哪个版本,什么环境等。 +- *独特的。*不要复制现有的已打开问题。 +- *范围仅限于单个错误。*每个报告一个错误。 + +**更好的是:提交带有修复或新功能的拉取请求!** + +### 如何提交拉取请求 + +1. 在我们的存储库中搜索 与您的提交相关的开放或关闭的 [Pull Requests](<%= pullRequestsUrl %>)。你不想重复努力。 + +2. Fork 本项目 + +3. 创建您的功能分支 ( `git checkout -b feat/your_feature`) + +4. 提交您的更改 + + 本项目使用 [约定式提交](https://www.conventionalcommits.org/zh-hans/v1.0.0/),因此请遵循提交消息中的规范。 + + git commit 将用于自动化生成日志,所以请勿直接提交 git commit。 + + 非常建议使用 [commitizen](https://github.com/commitizen/cz-cli) 工具来生成 git commit,使用 husky 约束 git commit + + ```sh + git add . + git cz # 使用 commitizen 提交! + git pull # 请合并最新代码并解决冲突后提交! + #请勿直接提交git commit + #若觉得修改太多也可分开提交。先 git add 一部分,执行 git cz 提交后再提交另外一部分 + ``` + +​ 关于选项,参考 [semantic-release](https://github.com/semantic-release/semantic-release) 的文档 + +- 若为 BUG 修复,则选择 `fix` +- 若为新增功能,则选择 `feat`,新增音声可以按这个提交。 +- 若为移除某些功能,则选择 `perf` 或填写 `BREAKING CHANGE` + - `perf` 和其他破坏性更新,若不是为了修复 BUG,原则上将拒绝该 PR + + +5. 推送到分支 ( `git push origin feat/your_feature`) + +6. [打开一个新的 Pull Request](<%= repositoryUrl %>/compare?expand=1) \ No newline at end of file diff --git a/templates/README.md b/templates/README.md index 9d0956a..f550335 100644 --- a/templates/README.md +++ b/templates/README.md @@ -8,6 +8,11 @@ <% if (projectVersion && !isProjectOnNpm) { -%> Version <% } -%> +<% if (isGithubRepos) { -%> + + GitHub Workflow Status + +<% } -%> <% if (projectPrerequisites) { -%> <% projectPrerequisites.map(({ name, value }) => { -%> @@ -123,7 +128,7 @@ ## 🤝贡献 -欢迎 Contributions, issues and feature!
如有问题请查看 [issues page](<%= issuesUrl %>). <%= contributingUrl ? `您还可以查看[contributing guide](${contributingUrl}).` : '' %> +欢迎 贡献、提问或提出新功能!
如有问题请查看 [issues page](<%= issuesUrl %>).
<%= contributingUrl ? `贡献或提出新功能可以查看[contributing guide](${contributingUrl}).` : '' %> <% } -%> ## 支持