【问题标题】:iconv deprecation warning with ruby 1.9.3ruby 1.9.3 的 iconv 弃用警告
【发布时间】:2011-12-30 05:31:34
【问题描述】:

我在运行 rspec 时收到此警告:

/gems/activesupport-3.1.0/lib/active_support/dependencies.rb:240:in `block in require': iconv 将在未来被弃用,使用 String#encode 代替。

我在使用 rails 3.1.03.1.13.1.2.rc2 版本时收到相同的警告。似乎它与sqlite3 gem 有关,但我不确定。 ruby 1.9.2 没有警告

有什么建议可以解决吗?

【问题讨论】:

    标签: ruby-on-rails ruby rspec


    【解决方案1】:

    要删除此警告...

    转到您的 .rvm 目录并找到 iconv.c(我的是 ~/.rvm/src/ruby-1.9.3-p125/ext/iconv/iconv.c

    编辑该文件,删除或注释掉对warn_deprecated()的调用(应该在底部附近)

    从该文件的目录,运行ruby extconf.rb 然后make 然后make install

    应该做的伎俩

    【讨论】:

      【解决方案2】:

      如果您看到这个,很可能不是 Rails。如果您查看您发布的错误中引用的行周围的方法,您将看到以下内容:

      def require(file, *)
        result = false
        load_dependency(file) { result = super }
        result
      end
      

      我并不是说它一定是你的代码,但我确信它实际上不是调用 iconv 的行。就我而言,我发现我的项目代码实际上包含对 iconv 的引用。

      如果您想检查您的代码中是否有此类参考,请在您的项目目录中尝试grep -ir iconv ./

      iconv 实际上在一个库中时,它可能更难找到。通过暂时将上述方法更改为:

      def require(file, *)
        result = false
        puts
        puts caller.reverse
        load_dependency(file) { result = super }
        result
      end
      

      然后,您可以轻松地运行您的代码并用 grep 查找回溯的相关行以找到警告的根本原因。

      ruby your/code.rb 2>&1 | grep -B 5 iconv
      

      【讨论】:

      • 只需在 load_dependency 行之前的一行中添加“p caller”并查看堆栈跟踪,就可以很容易地打乱您的 Gemfile 并修复过期的 gem。
      • 我认为最简单的方法是在load_dependency之前添加puts ">>>> #{file.inspect}",然后您可以看到是哪个文件加载导致了该消息。
      【解决方案3】:

      您收到此弃用通知是因为某处的某个库需要 iconv

      iconv 是由Matz 创建的 gem,可用于将字符串从一种格式转换为另一种格式。

      例如经常使用这个:

      Iconv.iconv('UTF-8//IGNORE', 'UTF-8', content) 这个小魔法将一个可能包含无效字符的 UTF-8 字符串转换为正确的 UTF-8 字符串。

      已经决定在 Ruby 1.9.3 中我们不应该再使用 iconv 而是使用内置的String#encodeencode 更强大,让您更灵活。

      理论上,上面的例子可以替换为:

      string.encode("UTF-8", :invalid => :replace, :undef => :replace, :replace => "?")

      实际上,这似乎是imperfect

      对于希望支持 1.8 的宝石创建者来说,这也导致了一个不太容易的故事:

      content = RUBY_VERSION.to_f < 1.9 ? 
        Iconv.iconv('UTF-8//IGNORE', 'UTF-8',  "content") :
        "#{content}".encode(Encoding::UTF_8, :invalid => :replace, :undef => :replace, :replace => '')
      

      所以,你有一个宝石需要 iconv 才能找到它:

      假设你的错误信息是:/gems/activesupport-3.1.0/lib/active_support/dependencies.rb:240

      在第 240 行打开/gems/activesupport-3.1.0/lib/active_support/dependencies.rb

      添加行:

      p caller if file =~ /iconv/
      

      (紧随其后:load_dependency(file) { result = super }

      你会得到一个很大的堆栈跟踪:

      耙--任务 /home/sam/.rvm/gems/ruby-1.9.3-p125/gems/activesupport-3.2.6/lib/active_support/dependencies.rb:251:in `block in require': iconv 将在未来被弃用,请改用 String#encode。 ["/home/sam/.rvm/gems/ruby-1.9.3-p125/gems/calais-0.0.13/lib/calais.rb:5:in `'", ..更多省略..

      这告诉我它是calais gem。查看拉取请求,我am not the first。拉力尚未拉入。


      根据gem的不同,可能有升级版本没有这个错误,所以我建议你先升级你的gem。如果你不走运,你可能会被困在 fork 一个 gem 以摆脱这个不幸的任务(例如,如果你修复它的 pull request 失败了)

      【讨论】:

      • 谢谢,这对我有帮助。我在 ActiveSupport 3.2.9 上,不得不使用:p caller if file.to_s =~ /iconv/(文件现在是 Pathname 而不是字符串。)
      • 这是一个很好的答案!我按照这些步骤找到了导致我的应用程序出现问题的 gem。很遗憾原始发帖人没有接受这个答案......或任何其他的答案。
      • 这是一个很棒的答案,也是如何编写 SO 答案的模型。清晰、简洁的解释和易于遵循的步骤来调试问题。
      【解决方案4】:

      您可以通过为 ActiveSupport::Deprecation 生成异常来确定警告的确切位置,而不仅仅是打印到日志中。在 application.rb 的顶部:

      ActiveSupport::Deprecation.behavior = Proc.new do |message, backtrace|
        raise message
      end
      

      一旦您确定了警告的来源(通过检查完整的回溯),请再次删除它。

      【讨论】:

      • 我得到undefined method behaviour= for ActiveSupport::Deprecation:Module (NoMethodError) -- Rails 3.2.3,Ruby 1.9.3-p125
      • 显然它使用了美国拼写——“行为”。
      • 嗯.. 似乎没有引发异常。我在require 'rails/all' 之后得到了它。
      【解决方案5】:

      将此添加到程序的开头:

      oldverb = $VERBOSE; $VERBOSE = nil
      require 'iconv'
      $VERBOSE = oldverb
      

      并诅咒那些认为这是处理弃用的专业方法的人。

      【讨论】:

      • 我不明白为什么这被否决了这么多。如果您已经意识到但不愿意升级,这是一种使其静音的方法。如果你把它放在其他requires 之前,可能会在一些深层嵌套的require 链中拉入iconv,那么该消息将不会再次出现。
      • 完美答案。这帮助我在我完全无法控制已安装的 gem 或任何东西的系统上摆脱了这个无用的警告。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-03-25
      • 2020-09-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多