211

Before I do a small release and tag it, I'd like to update the package.json to reflect the new version of the program.

Is there a way to edit the file package.json automatically?

Would using a git pre-release hook help?

tUrG0n
  • 3,408
  • 3
  • 16
  • 26
  • 1
    Why don't ou make a shell script which edit package.json, commits and then tag it? – gustavotkg Oct 31 '12 at 20:50
  • yeah so the pre-release hook would invoke that script right? – tUrG0n Nov 01 '12 at 12:18
  • 1
    Related to https://stackoverflow.com/questions/36214586/git-hook-update-package-json-version/ and https://stackoverflow.com/questions/25796533/how-can-i-place-my-meteor-apps-version-number-in-the-ui – Anima-t3d Jul 19 '18 at 08:13

13 Answers13

187

Right answer

To do so, just npm version patch =)

My old answer

There is no pre-release hook originally in git. At least, man githooks does not show it.

If you're using git-extra (https://github.com/visionmedia/git-extras), for instance, you can use a pre-release hook which is implemented by it, as you can see at https://github.com/visionmedia/git-extras/blob/master/bin/git-release. It is needed only a .git/hook/pre-release.sh executable file which edits your package.json file. Committing, pushing and tagging will be done by the git release command.

If you're not using any extension for git, you can write a shell script (I'll name it git-release.sh) and than you can alias it to git release with something like:

git config --global alias.release '!sh path/to/pre-release.sh $1'

You can, than, use git release 0.4 which will execute path/to/pre-release.sh 0.4. Your script can edit package.json, create the tag and push it to the server.

