2016-10-13 8 views
2

多くの外部の宝石を使用するThor CLIアプリケーションを構築しました。私はそれを実行すると、私は出力を乱雑にそれらの宝石から警告メッセージが表示されます - どのように私はこれを抑制することができますか?Thor CLIアプリケーションで警告メッセージを表示しない

明確化:私だけ警告メッセージを抑制したいが、それでもエラーやputs結果を含めて私のアプリのための標準出力を、受け取ります。

たとえば、Sinatraアプリケーションでこれらの同じ宝石を使用すると、私はThorと同じように宝石のコードからすべての警告メッセージが出ることはありません。この場合

http://willschenk.com/making-a-command-line-utility-with-gems-and-thor/由来)実施例

require 'thor' 
require 'safe_yaml' 

module Socialinvestigator 
    class HammerOfTheGods < Thor 
    desc "hello NAME", "This will greet you" 
    long_desc <<-HELLO_WORLD 

    `hello NAME` will print out a message to the person of your choosing. 

    HELLO_WORLD 
    option :upcase 
    def hello(name) 
     greeting = "Hello, #{name}" 
     greeting.upcase! if options[:upcase] 
     puts greeting 
    end 
    end 
end 

、我々はsafe_yaml宝石を必要としているので、我々は、コマンドを実行するたびに、我々は我々の出力に次の警告を取得します:

/usr/local/lib/ruby/gems/2.3.0/gems/safe_yaml-1.0.4/lib/safe_yaml.rb:28: 警告:メソッドが再定義。古いsafe_loadを破棄する /usr/local/Cellar/ruby/2.3.0/lib/ruby/2.3.0/psych.rb:290:警告: safe_loadの以前の定義はここにありました /usr/local/lib/ruby​​/gems/2.3.0/gems/safe_yaml-1.0.4/lib/safe_yaml.rb:52: 警告:メソッドが再定義されました。古いLOAD_FILE /usr/local/Cellar/ruby/2.3.0/lib/ruby/2.3.0/psych.rb:470を捨てる:警告:LOAD_FILEの 以前の定義は、ここで我々が使用している

ましたいくつかの異なる宝石と私たちの出力を混乱させる警告の全体の配列を得る...

+0

これについて再生するコード例があるといいですか? –

+0

[KISS](https://en.wikipedia.org/wiki/KISS_principle)解決策:警告を修正してください。 – Blacksilver

答えて

1

まず、プルリクエストを提出し、依存関係のメッセージを抑制するか、宝石の開発者にそれはあなたのためです

それ以外のこれは私が以前使っていたものです - おそらくどこかのSO(またはインターネット

したがって、ノイズの多いメソッドをsilenceメソッドでラップすると、単にSTDOUTをStringIOオブジェクトにプッシュしてから、STDOUTに戻すだけです...

require 'stringio' 
def silence 
    $stdout = temp_out = StringIO.new 
    yield 
    temp_out.string 
ensure 
    $stdout = STDOUT 
end 

out = silence { run_dependency_method } 
puts out # if in dev mode etc... 
+0

また、http://stackoverflow.com/questions/1496019/suppresing-output-to-console-with-rubyを参照してください –

+0

私の悪い私は明確ではなかった。私はまだ標準出力が必要です、私は宝石から出てくる警告メッセージを望んでいません。上記の私の編集を参照してください... – Yarin

0

@Yarin、

@イスマイル答えにフォローアップ、あなたが単語「警告」を含むメッセージをフィルタリングするsilenceメソッド内で新しい「一時的」にStringIOをオーバーロードすることで、このソリューションを拡張することができます。

はここに例を示します

require 'stringio' 

class FooIO < StringIO 
     def puts s 
       super unless s.start_with? "WARN" 
     end 
end 

def silence 
    $stdout = temp_out = FooIO.new 
    yield 
    temp_out.string 
ensure 
    $stdout = STDOUT 
end 

def foo 
     puts "INFO : Hello World!" 
     puts "WARN : Oops.. This is a warning..." 
     puts "ALRT : EVERYONE IS GOING TO DIE!!!" 
end 

out = silence { foo } 

puts out 
0

Rubyは出力のverbosenessを定義するグローバル変数を持っています。nilは何の警告を意味し、false「ノーマル」モードとtrueは余分な冗長です(ruby --verboseを実行するのと同じいくつかの追加のランタイム情報を、追加):

def without_warnings 
    verboseness_level = $VERBOSE 
    $VERBOSE = nil 

    yield 
ensure 
    $VERBOSE = verboseness_level 
end 

# Doesn't show warnings about overwriting the constant 
without_warnings do 
    Foo = 42 
    Foo = 'bar' 
end 

# Still shows normal output 
without_warnings { puts 42 } 

# Still shows and throws errors 
without_warnings { raise 'wtf' } 

あなたがプログラムする方法を管理している場合Rubyの-Wフラグの代わりに、それぞれの値が0,1または2(この場合はruby -W 0)を使用することができます。

関連する問題