我如何在JavaScript中建立良好的发布过程

by Dafna Rosenblum

达夫娜·罗森布拉姆(Dafna Rosenblum)

我如何在JavaScript中建立良好的发布过程 (How I established a good release process in JavaScript)

使用Git工作流,NPM和第三方库 (With Git Workflows, NPM, and 3rd party libraries)

Lately, I’ve sat down to define the release procedures for my team. I went through git workflows, best practices for versioning, and methods to upgrade external libraries. I wanted to have all my learning in one place, because I know I’ll get back to that in the future. I hope you’ll find it helpful as well.

最近,我坐下来为团队定义发布程序。 我经历了git工作流程,版本管理的最佳做法以及升级外部库的方法。 我想将所有的学习都集中在一个地方,因为我知道以后会再来的。 希望对您也有帮助。

In this article I will explain how to combine git workflow, semver, and NPM to create healthy library management and CI in JavaScript. It began bothering me when my team became bigger and we had to create a better process that worked for everyone and that we agreed upon. I read about 20 articles to create this elaborate combined summary of different practices and official recommendations.

在本文中,我将解释如何结合git工作流,semver和NPM来创建健康JavaScript库管理和CI。 当我的团队扩大时,这开始困扰我,我们必须创建一个更好的流程,该流程适用于每个人,并且我们达成了一致。 我阅读了约20篇文章,以创建这份详尽的总结,总结了不同的实践和官方建议。

GIT流 (GIT FLOW)

There are different patterns to using Git. The patterns dictate what types of branches will exist in the project, their naming conventions, when to use each type and so on. The most well-known pattern is Git Flow.

使用Git有不同的模式。 这些模式指示项目中将存在哪些类型的分支,它们的命名约定,何时使用每种类型等等。 最著名的模式是Git Flow。

GitFlow is like Agile — everyone is using some version of it.

GitFlow就像敏捷-每个人都在使用它的某些版本。

It was created in January 2010 by Vincent Driessen. It has been heavily used since then, although there are many critics of it. I’ll elaborate on their perspective after explaining the methodology itself.

它由Vincent Driessen于2010年1月创建。 从那时起,它就被大量使用,尽管有很多批评家。 在解释方法论本身之后,我将详细介绍他们的观点。

I highly recommend reading it entirely and using the below summary as a cheat sheet only (it contains some extra insights as well).

我强烈建议您完整阅读它,并仅将以下摘要用作备忘单(它也包含一些其他见解)。

两种类型的分支 (Two Types Of Branches)

无限的生命分支: 掌握发展 (Infinite lifetime branches: master and develop)
  • origin/master is always production ready.

    原始/母版始终准备就绪。
  • origin/develop always includes the latest delivered changes for the next release. When it’s ready, it’s merged to master and the changes are tagged with a release number.

    origin / develop始终包含下一版本的最新交付更改。 准备就绪后,将其合并到母版中,并使用发行版号标记更改。
终生分支机构 (Limited lifetime branches)
  • Feature branches

    功能分支
  • Release branches

    发布分支
  • Hot-fix branches

    修补程序分支

Let’s go through each of these in more detail.

让我们更详细地研究每个。

功能分支 (Feature Branches)
  • Branched off from and merged back to develop.

    从分支并合并回开发

  • Naming convention: anything except master, develop, release-*, or hotfix-*. I love to use the prefix feature/, for example feature/fix-texts.

    命名约定:除开发释放- *,hotfix- *任何东西。 我喜欢使用前缀feature/ ,例如feature/fix-texts

When merging back to develop, Vincent recommends using the —-no-ff flag, that always creates a new commit for the merge. This allows you to have as better understanding of tracking of history and know what commits were released together as a feature. It also simplifies reverting a feature.

在重新进行开发时 ,Vincent建议使用—-no-ff标志,该标志始终为合并创建一个新的提交。 这使您可以更好地了解历史记录,并知道作为功能一起发布了哪些提交。 它还简化了功能还原。

