You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python 3.8/3.10中inspect.getsource获取类源码差异及兼容方案咨询

Python 3.8与3.10中inspect.getsource获取类源码的差异及兼容方案

差异原因

  • Python 3.8及更早版本的inspect.getsource()在处理被装饰类时,只会提取类定义本身的源码,不会包含上方的装饰器。这是因为当时模块的实现逻辑是直接定位到类的定义节点,跳过了装饰器语法所在的代码段。
  • Python 3.10对inspect模块的源码定位逻辑做了优化,能够识别并包含类定义上方的装饰器代码,因此调用inspect.getsource(Test)会返回带@dec的完整源码。

兼容Python 3.8的解决方案

要在Python 3.8中获取包含装饰器的类源码,可以手动向上遍历源码文件,收集类定义上方的装饰器行,再和类源码拼接。具体实现如下:

import inspect

def dec(clz):
    return clz

@dec
class Test:
    pass

def get_source_with_decorators(obj):
    # 获取类的源码行和起始行号(行号从1开始计数)
    class_lines, start_line = inspect.getsourcelines(obj)
    source_file = inspect.getsourcefile(obj)
    
    # 读取整个源码文件的内容
    with open(source_file, 'r', encoding='utf-8') as f:
        all_lines = f.readlines()
    
    # 从类定义的上一行开始向上查找装饰器
    decorator_lines = []
    current_idx = start_line - 2  # 转换为0索引的行号,start_line是类定义行,减2得到上一行的索引
    while current_idx >= 0:
        line_content = all_lines[current_idx].strip()
        if line_content.startswith('@'):
            decorator_lines.insert(0, all_lines[current_idx])
            current_idx -= 1
        else:
            # 遇到非装饰器行,停止遍历
            break
    
    # 拼接装饰器和类的源码
    return ''.join(decorator_lines + class_lines)

# 测试调用
print(get_source_with_decorators(Test))

这个方法的核心是通过inspect.getsourcelines()拿到类的起始位置,再从该位置向上遍历源码文件,收集所有连续的装饰器行,最后和类本身的源码拼接,就能得到包含装饰器的完整代码。

内容的提问来源于stack exchange,提问作者cinqS

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.14 22:37:12