首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何在python中获得测试方法的起始行号和尾行号?

如何在python中获得测试方法的起始行号和尾行号?
EN

Stack Overflow用户
提问于 2019-12-14 20:06:17
回答 3查看 568关注 0票数 1

我目前正在尝试获取python文件中所有测试方法的第一行和最后一行号。

例如:

文件test_lift.py测试文件lift.py。

test_lift.py

代码语言:javascript
复制
1 import random
2
3 from src.lift import Lift
4 from flaky import flaky
5
6
7 def test_upwards():
8         tester = Lift()
9         tester.upwards()
10        assert 1 == tester.curr_floor
11
12 def test_downwards():
13        tester = Lift()
14        tester.curr_floor = 1
15        tester.downwards()
16        assert 0 == tester.curr_floor
17        tester.downwards()
18        assert 0 == tester.curr_floor
19
...

现在,我希望获得test_lift.py中每个测试方法的第一个和最后一个行号,例如:

test_upwards,7,10

test_downwards,12岁,18岁

我已经尝试过使用conftest.py,但没有成功。也许我忽略了什么?解决方案不一定必须在python中。如果有人知道如何通过解析文件来解决这个问题,我对此没有意见。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2019-12-14 20:26:47

或者,没有任何其他模块(只是一些Python内部组件):

代码语言:javascript
复制
>>> def thing():
...  a = 5
...  b = a + 4
...  return a + b * 2
... 
>>> thing.__code__.co_firstlineno  # self-explanatory
1
>>> list(thing.__code__.co_lnotab)
[0, 1, 4, 1, 8, 1]
>>> thing.__code__.co_firstlineno + sum(line_increment for i, line_increment in enumerate(thing.__code__.co_lnotab) if i % 2)
4

这样就有了它:函数从第1行(thing.__code__.co_firstlineno)到第4行。

dis模块证明了这一点(第一列中的数字是行号):

代码语言:javascript
复制
>>> import dis
>>> dis.dis(thing)
  2           0 LOAD_CONST               1 (5)
              2 STORE_FAST               0 (a)

  3           4 LOAD_FAST                0 (a)
              6 LOAD_CONST               2 (4)
              8 BINARY_ADD
             10 STORE_FAST               1 (b)

  4          12 LOAD_FAST                0 (a)
             14 LOAD_FAST                1 (b)
             16 LOAD_CONST               3 (2)
             18 BINARY_MULTIPLY
             20 BINARY_ADD
             22 RETURN_VALUE

注意最后一个数字是4--这是函数的最后一行。

有关co_lnotab结构的更多信息可以找到这里这里

测试程序

代码语言:javascript
复制
def span_of_function(func):
  start = func.__code__.co_firstlineno
  end = start + sum(line_increment for i, line_increment in enumerate(func.__code__.co_lnotab) if i % 2)
  
  return start, end

def hello(name):
  print(f'Hello, {name}!')
  return 5

print(span_of_function(span_of_function))
print(span_of_function(hello))

输出:

代码语言:javascript
复制
$ python3 test.py
(1, 5)
(7, 9)
票数 2
EN

Stack Overflow用户

发布于 2019-12-14 20:20:26

您可以为此使用inspect模块。

代码语言:javascript
复制
import inspect
lines,line_start = inspect.getsourcelines(test_downwards)

print("Lines:",line_start,line_start+len(lines) - 1 )
票数 0
EN

Stack Overflow用户

发布于 2019-12-14 20:27:28

检查工作做得很好:

代码语言:javascript
复制
import inspect


def line_number():
    return inspect.currentframe().f_back.f_lineno


print "This is line number:", line_number()
this = line_number()
print "This is line number:", line_number()
print "Variable 'this' at line: ", this
line_number()

输出:

代码语言:javascript
复制
This is line number: 8
This is line number: 10
Variable 'this' at line: 9
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/59338717

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档