TracePoint是一款跟踪Ruby代码的工具,可以细粒度的监控Ruby程序,但是只支持2.0.
基础知识
一个简单的例子
非tracepoint的例子
tracer = lambda do |event, file, line, id, binding, klass| to_display = [event, File.basename(file), line, klass, id] puts "%10s in %s at line %-2d %s:%s" % to_display end set_trace_func tracer
klass 是 类名 id 是方法名
TracePoint的例子
trace = TracePoint.new(:raise) do |tp| p [tp.lineno, tp.event, tp.raised_exception] end trace.enable # or trace.disable 0/0
基本范式
TracePoint.new(Event) do |tp| # tp 是一个 TracePoint 对象,有此刻正在运行的程序的所有的信息,包括事件等 end
Events
class level
TracePoint.new(:module) TracePoint.new(:class) TracePoint.new(:end)
method level
:call :return :c_call :c_return
block level
:b_call :b_return thread level :thread_begin :thread_end
other level
TracePoint的实例方法
控制方法
disable enable disable? enable?inspect # 返回关于tracepoint status字符串
获取调用类和方法
defined_class # 类名称 meethod_id # 方法名称 raise_exception # 抛出的异常 return_value # 方法的返回值
其他
event # 当前trigger的事件 lineno # 运行的行数 path: 该运行的文件的位置
结合Rails
使用rack middleware 整合如 Rails
# update application.rb # config.middleware.insert_before(ActionDispatch::Static, TracePoint::Middleware) class TracePoint class Middleware def initialize(app) @app = app end def call(env) stats = {} trace = TracePoint.new(:call) do |tp| stats[tp.defined_class] ||= {} stats[tp.defined_class][tp.method_id] ||= 0 stats[tp.defined_class][tp.method_id] += 1 end trace.enable response = @app.call(env) trace.disable puts env['PATH_INFO'] puts "#{stats.keys.size} classes used" puts "#{stats.map{|k,v| v.keys}.flatten.size} methods used" puts "#{stats.map{|k,v| v.values}.flatten.sum} methods dispatched" #File.open("tmp/#{env['PATH_INFO'].gsub('/', '_')}_req_stats.json", "w"){|f| f << stats.to_json } puts "" response end end end
https://gist.github.com/chucai/8037079
参考资料
http://www.slideshare.net/markykang/mangling-ruby-withtracepoint https://www.youtube.com/watch?v=V_dZQ6AeZDE http://www.ruby-doc.org/core-2.0.0/TracePoint.html http://matt.aimonetti.net/posts/2013/03/05/inspecting-rails-4-request-dispatch-using-ruby-2-dot-0/