发布分支 (Release Branches)
  • Branched off from develop and merged back to develop and master.

    开发分支出来,并合并回开发掌握

  • Naming convention: release-*, for example: release-1.2.

    命名约定: release- * ,例如: release-1.2。

  • Purpose: last minute small changes, so that develop is clear to receive changes for the next release.

    目的:在最后一刻进行细微更改,以便开发人员可以清楚地接收下一版本的更改。

Until branching off the release branch, the changes for the next release can’t be merged to develop. The version number is defined when creating the release branch, and used as its name.

在分支到发行分支之前,下一个发行版的更改不能合并为development 。 版本号是在创建发行分支时定义的,并用作其名称。

npm版本 (npm-version)

After creating the release branch, you should running ./bump-version.sh. This is a fictional script that updates the version number of the project. As I mentioned, the Git Flow article is from January 2010. This is also the month NPM was first released (coincidence??), and I prefer using npm-version like below:

创建发行分支之后,应运行./bump-version.sh 。 这是一个虚构的脚本,用于更新项目的版本号。 正如我提到的,Git Flow文章来自2010年1月。这也是NPM首次发布的月份(巧合?),我更喜欢使用npm-version,如下所示:

> npm version patch

The output will be the new version number. A commit will be added to the branch with the new version updated in the package.json and package-lock.json files.

输出将是新的版本号。 提交将添加到分支中,其中package.jsonpackage-lock.json文件中的新版本已更新。

Run git log -1 and then git show <commit hash> to see the changes.

运行git log -1 ,然后运行git log -1 git show <commit ha sh>来查看更改。

For changing minor version or major, use npm version minor or npm version major, accordingly.

要更改次要版本或专业 ,请相应地使用npm version minornpm version major

Use -m flag to add a commit message, otherwise it will be the number of the new version.

使用-m标志添加提交消息,否则它将是新版本的编号。

If preversion, version, or postversion are in the scripts property of the package.json — they will be executed as well.

如果package.json的scripts属性中包含preversion,versionpostversion,则它们也会被执行。

It will also create a git tag. You can see that by running git tag before and after running npm version patch, and notice the difference.

它还将创建一个git标签 。 您可以通过在运行npm version patch之前和之后运行git tag来看到这一点,并注意其中的区别。

As explained in the git tag documentation, by default, the git push command doesn’t transfer tags to remote servers. You will have to explicitly push tags to a shared server after you have created them. This process is just like sharing remote branches . You can run git push origin v1.5.1. It’s also possible to delete and check-out local and remote tags.

git标记文档中所述,默认情况下, git push命令不会将标记传输到远程服务器。 创建标签后,您必须将标签明确推入共享服务器。 这个过程就像共享远程分支一样。 您可以运行git push origin v1.5.1 。 还可以删除和签出本地和远程标签。

An alternative to npm-version is the popular tool release-it, that can bump version, create tags and releases, and more.

npm-version的替代方法是流行的工具release-it ,它可以提高版本,创建标签和发行等等。

返回发布分支 (Back To Release Branches)

So you created a release branch, ran npm version patch and pushed. Maybe you also added minor bug fixes. The next step is to merge to master and release.

因此,您创建了一个发布分支,运行了npm version patch并进行了推送。 也许您还添加了一些小错误修复。 下一步是合并到母版并发布。

从标签创建发布 (Creating a Release From Tag)

As explained in GitHub documentation, when creating a release, you need to type a version number for it. Versions are based on Git tags. Below the version input area, you’ll see the text: Choose an existing tag, or create a new tag on publish. You can choose whether to push the tag created by npm-version and then type it again when creating the release, or you can choose not to push it, and type it when creating the release. Of course, you can create automatic release instead of manually using GitHub website.

GitHub文档中所述 ,在创建发行版时,您需要为其输入版本号。 版本基于Git标签。 在版本输入区域下方,您将看到以下文本: 选择一个现有标签,或在发布时创建一个新标签。 您可以选择是否推送由npm-version创建的标签,然后在创建发行版时再次键入它,或者可以选择不推送它,然后在创建发行版时键入它。 当然,您可以创建自动发布,而不是使用GitHub网站手动创建

