有没有办法从nodejs代码中的package.json获取版本?


586

有没有办法package.json在nodejs应用程序中设置版本?我想要这样的东西

var port = process.env.PORT || 3000
app.listen port
console.log "Express server listening on port %d in %s mode %s", app.address().port, app.settings.env, app.VERSION

获取Node的版本或package.json中声明的版本更重要吗?如果是表格,它将为您提供运行版本:console.log(process.version)
Adrian Lynch

Answers:


957

我发现以下代码片段最适合我。由于它用于require加载package.json,因此无论当前工作目录如何,它都可以工作。

var pjson = require('./package.json');
console.log(pjson.version);

@Pathogen提供的警告:

使用Browserify这样做会带来安全隐患。
注意不要将您package.json的信息公开给客户端,因为这意味着所有依赖项版本号,构建和测试命令以及更多信息都将发送给客户端。
如果要在同一项目中构建服务器和客户端,则也要公开服务器端版本号。攻击者可以使用此类特定数据来更好地应对服务器上的攻击。


25
如果您试图从其他地方抓住它而被烧死(就像我以前一样),那么可以这样做require('root-require')('package.json').version
mikermcneil 2014年

5
在全球安装的shebang不能用于我的脚本。Error: Cannot find module 'package.json'
exebook

14
较短
-require

60
警告!使用browserify这样做会带来安全隐患:捆绑软件中的package.json意味着所有依赖项版本号,构建和测试命令以及更多信息都将发送到客户端。如果要在同一项目中构建服务器和客户端,则也要公开服务器端版本号。
病原

4
@Pathogen genversion解决了客户端方面的问题。这是一个从package.json读取版本并从中生成可导入模块的工具。免责声明:我是维护者。
阿克塞利·帕伦(AkseliPalén)'17年

348

如果您的应用是使用“ npm start”启动的,则可以简单地使用:

process.env.npm_package_version

有关更多详细信息,请参见package.json vars


6
这可能是最好的答案,因为package.json中的大多数信息都附加到流程运行时变量上
Alexander Mills

2
是的,我同意。使用不需要打开并重新读取package.json文件的过程变量,这应该是正确的答案。
Juanma

12
在节点之外(例如,通过执行的shell脚本npm run …),版本将在环境变量中$npm_package_version
Quinn Comendant 2015年

12
从另一个程序包的脚本中调用时,这会错误地报告调用程序包的版本,而不是被调用程序包的版本。
jjrv

6
它在以开头的电子应用程序中有效npm start,但在内置的电子应用程序中无效:为此,您可以在中找到它app.getVersion
ChrisV

158

使用ES6模块,您可以执行以下操作:

import {version} from './package.json';

2
我认为这些在节点中不受支持:github.com/nodejs/help/issues/53
ripper234 '17

1
尚不直接支持es6模块,但仍然可以使用es6模块,使用Babel
Patrick Lee Scott,

4
@Sornii不,整个package.json将在客户端中。我使用webpack的definePlugin仅将选定的信息从节点环境传递到浏览器。
doeke

2
是否像stackoverflow.com/a/10855054/540144中所指定的那样存在安全隐患?
itsazzad

1
是的,同样的安全问题。整个package.json将包含在客户端捆绑包中。
Neromancer

93

或在普通的旧外壳中:

node -e "console.log(require('./package.json').version);"

可以缩短为

node -p "require('./package.json').version"

即使这并不是问题的确切答案,但是如果您想在package.json自身内部使用版本,例如在日志中登录版本文件,也很有用script

