【问题标题】:Update npm package with fixed dependency from command line从命令行更新具有固定依赖关系的 npm 包
【发布时间】:2016-01-25 10:07:06
【问题描述】:

我有一个 npm 包,它的固定版本有更新。
示例 package.json 提取:

devDependencies: {
   "someFixedVersionPackage": "1.0.0", //1.1.0 is latest
   "anotherFixedVersionPackage": "2.3.2", //2.3.4 is latest
}

是否存在安装该软件包的最新版本并更新 package.json 的 npm 命令,最好同时更新所有软件包?

为了明确,我希望上面的 package.json sn-p 更新到这个,除了包本身被更新:

devDependencies: {
   "someFixedVersionPackage": "1.1.0", //latest
   "anotherFixedVersionPackage": "2.3.4", //latest
}

谢谢。

【问题讨论】:

  • 根据规范,npm update --save-dev 确实会更新你的包(并在 package.json 中写入新版本)。为了尊重semversioning,它只是不会更新某些案例。
  • 如果版本是固定的,它不会更新任何东西。仅当您使用 semver 范围时才会这样做。
  • 所以我注意到了。恐怕您最好手动修改版本范围,或者为每个软件包安装一个新版本。这些版本应该被修复是有原因的。我会看看还有什么可以建议的。
  • 手动修改作品,但不能从命令行进行修改是愚蠢的,因为它们就是这样创建的。固定版本经过新版本测试后更新。
  • 实际上,使用npm install --save 安装包默认会执行“^«latest»”。

标签: npm


【解决方案1】:

为什么npm update 在这里不起作用?

根据npm update 上的文档:

此命令会将列出的所有包更新到最新版本(由标签配置指定),尊重 semver。

它还会安装丢失的软件包。与所有安装包的命令一样, --dev 标志也会导致 devDependencies 被处理。

由于您的软件包是使用固定版本定义的,因此 update 子命令不会更新这些软件包以尊重 semantic versioning。因此,如果您为每个包指定更大的版本范围,它只会自动更新您的包。请注意,在 npm 项目中,指定松散范围版本实际上是很典型的;一种旨在避免破坏性更改但仍留有改进和修复空间的方法。

不过,为什么我不应该在我的 package.json 中修复依赖版本?

但它们是固定的,因为我想要它们。测试新版本后,我想通过命令行更新它们。

拥有一个具有固定版本的依赖项列表并不意味着安装的依赖项总是相同的,因为您的依赖项的依赖项很可能也使用版本范围来定义。为了跟踪经过测试的带有版本标签的依赖项列表,npm 提供了另一种机制:package locks

在 npm 版本 5 之前,您可以使用 shrinkwrap 命令创建“npm-shrinkwrap.json”文件:

npm 收缩包装

此命令锁定软件包依赖项的版本,以便您可以准确控制安装软件包时将使用每个依赖项的哪些版本。

从 npm 5 开始,当 npm 操作修改“node_modules”树或“package.json”时,会自动生成一个“package-lock.json”。

除了修改 package.json 之外,这些包锁中的任何一个都将覆盖 npm install 的默认行为,在创建或手动更新它们时使用锁指定的版本安装依赖项。有了这些,您的依赖项现在可以扩展,而不会有依赖项安装未经测试的软件包版本的风险。

Shrinkwraps 用于发布包。收缩包装:

  1. 在包根目录下运行npm install,安装所有依赖的当前版本。
  2. 验证包在这些版本中是否按预期工作。
  3. 运行npm shrinkwrap,将 npm-shrinkwrap.json 添加到 git,然后发布你的包。

此时,可以在你的 package.json 中放宽依赖版本(希望每次主要依赖更新只进行一次),以便以后可以使用 npm update 随意更新它们:

"devDependencies": {
   "someFixedVersionPackage": "^1.0.0",
   "anotherFixedVersionPackage": "^2.3.2",
}

package-lock.json 文件可以代替shrinkwrap,更适合复现开发环境。它也应该提交到存储库。

那么我该如何更新我的依赖呢?

调用npm update 将执行上述操作:在尊重语义版本控制的同时更新依赖项。在包中添加或升级依赖项:

  1. 在包根目录下运行npm install,安装所有依赖的当前版本。
  2. 添加或更新依赖项。 npm install --save 每个新的或更新的包单独更新 package.json,以及现有的包锁(“package-lock.json”和“npm-shrinkwrap.json”)。请注意,它们必须明确命名才能安装:不带参数运行 npm install 只会重现锁定的依赖项。
  3. 验证包是否可以使用新的依赖项按预期工作。
  4. 提交新的包锁。

此外,以下是从具有固定依赖项的项目平稳过渡的一些技巧:

  • 如果您还没有这样做,请通过在版本说明符之前添加波浪号 (~) 或插入符号 (^) 来扩展版本范围。然后npm update 将尝试分别安装所有补丁修订版和次要修订版(主要版本0 是一个极端情况,请参阅文档)。例如,“^1.0.0”现在可以更新为“^1.1.0”,“~2.3.2”可以更新为“~2.3.4”。添加--save--save-dev 标志也会使用已安​​装的版本更新“package.json”(同时保留以前的范围说明符)。

  • 运行 npm outdated 以检查哪些包已过时。红色条目将自动更新为npm update。其他条目需要人工干预。

  • 对于具有主要版本问题的软件包,请使用版本规范(例如 npm install browserify@11.2.0 --save-dev)安装该软件包。更新可能出现的其他问题必须手动处理。阅读新闻提要或该软件包的发布历史记录通常有助于进一步了解与以前版本相比有何变化。