合并发展 (Merge Back To develop)

Don’t forget to merge back the release branch to develop. Then the release branch can be deleted. You might experience merge conflicts here, so just fix them and commit.

不要忘记合并发布分支以进行开发。 然后可以删除发布分支。 您可能会在此处遇到合并冲突,因此只需解决它们并提交即可。

修补程序分支 (Hotfix Branches)

  • Contain fixes for urgent production bugs.

    包含针对紧急生产错误的修复程序。
  • Branched off from master, and merged back to develop and master.

    大师分支出来,并合并回开发大师

  • Naming convention: hotfix-*.

    命名约定: hotfix-*

Like release branches, they’re meant to prepare for a new release, and the process of creating the branch and finishing it is exactly the same.

像发行分支一样,它们也准备为新发行做准备,创建分支和完成分支的过程完全相同。

If you work with Release Branches, and a release branch exists, try not to merge it back to develop, but to the release branch, that will be merged into develop later.

如果您使用Release Branches,并且存在Release分支,请尝试不要将其合并回进行开发,而应合并到release分支,该分支将在以后合并到Development中。

是这样吗? (Is That So?)

This is the Git Flow way. It will work better with waterfall methodology. The recommended way to work today is Continuous Deployment — be fully covered by tests, have no develop branch, merge the feature branches to master and deploy immediately.

这就是Git Flow的方式。 使用瀑布方法会更好。 今天推荐的工作方式是持续部署-被测试完全覆盖,没有开发分支,合并功能分支以立即掌握和部署。

But the type of product and market might dictate a different kind of deployment process sometimes. For example, in healthcare, it’s not always possible to have continuous deployment, due to regulations. In the gaming industry, there are release dates to games and they often don’t work with continuous integration and delivery.

但是有时产品和市场的类型可能会决定另一种部署过程。 例如,在医疗保健行业中 ,由于法规的限制,并不总是能够连续部署。 在游戏行业中,游戏有发行日期,它们通常无法与持续集成和交付结合使用。

反对者 (OPPONENETS)

If you look for “don’t use gitflow” on Google, you can find a lot of articles. Here are the main points in some of them:

如果您在Google上查找“请勿使用gitflow”,则可以找到很多文章。 以下是其中一些要点:

1个 (1)

In his blog “End Of Line”, Adam Ruka states that using the --no-ff flag results with “git train maps” (see photo), that are very hard to track in retrospective. He highly recommends using rebase instead.

Adam Ruka在他的博客“ End Of Line”中指出,将--no-ff标志用于“ git train maps”(见照片),很难追溯。 他强烈建议改用rebase

He also claims that the methodology is too complex, and that it’s impossible for developers not to make mistakes and merge from/to the wrong branch.

他还声称这种方法太复杂了,开发人员不可能不犯错误并从错误分支合并到错误分支。

While I agree with the first point, I think that build automation (like automatic tagging) and well-configured branches on GitHub can solve most of the human errors. He offers a different take on Git Flow in this article.

虽然我同意第一点,但我认为GitHub上的构建自动化(如自动标记)和配置良好的分支可以解决大多数人为错误。 他提供了不同的看法上的Git流在文章。

2 (2)

In his article “Git: How I use it and Why I don’t use GitFlow”, Matthew DeKrey says about the develop branch:

在他的文章“混帐:我如何使用它,为什么我不使用GitFlow”马修DeKrey说,有关develop分支:

“Having code in a common place where it’s not fully tested and not necessarily working towards a feature that is to be released ends up being a ghost town of half-completed architectures and not-released features if the team is ever busy.”
“在没有经过全面测试且不一定要开发要发布的功能的公共场所放置代码,最终会变成半成品架构和如果团队忙于不发布功能的鬼城。”