{
  "name": "myapp",
  "version": "0.1.2",
  "scripts": {
    "run": "node index.js 2>&1 | tee -a myapp_v$(node -p \"require('./package.json').version\").log",
  ...
}

但是,根据要求,这不在nodeJS应用程序本身内。
史蒂夫·贝内特

1
@SteveBennett不,但是它确实帮助了90个人和我。
卡尔·莫里森

1
可能不止于此。
史蒂夫·本内特

61

有两种获取版本的方法:

  1. 要求package.json并获取版本:
const { version } = require('./package.json');
  1. 使用环境变量:
const version = process.env.npm_package_version;

请不要使用JSON.parsefs.readFilefs.readFileSync并且不使用另一种npm modules,没有必要为这个问题。


2
感谢您提供此代码段,它可能会提供一些有限的即时帮助。通过说明为什么这是解决问题的好方法,适当的解释将大大提高其长期价值,对于其他类似问题的读者也将更有用。请编辑您的答案以添加一些解释,包括您所做的假设。
milo526

8
然后npm_*,仅当脚本由NPM启动时,环境值才可用npm start。如果您正在执行node app.js类似操作,则它们将不存在。
Nate

@Nate所以最好使用from版本package.json
FilipŠ18年

37

这是从package.json中读取版本的方法:

fs = require('fs')
json = JSON.parse(fs.readFileSync('package.json', 'utf8'))
version = json.version

我看过很多,我很喜欢-您/任何人都知道require() introduces? (for instance, does require()不支持utf8阅读的注意事项吗?为您的片断可能会建议)
electblake

4
require()缓存文件,在这种情况下应该没有什么区别。
jlee 2014年

@jlee是人们通常这样做的原因JSON.parse(fs.readFileSync('package.json', 'utf8'))而不是delete require.cache[require.resolve('package.json')]; require('package.json')何时要重新加载吗?
Mihail Malostanidis

const {version} = require('./ package.json');
аlexdykyі

23

还有另一种从package.json文件中获取某些信息的方法,即使用pkginfo模块。

该模块的用法非常简单。您可以使用以下方法获取所有程序包变量:

require('pkginfo')(module);

或仅特定细节(version在这种情况下)

require('pkginfo')(module, 'version');

并且您的软件包变量将设置为module.exports(因此可通过访问版本号module.exports.version)。

您可以使用以下代码段:

require('pkginfo')(module, 'version');
console.log "Express server listening on port %d in %s mode %s", app.address().port, app.settings.env, module.exports.version

该模块具有非常好的功能-可以在项目中的任何文件中使用(例如,在子文件夹中),并且它将自动从中获取信息package.json。因此,您不必担心自己在哪里package.json

我希望这会有所帮助。


1
这是module什么
chovy

@chovy,module不是这个特定的示例变量;它是代表node.js中当前模块的变量。您可以在此处阅读有关node.js模块的更多信息:nodejs.org/api/modules.html#modules_the_module_object
Tom

2
我正在尝试获取模块所需的其他模块的版本...而且我很难确定pkginfo是否可以实现这一点。
迈克尔

23

对于那些寻求在服务器端也可以使用的安全客户端解决方案的人来说,可以使用genversion。这是一个命令行工具,可从最近的package.json中读取版本,并生成可导入的CommonJS模块文件,以导出该版本。免责声明:我是维护者。

$ genversion lib/version.js

我承认客户端安全不是OP的主要意图,但是正如Mark Wallaceaug的回答所讨论的那样,它与客户的需求高度相关,也是我找到此问答的原因。


4
这就是答案,它需要更多的选票才能超越目前最棘手的问题。
杰夫·艾伦

1
某些人可能会对这是一个命令行工具感到震惊。别担心!该工具的自述文件描述了如何(轻松地)将build的调用集成到package.json中,以便您可以忘记该工具的存在,并且始终具有最新的版本号。
malamut

11

只是添加一个答案是因为我遇到了这个问题,以查看在Web应用程序中包含package.json版本的最佳方法。

我知道这个问题是针对Node.js的,但是,如果您使用Webpack捆绑您的应用程序,只是提醒您,建议的方法是使用DefinePlugin在配置中声明全局版本并引用该版本。所以你可以在你的webpack.config.json

const pkg = require('../../package.json');

...

plugins : [
    new webpack.DefinePlugin({
      AppVersion: JSON.stringify(pkg.version),
...

然后AppVersion是一个可供您使用的全局变量。还要确保您.eslintrc通过globals prop忽略了这一点


8

选项1

最佳做法是使用npm环境变量从package.json进行版本控制。

process.env.npm_package_version

有关更多信息,请访问:https : //docs.npmjs.com/using-npm/config.html

仅当您使用NPM命令启动服务时,这才有效。

快速信息:您可以使用process.env.npm_package_ [keyname]读取pacakge.json中的任何值

选项2

使用https://www.npmjs.com/package/dotenv作为.env文件在环境变量中设置版本,并在process.env.version


7

您可以使用ES6导入package.json来获取版本号并在控制台上输出版本。

import {name as app_name, version as app_version}  from './path/to/package.json';

console.log(`App ---- ${app_name}\nVersion ---- ${app_version}`);

3
只要您在tsconfig.json中将“ resolveJsonModule”设置为“ true”,此方法就起作用。
罗素·菲利普斯

6

要确定节点代码中的软件包版本,可以使用以下命令:

  1. const version = require('./package.json').version; 对于<ES6版本

  2. import {version} from './package.json'; 对于ES6版本

  3. const version = process.env.npm_package_version; 如果已经使用启动了应用程序npm start,则所有npm_ *环境变量都可用。

  4. 您也可以使用以下npm软件包-root-require,pkginfo,project-version。


4

您可以使用项目版本包。

$ npm install --save project-version

然后

const version = require('project-version');

console.log(version);
//=>  '1.0.0'

如果由于某种原因缺少env var,它将使用process.env.npm_package_version但回退到编写的版本package.json


例如,如果js文件不是从npm启动的?
Mihail Malostanidis

1

我这样做findup-sync

var findup = require('findup-sync');
var packagejson = require(findup('package.json'));
console.log(packagejson.version); // => '0.0.1' 

findup以cwd开始,因此在大多数情况下,它只会获得最高级别package.json,类似于process.env.npm_package_version不要求通过npm启动它。因此,尝试获取您的库版本实际上会获取调用方的版本。一个简单的require('./ package.json')可以避免这种情况。
Mihail Malostanidis

1

我知道这不是OP的意图,但我只需要这样做,因此希望对下一个人有所帮助。

如果您将docker-compose用于CI / CD进程,则可以通过这种方式获得它!

version:
  image: node:7-alpine
  volumes:
    - .:/usr/src/service/
  working_dir: /usr/src/service/
  command: ash -c "node -p \"require('./package.json').version.replace('\n', '')\""

对于图像,您可以使用任何节点图像。我使用阿尔卑斯山,因为它是最小的。


1

为什么不使用需求解决方案...

const packageJson = path.dirname(require.resolve('package-name')) + '/package.json';
const { version } = require(packageJson);
console.log('version', version)

用这种方法可以处理所有子路径:)


0

package.json文件导入到server.js或中app.js,然后将package.json属性访问到服务器文件中。

var package = require('./package.json');

package变量包含package.json中的所有数据。


0

我做了一个有用的代码来获取父模块的package.json

function loadParentPackageJson() {
    if (!module.parent || !module.parent.filename) return null
    let dir = path.dirname(module.parent.filename)
    let maxDepth = 5
    let packageJson = null
    while (maxDepth > 0) {
        const packageJsonPath = `${dir}/package.json`
        const exists = existsSync(packageJsonPath)
        if (exists) {
            packageJson = require(packageJsonPath)
            break
        }
        dir = path.resolve(dir, '../')
        maxDepth--
    }
    return packageJson
}

0

如果使用汇总,该rollup-plugin-replace插件可用于添加版本,而无需将package.json暴露给客户端。

// rollup.config.js

import pkg from './package.json';
import { terser } from "rollup-plugin-terser";
import resolve from 'rollup-plugin-node-resolve';
import commonJS from 'rollup-plugin-commonjs'
import replace from 'rollup-plugin-replace';

export default {
  plugins: [
    replace({
      exclude: 'node_modules/**',
      'MY_PACKAGE_JSON_VERSION': pkg.version, // will replace 'MY_PACKAGE_JSON_VERSION' with package.json version throughout source code
    }),
  ]
};

然后,在源代码中,要获取package.json版本的任何地方,都将使用字符串“ MY_PACKAGE_JSON_VERSION”。

// src/index.js
export const packageVersion = 'MY_PACKAGE_JSON_VERSION' // replaced with actual version number in rollup.config.js
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.