如何记录在Ruby程序中调用的每个方法? [英] How do I log every method that's called in a Ruby program?

查看:92
本文介绍了如何记录在Ruby程序中调用的每个方法?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

坦率地说,我继承了一大堆Ruby代码,对于像我这样的凡人来说,这几乎是不可能理解的.它实际上是Rspec单元测试代码,但说得很好,其结构非常不寻常".

I've inherited a large pile of Ruby code that's, frankly, close to impossible to understand for a mortal like myself. It's actually Rspec unit test code, but the structure is "highly unusual" to put it nicely.

我想做的是运行代码,并在某处记录以下信息:

What I'd like to be able to do is run the code, and have the following information logged somewhere:

  • 每个被调用的方法,包括定义该方法的类的名称,以及已定义被调用方法的文件名(是的,我们在多个不同的文件中定义了相同的类/方法,很难知道正在调用哪个)
  • (可选)传递给调用的每个方法的参数

有了这个,我可以开始尝试重构它.如果没有它,由于代码库(20k +单元测试用例)的大小,要弄清楚它将是一个非常困难的任务.

With that, I could start trying to refactor it. Without it, it's going to be a very difficult task to get it straightened out, due to the size of the code base (20k+ unit test cases).

我无法对正在运行的代码进行大规模编辑,因为当您甚至在周围使用苛刻的语言时(即频繁使用),它就会中断.相反,我需要能够在现有状态下对代码进行检测,或者对现有状态进行最小的改动.

I can't afford to go in and perform wholesale edits to the code being run, because it breaks when you even use harsh language around it (i.e. frequently). Instead, I need to be able to instrument the code in its existing state, or with minimal changes to what exists now.

是否有一种方法可以记录此详细级别,而无需对代码库进行大量更改?我看过Ruby探查器,看它是否有帮助,而且可能有帮助;我很好奇是否有更好的方法(特别是记录包含调用方法的文件名).

Is there a way of logging this level of detail without making wholesale changes to the code base? I've had a look at the Ruby profiler to see if it could help, and it probably could; I'm curious if there's a better way (particularly logging the filename containing the invoked method).

预先感谢

推荐答案

这绝对是可能的-实际上,甚至还有一种方法!只需在要开始记录的点之前将其添加到代码中的某个位置即可:

This is definitely possible -- in fact, there's even a method for it! Just add this somewhere in your code before the point that you want to start logging things:

set_trace_func proc { |event, file, line, id, binding, classname|
  printf "%8s %s:%-2d %10s %8s\n", event, file, line, id, classname
}

您想要的秘密调味料来自 Kernel#set_trace_func ,如上所述:

The secret sauce you want comes from Kernel#set_trace_func, as noted above:

  • set_trace_func(proc)=> proc
  • set_trace_func(nil)=>无
  • set_trace_func(proc) => proc
  • set_trace_func(nil) => nil

proc建立为跟踪处理程序,如果参数为nil,则禁用跟踪. proc最多包含六个参数:事件名称,文件名,行号,对象ID,绑定和类名.每当事件发生时,都会调用proc.事件包括:c-call(调用C语言例程),c-return(从C语言例程返回),call(调用Ruby方法),class(启动类或模块定义), end(完成类或模块的定义),line(在新行上执行代码),raise(引发异常)和return(从Ruby方法返回).在proc的上下文中禁用了跟踪.

Establishes proc as the handler for tracing, or disables tracing if the parameter is nil. proc takes up to six parameters: an event name, a filename, a line number, an object id, a binding, and the name of a class. proc is invoked whenever an event occurs. Events are: c-call (call a C-language routine), c-return (return from a C-language routine), call (call a Ruby method), class (start a class or module definition), end (finish a class or module definition), line (execute code on a new line), raise (raise an exception), and return (return from a Ruby method). Tracing is disabled within the context of proc.

这是一个方便的示例:

class Test
  def test
    a = 1
    b = 2
  end
end

set_trace_func proc { |event, file, line, id, binding, classname|
  printf "%8s %s:%-2d %10s %8s\n", event, file, line, id, classname
}

t = Test.new
t.test

(注意:除非想要巨大的文本滚动屏幕,否则请不要在irb中尝试此操作.)结果输出为:

(Note: don't try this in irb unless you want a huge scrolling screen of text.) The resulting output is:

    line test.rb:11               false
  c-call test.rb:11        new    Class
  c-call test.rb:11 initialize   Object
c-return test.rb:11 initialize   Object
c-return test.rb:11        new    Class
    line test.rb:12               false
    call test.rb:2        test     Test
    line test.rb:3        test     Test
    line test.rb:4        test     Test
  return test.rb:4        test     Test

您可以使用上面的格式字符串来获取您想要记录的结果(例如,听起来您只对call事件感兴趣).希望能对所有这些单元测试进行分类,并祝您好运!

You can play around with the formatting string above to get just the results you want to log (for example, it sounds like you're only interested in call events). Hope that helps, and good luck with sorting through all those unit tests!

这篇关于如何记录在Ruby程序中调用的每个方法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