1

Rails 3.2.14 の使用。次のように、コントローラーのアクション応答をストリーミングしています。

def my_controller_action
    stream = StreamingClass.new(*args) #responds to each
    response.sending_file= true
    headers.merge!(
      'Content-Disposition'       => 'inline',
      'Content-Transfer-Encoding' => 'binary',
      'Cache-Control'             => 'no-cache'
       )
       self.status = 200
    self.content_type= 'application/json'
    self.response_body = stream
end

ストリーミングは問題なく動作しますが、問題は、ストリーミングが完了する前 (つまり、それぞれが「ストリーム」オブジェクトで呼び出される前) にコントローラーのアクションが返されることです。「ストリーム」オブジェクトを self.response_body に代入すると、基本的にすぐに戻ります。

ロギングを整理するために lograge gem を使用しています。Lograge は基本的に「process_action.action_controller」通知をサブスクライブします。ストリーム オブジェクト コードに費やされた時間を追跡せずに、実際のコントローラーの戻り時間に基づいてタイミング (期間、db_runtime など) を記録しています。

大変な作業は StreamingClass メソッドで発生しますが、ログからこの情報が完全に失われています。ログにストリーミング応答のタイミングを含める方法はありますか?

4

1 に答える 1

0

私もこの同じ問題に遭遇しています。ストリーミングがいつ完了したかを知る唯一の方法は、必要な統計を記録する追加のロジックをメソッドに含むresponse_bodyプロキシ オブジェクトにラップすることだと思います。closeおそらく次のようなものを使用できます。

class BodyProxy
  def initialize(body)
    @body = body
  end

  def each(&block)
    @body.each(&block)
  end

  def close
    @body.close if @body.respond_to?(:close)
    # Your code here. Probably something involving `Time.now`
  end
end

これが機能するのは、Rack の仕様closeでは、"反復後に" 本体で呼び出す必要があるためです。

私は Lograge に慣れていないので、この情報をその gem に送信する方法はわかりませんが、始めるにはこれで十分です。

于 2014-06-02T20:44:56.113 に答える