这还不够简单,还有其他方法吗?

在继续之前,始终值得一提的是,软件包具有符合 SemVer 的版本定义是有原因的。应避免盲目安装每个软件包的最新版本。尽管有这样一个完整的更新can be done 和工具可用,但还是建议谨慎行事。例如,如果剩余的 React 组件和库与 react@15.x.x 不兼容,您就不想安装 React 15。另见 npm 的博文:Why use SemVer?

我会抓住机会的。还有哪些其他工具?

仅举几例:

  • npm-check-updates 将执行问题中最初提出的问题:安装和更新所有依赖项的版本,而不管给定的范围约束如何。然而,这将是最不推荐的工作工具。
  • updtr 会一一更新依赖,如果项目测试失败,会回滚到之前的版本,这样可以节省测试覆盖率好的项目的时间。
  • npm-check 提供交互式命令行界面,让您可以轻松选择要更新的软件包。

这与 npm 5 有什么不同吗?

从major version 5开始,npm会自动创建一个"package-lock.json",当一个shrinkwrap不存在时,它会起到指定依赖树的作用。更详细的描述可以在package-locks documentation 中找到。一般来说,npm-shrinkwrap.json 是在发布时使用的,而 package-lock.json 是在开发中使用的。这就是为什么您还应该将“package-lock.json”提交到存储库的原因。

Yarn 怎么样?

Yarn,一个与 npm 兼容的依赖管理器,在使用时自动创建一个锁定文件,其行为类似于 npm 收缩包装。调用yarn upgrade «package» 会将一个依赖更新为latest 标签中的版本,无论package.json 或lock 文件中记录的版本范围如何。使用yarn upgrade-interactive 还允许您有选择地将软件包升级到最新版本,这与npm-check 不同。

$ yarn outdated
yarn outdated v0.16.1
Package      Current Wanted Latest
babel-eslint 7.0.0   7.0.0  7.1.0 
chai         3.0.0   3.0.0  3.5.0 
Done in 0.84s.
$ yarn upgrade babel-eslint chai
yarn upgrade v0.16.1
[1/4] Resolving packages...
[2/4] Fetching packages...
[3/4] Linking dependencies...
[4/4] Building fresh packages...
success Saved lockfile.
success Saved 2 new dependencies.
├─ babel-eslint@7.1.0
└─ chai@3.5.0

【讨论】:

  • 依赖的固定版本是另一回事。它们是固定的,因为我想要它们。测试新版本后,我想通过命令行更新它们。
  • 因此,您希望保留经过测试的版本标记依赖项列表,同时仍允许 npm 更新它们。我会尽快更新答案,但目前,看看shrinkwrap 是否适合你。
  • 不,我希望通过命令行将固定版本更新到最新版本,也已修复。我会将 package.json 文件中的预期输出添加到问题中,以便完全清楚。
  • @Francisc 一开始就已经很清楚了。请查看我的更新。
  • 不幸的是,手动锁定项目可以防止设计错误的不尊重 semver 的包进入您的构建。这就是我们在能够测试依赖项时使用 npm-check-updates 升级依赖项的原因。
【解决方案2】:

运行以下命令会做你想做的事:

npm install someFixedVersionPackage@latest anotherFixedVersionPackage@latest --save-dev --save-exact

细分:

  • npm install someFixedVersionPackage@latest 将安装最新版本的软件包
  • --save-dev 标志将导致它更新您的package.jsondevDependencies 中的版本
  • --save-exact 标志将导致它保存固定版本而不是 semver 范围运算符

链接到npm install docs

【讨论】:

  • 我不想保存一个精确的版本,我想保存一个范围,就像 install 一样(假设 save-exact 在.npmrc 中没有设置为 true)。这种方法的另一个问题是冗长,键入每个包名称需要很长时间。
  • 您在问题中给出的示例显示了保存在 package.json 中的确切版本。删除 --save-exact 将保存一个范围。同意指定所有包是冗长的。如果您只想更新所有内容并设置范围,那么我所知道的唯一方法是使用 npm 工具,例如 npm-check-updates
  • 它们是使用--save-exact 保存的。我想知道是否有办法通过 npm 覆盖 package.json 中的内容。我会看看你发布的链接。
  • 能够自动覆盖依赖项的固定版本只会首先破坏使用固定版本的目的。
【解决方案3】:

长期以来,我一直在寻找一种简单的方法来更新 npm 依赖项。然后我找到了这个工具:https://github.com/dylang/npm-check

它会在漂亮的 ui 中向您显示哪些依赖项已过期,并允许您更新它们。它甚至会告诉您哪些可能由于重大更改而中断,并警告您未使用的依赖项。

【讨论】:

    猜你喜欢
    • 2019-08-01
    • 2015-06-06
    • 1970-01-01
    • 2016-01-06
    • 2016-07-21
    • 1970-01-01
    • 2021-11-28
    • 2020-04-30
    • 2023-04-06
    相关资源
    最近更新 更多