Ruby 2.5.0+Rails5.1.6项目bundle install时json1.8.0安装失败求助
Ruby 2.5.0 + Rails 5.1.6环境下bundle install失败的原因与解决办法
先来看你遇到的具体错误输出:
Fetching gem metadata from http://rubygems.org/.......... Using rake 0.8.7z Using abstract 1.0.0 Using activesupport 3.0.7 Using builder 2.1.2 Using i18n 0.5.0 Using activemodel 3.0.7 Using erubis 2.6.6 Using rack 1.2.8 Using rack-mount 0.6.14 Using rack-test 0.5.7 Using tzinfo 0.3.37 Using actionpack 3.0.7 Using mime-types 1.23 Using polyglot 0.3.3 Using treetop 1.4.14 Using mail 2.2.20 Using actionmailer 3.0.7 Using arel 2.0.10 Using activerecord 3.0.7 Using activeresource 3.0.7 Using addressable 2.3.4 Fetching json 1.8.0 Installing json 1.8.0 with native extensions Gem::Ext::BuildError: ERROR: Failed to build gem native extension. current directory: /home/daniele/.rvm/gems/ruby-2.5.0/gems/json-1.8.0/ext/json/ext/generator /home/daniele/.rvm/rubies/ruby-2.5.0/bin/ruby -r ./siteconf20180512-28287-pzwgum.rb extconf.rb creating Makefile current directory: /home/daniele/.rvm/gems/ruby-2.5.0/gems/json-1.8.0/ext/json/ext/generator make "DESTDIR=" clean current directory: /home/daniele/.rvm/gems/ruby-2.5.0/gems/json-1.8.0/ext/json/ext/generator make "DESTDIR=" compiling generator.c In file included from generator.c:1:0: ../fbuffer/fbuffer.h: In function ‘fbuffer_to_s’: ../fbuffer/fbuffer.h:175:47: error: macro "rb_str_new" requires 2 arguments, but only 1 given VALUE result = rb_str_new(FBUFFER_PAIR(fb)); ^ ../fbuffer/fbuffer.h:175:20: warning: initialization makes integer from pointer without a cast [-Wint-conversion] VALUE result = rb_str_new(FBUFFER_PAIR(fb)); ^ generator.c: In function ‘generate_json’: generator.c:840:25: error: ‘rb_cFixnum’ undeclared (first use in this function) } else if (klass == rb_cFixnum) { ^ generator.c:840:25: note: each undeclared identifier is reported only once for each function it appears in generator.c:842:25: error: ‘rb_cBignum’ undeclared (first use in this function) } else if (klass == rb_cBignum) { ^ generator.c: At top level: cc1: warning: unrecognized command line option ‘-Wno-self-assign’ cc1: warning: unrecognized command line option ‘-Wno-constant-logical-operand’ cc1: warning: unrecognized command line option ‘-Wno-parentheses-equality’ cc1: warning: unrecognized command line option ‘-Wno-tautological-compare’ Makefile:241: set di istruzioni per l'obiettivo "generator.o" non riuscito make: *** [generator.o] Errore 1 make failed, exit code 2 Gem files will remain installed in /home/daniele/.rvm/gems/ruby-2.5.0/gems/json-1.8.0 for inspection. Results logged to /home/daniele/.rvm/gems/ruby-2.5.0/extensions/x86_64-linux/2.5.0/json-1.8.0/gem_make.out An error occurred while installing json (1.8.0), and Bundler cannot continue. Make sure that `gem install json -v '1.8.0'` succeeds before bundling. In Gemfile: airbrake was resolved to 3.1.12, which depends on json
错误原因分析
核心问题是json 1.8.0版本过于老旧,完全不兼容Ruby 2.5.0的底层API变更:
- Ruby 2.5.0调整了
rb_str_new的调用规则,从原来的1个参数改成需要2个参数,但json 1.8.0的C扩展代码还在沿用旧写法,直接导致编译报错。 - Ruby 2.5.0将
rb_cFixnum和rb_cBignum两个常量合并为rb_cInteger,老版本json gem的代码仍在引用这两个已被移除的常量,所以编译时提示未声明。
另外你本地环境是Ruby 2.5.0 + Rails 5.1.6,但从安装的gem来看,你下载的GitHub项目实际是基于Rails 3.0.7的老项目,依赖的airbrake 3.1.12又强制绑定了json 1.8.0,这就造成了新Ruby版本与旧gem的兼容性冲突。
解决办法
以下是几个可行方案,按推荐程度排序:
方案1:升级airbrake版本(最优解)
airbrake 3.1.12是非常老旧的版本,你可以在Gemfile里将其升级到支持Ruby 2.5的版本,比如:
gem 'airbrake', '~> 6.0'
然后执行命令更新依赖:
bundle update airbrake
这样bundler会自动安装兼容Ruby 2.5的json版本,彻底解决编译问题。
方案2:直接指定兼容的json版本
如果不想升级airbrake,可以尝试在Gemfile里直接指定兼容Ruby 2.5的json版本,比如json ~> 2.1.0:
- 在Gemfile末尾添加:
gem 'json', '~> 2.1.0'
- 执行命令强制更新json:
bundle update json
注意:这种方式可能存在与airbrake 3.1.12的兼容性风险,如果运行时出现报错,还是建议采用方案1。
方案3:降级Ruby版本(不推荐)
如果项目必须保留所有旧gem版本,只能降级Ruby到兼容json 1.8.0的版本(比如Ruby 2.3.x,因为Ruby 2.4开始已有API变更)。用rvm操作如下:
rvm install 2.3.8 rvm use 2.3.8 --default
之后重新执行bundle install即可正常编译json 1.8.0,但Ruby 2.3已停止维护,存在安全风险,不建议长期使用。
内容的提问来源于stack exchange,提问作者cricket
相关产品推荐
相关产品推荐

