forked from pyutils/line_profiler
-
Notifications
You must be signed in to change notification settings - Fork 0
/
autoprofile-poc.py
134 lines (117 loc) · 3.99 KB
/
autoprofile-poc.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
import ubelt as ub
# try:
# import ast
# unparse = ast.unparse
# except AttributeError:
# try:
# import astunparse
# unparse = astunparse.unparse
# except ModuleNotFoundError:
# unparse = None
# import sys
# sys.path.append('../')
from line_profiler.autoprofile import autoprofile
def create_poc(dry_run=False):
root = ub.Path.appdir('line_profiler/test/poc/')
repo = (root / 'repo')
modpaths = {}
modpaths['script'] = (root / 'repo/script.py')
modpaths['foo'] = (root / 'repo/foo')
modpaths['foo.__init__'] = (root / 'repo/foo/__init__.py')
modpaths['foo.bar'] = (root / 'repo/foo/bar.py')
modpaths['foo.baz'] = (root / 'repo/foo/baz')
modpaths['foo.baz.__init__'] = (root / 'repo/foo/baz/__init__.py')
modpaths['foo.baz.spam'] = (root / 'repo/foo/baz/spam.py')
modpaths['foo.baz.eggs'] = (root / 'repo/foo/baz/eggs.py')
if not dry_run:
root.delete().ensuredir()
repo.ensuredir()
modpaths['script'].touch()
modpaths['foo'].ensuredir()
modpaths['foo.__init__'].touch()
modpaths['foo.bar'].touch()
modpaths['foo.bar'].write_text('def asdf():\n 2**(1/65536)')
modpaths['foo.baz'].ensuredir()
modpaths['foo.baz.__init__'].touch()
modpaths['foo.baz.spam'].touch()
modpaths['foo.baz.spam'].write_text('def spamfunc():\n ...')
modpaths['foo.baz.eggs'].touch()
modpaths['foo.baz.eggs'].write_text('def eggfunc():\n ...')
"""different import variations to handle"""
script_text = ub.codeblock(
'''
import foo # mod
import foo.bar # py
from foo import bar # py
from foo.bar import asdf # fn
import foo.baz as foodotbaz # mod
from foo import baz as foobaz # mod
from foo import bar, baz as baz2 # py,mod
import foo.baz.eggs # py
from foo.baz import eggs # py
from foo.baz.eggs import eggfunc # fn
from foo.baz.spam import spamfunc as yum # fn
from numpy import round # fn
# @profile
def test():
2**65536
foo.bar.asdf()
def main():
2**65536
test()
# foo.bar.asdf()
main()
test()
# asdf()
''')
ub.writeto(modpaths['script'], script_text)
return root, repo, modpaths
def main():
root, repo, modpaths = create_poc(dry_run=False)
script_file = str(modpaths['script'])
"""separate from prof_mod, profile all imports in script"""
profile_script_imports = False
"""modnames to profile"""
modnames = [
# 'fool', # doesn't exist
# 'foo',
'foo.bar',
# 'foo.baz',
# 'foo.baz.eggs',
# 'foo.baz.spam',
# 'numpy.round',
]
"""modpaths to profile"""
modpaths = [
# str(root),
# str((repo / 'fool')), # doesn't exist
# str(modpaths['foo']),
# str(modpaths['foo.__init__']),
# str(modpaths['foo.bar']),
# str(modpaths['foo.baz']),
# str(modpaths['foo.baz.__init__']),
# str(modpaths['foo.baz.spam']),
# str(modpaths['foo.baz.eggs']),
# str(modpaths['script']), # special case to profile all items
]
prof_mod = modnames + modpaths
# prof_mod = modpaths
# prof_mod = modnames
"""mimick running using kernprof"""
import sys
import os
import builtins
__file__ = script_file
__name__ = '__main__'
script_directory = os.path.realpath(os.path.dirname(script_file))
sys.path.insert(0, script_directory)
import line_profiler
prof = line_profiler.LineProfiler()
builtins.__dict__['profile'] = prof
ns = locals()
autoprofile.run(script_file, ns, prof_mod=prof_mod)
print('\nprofiled')
print('=' * 10)
prof.print_stats(output_unit=1e-6, stripzeros=True, stream=sys.stdout)
if __name__ == '__main__':
main()