私は現在この壁に戸惑っていますが、エラーが見つからないようですが、Rubyのブロックスコープのルールと関係していると思います。私はここでかなりの数の記事を読んだことがありますが、私は経験している問題と似ていないようです(あるいは、あまりにも見苦しいかもしれません)。 setter/gettersが定義されているインスタンス変数(ホスト名とOS)が2つしかないServerオブジェクトがあります。Rubyブロック変数スコープの問題?
問題は、sshチャネルデータを読み取っているブロックの途中にServerオブジェクトのOSを定義することです。私は、スクリプトを実行すると正しいデータを持っていることを知っています。しかし、ch.execブロックの最後に到達すると、Server.getOSはnilに戻ってしまいます。
アイデア?
注&コード: "hosts"はServerオブジェクトの配列です。
hosts.each do |server|
begin
Net::SSH.start(server.getHostname, user , :password => password , :port=> port) do |ssh|
channel = ssh.open_channel do |ch|
ch.exec "uname" do |chan, success|
raise "could not execute uname command" unless success
chan.on_data do |c, data|
server.setOS = data
puts "local OS: #{server.getOS}"
# server.getOS = "AIX" here
end
chan.on_extended_data do |c, type, data|
puts data
end
end
puts "OS: #{server.getOS} -- hostname: #{server.getHostname}"
# server.getOS = "" here..
..そこからserver.getOSに基づいて処理が開始されますが、server.getOSはnilです。
"ブロックされていることを保証していません。すぐに実行されます。"それが本当であれば、どのような手順が意図どおりに動作することを保証しますか?私はおそらくあなたを誤解していますが、そのコメントはRubyがブロックを動かして無作為に実行するようなものです。 2 + 3 * 6は常に20になるはずです。 –
@tadman torontoのレール市場はどうですか? – codecompleting
Rubyブロックをメソッドに提供すると、そのブロックが実行されるかどうか、実行されるタイミングはわかりません。メソッドが提供する "契約"に精通し、それに応じて行動する必要があります。例えば、反復子はあなたのメソッドをすぐにN回実行しますが、ほとんどの非同期コールバックメソッドは一度呼び出されますが、何らかの条件のためにメソッドがいつ実行されないかはわかりません。それは無作為ではなく、ほとんど予測可能ですが、一度ブロックを指定すると、それが呼び出された方法に関して与えられたメソッドを慈悲にしています。 – tadman