0

在我工作的地方,我们开发了几个 Ruby Gems 供内部使用。它们都依赖于我们自己的内部 gem 以及来自 RubyGems.org 的第三方 gem 的各种组合。

当我们使用构建服务器 (ElectricCommander) 进行更改时,我们会自动构建我们的 gem,该服务器将它们打包为 gem 并将它们存储在内部存储库中。作为该过程的一部分,我们运行bundle package --all. 直到上周,这对我们所有的宝石都完美无缺。

上周,我们的一个 gem 开始花费 1 多小时来运行 bundle package 命令。它运行成功,但只需要一个多小时即可完成,这有点荒谬。

在我们的其他 gem 构建中,bundle package 命令在更可观的一分钟左右运行得很好。每个 gem 包含的依赖项数量没有太大差异。它们都构建在相同的环境中。

我们正在把头发拉出来。谷歌搜索没有发现任何有同样问题的人。有没有人遇到过这个问题,或者有人知道可能是什么原因造成的吗?

4

2 回答 2

2

Bundler 非常努力地寻找一组满足您的捆绑包要求的 gem,但在某些情况下,此搜索可能需要很长时间。根据 Gemfile 中 gem 的顺序、您提供的约束以及在其他 gem 中遇到的依赖关系,Bundler 可能需要回溯解析过程并重新解析一些 gem。在最坏的情况下,这可能需要指数级的时间。

Pat Shaughnessy 在Bundler 如何捆绑?. 正如他所提到的,在环境中运行 BundlerDEBUG_RESOLVER=1可以帮助向您展示正在发生的事情。

您可以通过更改 Gemfile 中 gem 的顺序或使用 Shadwell 建议的更具体的版本约束来解决这些问题。

于 2013-08-01T11:57:27.577 回答
2

当有问题的 gem 依赖于另一个 gem 时,我遇到过类似的问题,该 gem 既有多个版本,又有许多其他依赖项。在我们的 gem 中,我们将另一个 gem(它是 rails)作为依赖项,而不依赖于特定版本。

所以我们有:

s.add_runtime_dependency "rails"

当我们添加一个版本时,我们看到捆绑速度显着提高:

s.add_runtime_dependency "rails", "~>3.2"

使用绝对严格的版本,它甚至更快:

s.add_runtime_dependency "rails", "3.2.14"

我相信,缓慢的原因是它会查看与 gemspec 中的依赖项匹配的所有 gem 版本的所有依赖项。正如您可以想象的那样,使用一个已经存在了一段时间并且本身具有许多其他依赖项的 gem,这可能会导致相当多的环顾四周。

于 2013-07-30T21:10:16.483 回答