I think that with some discipline and a decent CI, the team will merge (or rebase) to develop only features that are ready and passed unit tests and integration tests, and then the nightly test suit (or system tests) can run on develop and make sure features work together.

我认为,通过一定的纪律和适当的CI,团队将合并(或重新设置基础)以仅develop已准备就绪且已通过单元测试和集成测试的功能,然后夜间测试套件(或系统测试)可以在开发和运行中运行。确保功能协同工作。

The other problem that he mentions is supporting old versions: “once you cut release v1.2, you can no longer patch v1.1”. And in this article you can also find his recommended way to work with Git branches.

他提到的另一个问题是支持旧版本: “一旦切断发行版v1.2,就无法再修补v1.1” 。 在本文中,您还可以找到他推荐的与Git分支一起使用的方法。

3 (3)

In his article GitHub workflows inside of a company, Nicholas C. Zakas says:

Nicholas C. Zakas 在公司内部的GitHub工作流文章中说:

“The general feeling is that git-flow works well for products in a more traditional release model, where releases are done once every few weeks, but that this process breaks down considerably when you’re releasing once a day or more”.

“一般的感觉是,git-flow在更传统的发行模型中适用于产品,该发行模型每隔几周发布一次,但是当您每天发行一次或多次时,此过程将大大中断 。”

A year and a half after the publication of Git Flow, Scott Chacon, an engineer who helped start GitHub, published GitHub flow, which is a simpler version of Git Flow that works better for CD projects.

在Git Flow发布一年半之后,帮助创建GitHub的工程师Scott Chacon发布了GitHub flow ,它是Git Flow的简单版本,更适合CD项目。

然后要选择什么? (WHAT TO CHOOSE THEN?)

One of the problems we are facing in the industry today is battling the perception that there’s only one way to do things right. We ignore the fact that different teams, products and markets require different solutions.

我们当今行业所面临的问题之一是与人们认为只有一种正确的方法做对的斗争。 我们忽略了以下事实:不同的团队,产品和市场需要不同的解决方案。

Of course, before choosing a technology or pattern, the team needs to understand the pros and cons of using it. But there’s no “one solution fits all”. In this recommended article of Atlassian (BitBucket), they review some possible Git workflows, and say:

当然,在选择一种技术或模式之前,团队需要了解使用该技术的优缺点。 但是,没有“一种解决方案适合所有人”。 在Atlassian(BitBucket)的这篇推荐文章中,他们回顾了一些可能的Git工作流程,并说:

“Remember that these workflows are designed to be guidelines rather than concrete rules. We want to show you what’s possible, so you can mix and match aspects from different workflows to suit your individual needs. When evaluating a workflow for your team, it’s most important that you consider your team’s culture.”

“请记住,这些工作流被设计为指导而非具体规则。 我们想向您展示可行的方法,因此您可以混合和匹配来自不同工作流程的各个方面,以满足您的个性化需求。 在为团队评估工作流程时,最重要的是要考虑团队的文化。”

Later they add:

后来他们添加:

“There is no one size fits all Git workflow. It’s important to develop a Git workflow that is a productivity enhancement for your team. In addition to team culture, a workflow should also complement business culture. Git features like branches and tags should complement your business’s release schedule.”

“没有一种适合所有Git工作流程的尺寸。 开发一个Git工作流程对您的团队来说是非常重要的,这很重要。 除了团队文化之外,工作流还应补充业务文化。 分支和标签之类的Git功能应能补充您企业的发布时间表。”

They recommend working towards short-lived branches and aiming to minimize and simplify reverts.

他们建议朝着寿命短的分支机构努力,并努力减少和简化还原。

是否压缩提交? (Squashed commits or not?)

Another question I was wondering about is what’s better: having one commit per feature or having small commits, so that you can look at the annotation of some line and understand exactly why this specific change has been made.

我想知道的另一个问题是更好的方法:每个功能一次提交或一次小的提交,这样您就可以查看某些行的注释并确切地了解为什么要进行此特定更改。