gustavotkg
  • 3,501
  • 1
  • 17
  • 29
  • could you share a code snippet of what would the script look like? :D – tUrG0n Nov 02 '12 at 12:48
  • 1
    Check this link out https://github.com/visionmedia/git-extras/blob/master/bin/git-release – gustavotkg Nov 05 '12 at 11:26
  • i actually use visionmedia's git-extra repo. But ``git release`` does not update the package.json accordingly ... https://github.com/visionmedia/git-extras/issues/150 :D – tUrG0n Nov 05 '12 at 11:53
  • So, just create `.git/hooks/pre-release.sh` containing: `echo -e "{\n\"version\": "$1"\n}" > package.json` and try using `git release $version` – gustavotkg Nov 05 '12 at 12:10
  • 5
    as Commented [here](https://github.com/visionmedia/git-extras/issues/150#issuecomment-10070145) ``npm version patch`` or ``npm version 0.3.1`` will solve it! Could you update your answer accordingly? ty!! – tUrG0n Nov 05 '12 at 13:31
  • Yes please update answer, the solution is `npm version patch` -- thanks – Merc Mar 07 '13 at 03:37
  • Is there a way to do this without commit to git? I just want to update the package version – qodeninja Oct 30 '13 at 19:07
  • @qodeninja does `npm version` use git? – gustavotkg Nov 06 '13 at 17:41
  • When I stage my changes and run `npm version patch -m 'My cnages message'`, npm gives me `Git working directory not clean.` error. Which forces me to make two commits every time. one for my changes and one for version increment – Junaid Qadir Shekhanzai Dec 04 '18 at 10:17
108

npm version is probably the correct answer. Just to give an alternative I recommend grunt-bump. It is maintained by one of the guys from angular.js.

Usage:

grunt bump
>> Version bumped to 0.0.2

grunt bump:patch
>> Version bumped to 0.0.3

grunt bump:minor
>> Version bumped to 0.1.0

grunt bump
>> Version bumped to 0.1.1

grunt bump:major
>> Version bumped to 1.0.0

If you're using grunt anyway it might be the simplest solution.

zemirco
  • 15,163
  • 6
  • 56
  • 84
  • 12
    And if you're using [gulpjs](http://gulpjs.com/): [gulp-bump](https://github.com/stevelacy/gulp-bump) :) – GabLeRoux May 22 '15 at 19:10
  • I coded Vik for this, which bumps npm, Bower, etc... in one fell swoop: https://github.com/Wildhoney/Vik – Wildhoney Aug 12 '15 at 08:46
  • 8
    why use external libraries when npm has this functionality built in? – linuxdan Dec 09 '15 at 19:44
  • 9
    What's the benefit of using these over `npm version`? – Steve Bennett Jan 19 '16 at 03:17
  • Out of curiosity, I'd like to know why some people downvoted this answer. – Johann Philipp Strathausen Aug 14 '16 at 18:34
  • Is there a way to use `npm version` without forcing it to tag in this format `v\d.\d.\d`? – Con Antonakos Nov 16 '16 at 23:45
  • 7
    @ConAntonakos Yes. Try something like `npm --no-git-tag-version version patch`. – Tong Shen Feb 22 '17 at 21:05
  • Yarn has similar functionality built-in. See Eric Kim's answer. – Kenmore Oct 13 '18 at 19:05
  • 1
    @JohannPhilippStrathausen Probably people downvoted because even though it mentions `npm version` (which is the correct answer to the question) it proposes `grunt`, which is not the correct answer (I could elaborate for a very long time why it's not the correct answer but that would be probably something more than the characters I am allowed to add here) – Alejandro Vales Feb 20 '19 at 13:43
  • @JohannPhilippStrathausen you can see why I think this anwer is not the best in my comment below (https://stackoverflow.com/a/54788216/4229159) hope it helps, and remember, the fact that you can do something with other commands doesn't mean they are the best – Alejandro Vales Feb 20 '19 at 14:05
79

This is what I normally do with my projects:

npm version patch
git add *;
git commit -m "Commit message"
git push
npm publish

The first line, npm version patch, will increase the patch version by 1 (x.x.1 to x.x.2) in package.json. Then you add all files -- including package.json which at that point has been modified. Then, the usual git commit and git push, and finally npm publish to publish the module.

I hope this makes sense...

Merc.

jcollum
  • 36,681
  • 46
  • 162
  • 279
Merc
  • 13,909
  • 14
  • 64
  • 109
  • 13
    As far as I can tell, `npm version patch` does the commit itself; however, to push the tag to github, I think you also need to `git push --tags`. – ChrisV Jan 14 '15 at 10:39
  • @ChrisV is correct -- `npm version patch` bumps the version number *and immediately commits the change* – Dan Esparza Mar 20 '15 at 14:53
  • 3
    @DanEsparza This might be a setting thing. `npm version patch` does not commit anything for me. – Mordred Apr 06 '15 at 16:03
  • @Mordred Hmmm ... possibly. I don't see anything in the [npm config](https://docs.npmjs.com/misc/config) docs about that, but could it be that you don't have git in your path or something? – Dan Esparza Apr 07 '15 at 13:17
  • @DanEsparza git is definitely in the path as I commit from the exact same folder I run `npm version`. – Mordred Apr 07 '15 at 14:13
  • If i want to use npm verision patch from bamboo (CI) then how would you determine whether to increment, the major or minor versions? – user804401 Oct 20 '17 at 15:52
  • I don't understand why this isn't the selected answer. – Yulian Apr 30 '20 at 11:50
  • I would like to amend previous commit instead of creating new. – Qwerty Oct 17 '20 at 19:19
34

As an addition to npm version you can use the --no-git-tag-version flag if you want a version bump but no tag or a new commit:

npm --no-git-tag-version version patch

https://docs.npmjs.com/cli/version

Tieme
  • 53,990
  • 18
  • 90
  • 147
33

To give a more up-to-date approach.

package.json

  "scripts": {
    "eslint": "eslint index.js",
    "pretest": "npm install",
    "test": "npm run eslint",
    "preversion": "npm run test",
    "version": "",
    "postversion": "git push && git push --tags && npm publish"
  }

Then you run it:

npm version minor --force -m "Some message to commit"

Which will:

  1. ... run tests ...

  2. change your package.json to a next minor version (e.g: 1.8.1 to 1.9.0)

  3. push your changes

  4. create a new git tag release and

  5. publish your npm package.

--force is to show who is the boss! Jokes aside see https://github.com/npm/npm/issues/8620

Jonatas Walker
  • 11,553
  • 5
  • 43
  • 74
  • 3
    You can also add a script like `"deploy-minor": "npm version minor --force -m \"version %s\""` so all you need to remember is `npm run deploy-minor` :) – Kristofor Carle Dec 02 '16 at 06:30
24

If you are using yarn you can use

yarn version --patch

This will increment package.json version by patch (0.0.x), commit, and tag it with format v0.0.0

Likewise you can bump minor or major version by using --minor or --major

When pushing to git ensure you also push the tags with --follow-tags

git push --follow-tags

You can also create a script for it

    "release-it": "yarn version --patch && git push --follow-tags"

Simply run it by typing yarn release-it

Eric Kim
  • 7,997
  • 4
  • 24
  • 28
13

I am using husky and git-branch-is:

As of husky v1+:

// package.json
{
  "husky": {
    "hooks": {
      "post-merge": "(git-branch-is master && npm version minor || 
  (git-branch-is dev && npm --no-git-tag-version version patch)",
    }
  }
}

Prior to husky V1:

"scripts": {
  ...
  "postmerge": "(git-branch-is master && npm version minor || 
  (git-branch-is dev && npm --no-git-tag-version version patch)",
  ...
},

Read more about npm version

Webpack or Vue.js

If you are using webpack or Vue.js, you can display this in the UI using Auto inject version - Webpack plugin

NUXT

In nuxt.config.js:

var WebpackAutoInject = require('webpack-auto-inject-version');

module.exports = {
  build: {
    plugins: [
      new WebpackAutoInject({
        // options
        // example:
        components: {
          InjectAsComment: false
        },
      }),
    ]
  },
}

Inside your template for example in the footer:

<p> All rights reserved © 2018 [v[AIV]{version}[/AIV]]</p>
Anima-t3d
  • 2,873
  • 6
  • 34
  • 51
  • i like this husky option the best, although i don't think it works as is anymore. i don't think 'postmerge' exists, "pre-push" is probably the best option. and the 'git-branch-is' results don't really work since they error out and basically crash the whole post (since it's checking both master and dev, it'll error out on one of them) – Phil Sep 07 '19 at 21:47
  • @Phil You can still use `postmerge`, but it is now `post-merge` inside the `husky: {hooks:{}}` config. What issue do you have with `git-branch-is`? – Anima-t3d Sep 08 '19 at 12:46
  • it would just error out for me instead of running. No worries though, i've ended up going with this option : https://marketplace.visualstudio.com/items?itemName=richardfennellBM.BM-VSTS-Versioning-Task – Phil Sep 08 '19 at 21:22
  • 1
    @Phil thanks for following up. I just tried with updated version and I have no errors, perhaps something is wrong with your post-merge command itself. – Anima-t3d Sep 09 '19 at 09:24
8

I want to add some clarity to the answers this question got.

Even thought there are some answers here that are tackling properly the problem and providing a solution, they are not the correct ones. The correct answer to this question is to use npm version

Is there a way to edit the file package.json automatically?

Yes, what you can do to make this happen is to run the npm version command when needed, you can read more about it here npm version, but the base usage would be npm version patch and it would add the 3rd digit order on your package.json version (1.0.X)

Would using a git pre-release hook help?

You could configure to run the npm version command on the pre-release hook, as you need, but that depends if that is what you need or not in your CD/CI pipe, but without the npm version command a git pre-release hook can't do anything "easily" with the package.json

The reason why npm version is the correct answer is the following:

  1. If the user is using a folder structure in which he has a package.json he is using npm if he is using npm he has access to the npm scripts.
  2. If he has access to npm scripts he has access to the npm version command.
  3. Using this command he doesn't need to install anything more in his computer or CD/CI pipe which on the long term will reduce the maintainability effort for the project, and will help with the setup

The other answers in which other tools are proposed are incorrect.

gulp-bump works but requires another extra package which could create issues in the long term (point 3 of my answer)

grunt-bump works but requires another extra package which could create issues in the long term (point 3 of my answer)

Alejandro Vales
  • 2,546
  • 17
  • 31
7

First, you need to understand the rules for upgrading the versioning number. You can read more about the semantic version here.

Each version will have x.y.z version where it defines for different purpose as shown below.

  1. x - major, up this when you have major changes and it is huge discrepancy of changes occurred.
  2. y - minor, up this when you have new functionality or enhancement occurred.
  3. z - patch, up this when you have bugs fixed or revert changes on earlier version.

To run the scripts, you can define it in your package.json.

"script": {
    "buildmajor": "npm version major && ng build --prod",
    "buildminor": "npm version minor && ng build --prod",
    "buildpatch": "npm version patch && ng build --prod"
}

In your terminal, you just need to npm run accordingly to your needs like

npm run buildpatch

If run it in git repo, the default git-tag-version is true and if you do not wish to do so, you can add below command into your scripts:

--no-git-tag-version

for eg: "npm --no-git-tag-version version major && ng build --prod"

Mnemo
  • 544
  • 1
  • 10
  • 15
4

Just in case if you want to do this using an npm package semver link

let fs = require('fs');
let semver = require('semver');

if (fs.existsSync('./package.json')) {
    var package = require('./package.json');
    let currentVersion = package.version;
    let type = process.argv[2];
    if (!['major', 'minor', 'patch'].includes(type)) {
        type = 'patch';
    }

    let newVersion = semver.inc(package.version, type);
    package.version = newVersion;
    fs.writeFileSync('./package.json', JSON.stringify(package, null, 2));

    console.log('Version updated', currentVersion, '=>', newVersion);
}

package.json should look like,

{
  "name": "versioning",
  "version": "0.0.0",
  "description": "Update version in package.json using npm script",
  "main": "version.js",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1",
    "version": "node version.js"
  },
  "author": "Bhadresh Arya",
  "license": "ISC",
  "dependencies": {
    "semver": "^7.3.2"
  }
}

just pass major, minor, patch argument with npm run version. Default will be patch.

example: npm run version or npm run verison patch or npm run verison minor or npm run version major

Git Repo

Bhadresh Arya
  • 486
  • 3
  • 6
3

You can use the version-select package:

npm i -D version-select
{
    "name": "test",
    "version": "1.0.0",
    "scripts": {
        "version-select": "version-select"
    },
    "devDependencies": {
        "version-select": "^1.0.13"
    }
}

enter image description here

Read more

Dmitry Grinko
  • 8,671
  • 12
  • 35
  • 63
1

With Husky:

{
  "name": "demo-project",
  "version": "0.0.3",
  "husky": {
    "hooks": {
      "pre-commit": "npm --no-git-tag-version version patch && git add ."
    }
  }
}
Duc Trung Mai
  • 733
  • 1
  • 6
  • 13
0

I have created a tool that can accomplish automatic semantic versioning based on the tags in commit messages, known as change types. This closely follows the Angular Commit Message Convention along with the Semantic Versioning Specification.

You could use this tool to automatically change the version in the package.json using the npm CLI (this is described here).

In addition, it can create a changelog from these commits and also has a menu (with a spell checker for commit messages) for creating commits based on the change type. I highly recommend checking it out and reading to docs to see everything that can be accomplished with it.

I wrote the tool because I couldn't find anything that suited my needs for my CICD Pipeline to automate semantic versioning. I'd rather focus on what the actual changes are than what the version should be and that's where my tool saves the day.

For more information on the rationale for the tool, please see this.

Daniel Eagle
  • 1,745
  • 2
  • 16
  • 16