Forum: Ruby-dev Net::HTTP、ZlibとFiberError

Bdcb9af0b168cf425bac2d3772164bee?d=identicon&s=25 Masatoshi SEKI (Guest)
on 2014-02-10 17:40
(Received via mailing list)
咳といいます。

Net::HTTP#requestをブロック付きで呼び出し、ブロックの中で
Net::HTTPResponse#read_bodyをブロック付きで呼び出しています。

例えばこんな雰囲気。

    oauth.request(:GET, 'https://userstream.twitter.com/2/user.json') do
|r|
      r.read_body do |chunk|
        json.push(chunk) # ←ここ
      end
    end

内側のブロックの中でFiberを切り替えると次のようなFiberError例外が発生します。

Exception `FiberError' at drip_tw.rb:36 - fiber called across stack
rewinding barrier
Exception `Zlib::BufError' at
/usr/local/lib/ruby/2.2.0/net/http/response.rb:357 - buffer error
Exception `Zlib::BufError' at /usr/local/lib/ruby/2.2.0/net/http.rb:1442
- buffer error
/usr/local/lib/ruby/2.2.0/net/http/response.rb:357:in `finish': buffer
error (Zlib::BufError)
  from /usr/local/lib/ruby/2.2.0/net/http/response.rb:357:in `finish'
  from /usr/local/lib/ruby/2.2.0/net/http/response.rb:262:in `ensure in
inflater'
  from /usr/local/lib/ruby/2.2.0/net/http/response.rb:262:in `inflater'
  from /usr/local/lib/ruby/2.2.0/net/http/response.rb:274:in
`read_body_0'
  from /usr/local/lib/ruby/2.2.0/net/http/response.rb:201:in `read_body'
  from drip_tw.rb:180:in `block in drip_stream'
  from /usr/local/lib/ruby/2.2.0/net/http.rb:1415:in `block (2 levels)
in transport_request'
  from /usr/local/lib/ruby/2.2.0/net/http/response.rb:162:in
`reading_body'
  from /usr/local/lib/ruby/2.2.0/net/http.rb:1414:in `block in
transport_request'
  from /usr/local/lib/ruby/2.2.0/net/http.rb:1405:in `catch'
  from /usr/local/lib/ruby/2.2.0/net/http.rb:1405:in `transport_request'
  from /usr/local/lib/ruby/2.2.0/net/http.rb:1378:in `request'
  from /usr/local/lib/ruby/2.2.0/net/http.rb:1371:in `block in request'
  from /usr/local/lib/ruby/2.2.0/net/http.rb:853:in `start'
  from /usr/local/lib/ruby/2.2.0/net/http.rb:1369:in `request'
  from drip_tw.rb:118:in `request'
  from drip_tw.rb:179:in `drip_stream'
  from drip_tw.rb:298:in `<main>'


Rubyのバージョンはruby 2.2.0dev (2014-02-10 trunk 44902) [x86_64-darwin13.0]。
1.9系の頃は動いていたスクリプトです。
Fiberと同様な動作をするThread版を使うと例外は発生しません。

Zlibがrb_protect()しているときにFiberを切り替えているってことでしょうか?(勘)



再現させる最小のコードになってないし実行の準備がめんどくさいけど、件のコードはこちらです。

https://github.com/seki/Drip/blob/master/sample/drip_tw.rb
(178行目のDripFiberをDripThreadにするとThread版になります)
This topic is locked and can not be replied to.