Now that I’ve educated myself with the healthy approach of the Atlassian article mentioned above, I think it highly depends on the project. For open source projects, with a lot of remote contributors, it’s better to squash, to keep the high level vision about the project.

现在,我已经对上述Atlassian文章的健康方法进行了自我教育,我认为这在很大程度上取决于项目。 对于具有大量远程贡献者的开源项目,最好压榨一下,以保持对项目的高级了解。

For stable organizations in which at least part of the team continues working on the project at any given moment, it’s better to elaborate and keep small commits, but only if two conditions are met:

对于稳定的组织,其中至少有一部分团队在任何给定的时刻继续从事该项目,最好制定并保留少量提交,但前提是要满足以下两个条件:

  1. With indicative messages and not “wip”, “fix”, etc.

    带有指示性消息,而不是“ wip”,“ fix”等
  2. Every commit on its own does not break the build or the product, i.e., if a feature contains 3 commits, and we revert 2 of them, the product is stable and working well.

    每次提交都不会破坏构建或产品,即,如果功能包含3个提交,而我们还原了2个提交,则该产品是稳定且运行良好的。

扫描仪 (SEMVER)

Semver, or Semantic Versioning, is a specification of name convention for versions of code projects. You can find the link to it on the release page of GitHub.

Semver(或语义版本控制)是代码项目版本的名称约定的规范。 您可以在GitHub的发布页面上找到指向它链接

The idea is that every new release will have a version number of the form x.y.z, for example: 1.1.2. The x is increased when a major version is out — i.e. when an API breaks. The y — minor — new functionality but the API changes in a backwards compatible way, and the z — patch — is increased when doing a bug fix in a backwards compatible way.

这个想法是,每个新发行版都将具有xyz形式的版本号,例如:1.1.2。 当主要版本发布时,即API中断时,x会增加。 y( 次要功能)是新功能,但API以向后兼容的方式更改,而z- 补丁则在以向后兼容的方式进行错误修复时增加了。

This is an NPM tool to verify it.

这是一个NPM验证工具

JavaScript版本控制 (JavaScript Versioning)

NPM encourages JavaScript developers to keep the Semver methodology. It should definitely be something to take into consideration when creating your own git workflow.

NPM 鼓励 JavaScript开发人员保留Semver方法。 创建自己的git工作流程时,绝对应该考虑这一点。

更新外部库不应该成为您的Git工作流程的一部分 (Updating External Libraries Should Not be Part of Your Git Workflow)

When working with NPM, if you don’t change your default configuration, installing new packages will install them with a carat: ^. You will see something like this in your package.json:

使用NPM时,如果不更改默认配置,则安装新软件包将以克拉^开头安装它们。 您将在package.json中看到以下内容:

“dependencies”: {    “my_dep”: “^1.0.0”,}

If you don’t want to have the carat, and you want to use a fixed version, you can install like this:

如果您不想拥有克拉,并且想要使用固定版本,则可以这样安装:

npm install foobar --save --save-exact

Or better, you can define it in your .npmrc config file, like this:

或者更好的是,您可以在.npmrc配置文件中定义它,如下所示:

npm config set save=true
npm config set save-exact=true

The above is from Heroku’s Best Practices for Node.js Development article. But why is it recommended?

以上摘自Heroku的Node.js开发最佳实践 文章。 但是为什么推荐呢?

To understand that, I highly recommend reading Pinning Dependencies and Lock Files by Renovate. To summarize the main points:

要了解这一点,我强烈建议您阅读Renovate的固定依赖关系和锁定文件 。 总结要点:

  • “A lock file [package-lock.json] will lock down the exact dependencies and sub-dependencies that your project uses, so that everyone running npm install will install the exact same dependencies as the person that last updated the lock file.” You can see why it’s problematic not to use your lock file — things might break in production due to a change in some dependency, and it will be very hard to track the problem, because you’ll have a different version of this dependency on your local environment.

    “锁定文件[package-lock.json]将锁定项目使用的确切依赖性和依赖性,以便每个运行npm install人都将安装与上次更新锁定文件的人完全相同的依赖性。” 您可以看到为什么不使用锁定文件会带来问题的原因-由于某些依赖项的更改,生产可能会中断,并且很难跟踪该问题,因为您的依赖项将具有不同的版本当地环境。

  • A lock file isn’t made to be human-readable. In case a new version of a third-party library you use is released, and it’s within the range of the allowed versions in the package.json file, the package-lock.json will make sure everyone just uses the fixed version that has been defined when it was last updated. For example, in your package.json you have this definition:

    锁定文件并非易读。 如果发布了您使用的第三方库的新版本,并且该新版本在package.json文件中允许的版本范围之内,则package-lock.json将确保每个人都使用已被修复的固定版本。定义上次更新的时间。 例如,在package.json中,您具有以下定义:
“dependencies”: {    “my_dep”: “^1.0.0”,}

Now if my_dep team releases a new major version, 2.0.0, it will never be used by your application, unless you manually update it.

现在,如果my_dep团队发布了一个新的主要版本2.0.0,除非您手动对其进行更新,否则它将永远不会被您的应用程序使用。

But if they release minor version, 1.2.0, then it will not be used by your application as well, in any environment, because the lock file is making sure a fixed version is used — the one that was within the range that last time it was updated.

但是,如果他们发布的是次要版本1.2.0,则在任何环境下您的应用程序也都不会使用该版本,因为锁定文件确保使用的是固定版本,该版本在上一次的范围内它已更新。

However, if you update your lock file (by running npm update, which updates the lock file according to the rule defined in the package.json file), 1.2.0 will become your fixed version that is defined in the lock file, and it will be hard to track that.

但是,如果更新锁定文件(通过运行npm update ,该更新根据package.json文件中定义的规则更新锁定文件),则1.2.0将成为锁定文件中定义的固定版本,很难追踪到。

  • The usual recommendation is to use a lock file regardless of whether you pin dependencies or not, and pinning even if you have a lock file.

    通常的建议是使用锁定文件,而不管是否固定依赖项,即使有锁定文件也要固定。

In case you choose to pin dependencies, you need some automatic mechanism to upgrade them, so that security fixes and other useful new features won’t surprise you all the time and interfere with your product plan. Renovate is one solution for that, and Dependabot is also a good option. I’m sure you can find more. I think it’s a great solution even if you don’t pin the versions, because there are always new versions that can be outside of the range.

如果选择固定依赖关系,则需要某种自动机制来升级依赖关系,以使安全修复程序和其他有用的新功能不会一直使您感到惊讶并干扰您的产品计划。 翻新是一个解决方案, Dependabot也是一个不错的选择。 我相信您可以找到更多。 我认为,即使您不固定版本,这也是一个很好的解决方案,因为总会有一些新版本超出此范围。

摘要 (Summary)

  1. It’s important for any engineer to know different Git workflows, and to understand the semver methodology and how to use lock files.

    对于任何工程师而言,重要的是要了解不同的Git工作流程,并了解semver方法以及如何使用锁定文件。
  2. Different teams need different workflows. It depends on the market and the team, and the workflow should make life as easy as possible for the engineers using it, allowing them to release stable code fast.

    不同的团队需要不同的工作流程。 这取决于市场和团队,工作流程应使使用它的工程师的工作尽可能轻松,从而使他们能够快速发布稳定的代码。
  3. I think the closest workflow to what I want to work with is described in this article — Feature Branch Workflow.

    我认为本文介绍了与我想使用的最接近的工作流程-Feature Branch Workflow

  4. It’s nice to use semver and fixed versions, together with a service that helps upgrading third party libraries.

    最好使用semver和固定版本,以及有助于升级第三方库的服务。

  5. I’m a great fan of design patterns and I loved reading the different patterns to work with Git.

    我是设计模式的忠实拥护者,我喜欢阅读与Git一起使用的不同模式。

翻译自: https://www.freecodecamp.org/news/how-i-established-a-good-release-process-in-javascript-b93e57e247e1/

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值