mirror of
https://gitee.com/fastnlp/fastNLP.git
synced 2024-12-05 05:38:31 +08:00
192 lines
6.6 KiB
Python
192 lines
6.6 KiB
Python
import inspect
|
|
import os
|
|
import sys
|
|
|
|
|
|
def _colored_string(string: str, color: str or int) -> str:
|
|
"""在终端中显示一串有颜色的文字
|
|
:param string: 在终端中显示的文字
|
|
:param color: 文字的颜色
|
|
:return:
|
|
"""
|
|
if isinstance(color, str):
|
|
color = {
|
|
"black": 30, "Black": 30, "BLACK": 30,
|
|
"red": 31, "Red": 31, "RED": 31,
|
|
"green": 32, "Green": 32, "GREEN": 32,
|
|
"yellow": 33, "Yellow": 33, "YELLOW": 33,
|
|
"blue": 34, "Blue": 34, "BLUE": 34,
|
|
"purple": 35, "Purple": 35, "PURPLE": 35,
|
|
"cyan": 36, "Cyan": 36, "CYAN": 36,
|
|
"white": 37, "White": 37, "WHITE": 37
|
|
}[color]
|
|
return "\033[%dm%s\033[0m" % (color, string)
|
|
|
|
|
|
def gr(string, flag):
|
|
if flag:
|
|
return _colored_string(string, "green")
|
|
else:
|
|
return _colored_string(string, "red")
|
|
|
|
|
|
def find_all_modules():
|
|
modules = {}
|
|
children = {}
|
|
to_doc = set()
|
|
root = '../fastNLP'
|
|
for path, dirs, files in os.walk(root):
|
|
for file in files:
|
|
if file.endswith('.py'):
|
|
name = ".".join(path.split('/')[1:])
|
|
if file.split('.')[0] != "__init__":
|
|
name = name + '.' + file.split('.')[0]
|
|
__import__(name)
|
|
m = sys.modules[name]
|
|
modules[name] = m
|
|
try:
|
|
m.__all__
|
|
except:
|
|
print(name, "__all__ missing")
|
|
continue
|
|
if m.__doc__ is None:
|
|
print(name, "__doc__ missing")
|
|
continue
|
|
if "undocumented" not in m.__doc__:
|
|
to_doc.add(name)
|
|
for module in to_doc:
|
|
t = ".".join(module.split('.')[:-1])
|
|
if t in to_doc:
|
|
if t not in children:
|
|
children[t] = set()
|
|
children[t].add(module)
|
|
for m in children:
|
|
children[m] = sorted(children[m])
|
|
return modules, to_doc, children
|
|
|
|
|
|
def create_rst_file(modules, name, children):
|
|
m = modules[name]
|
|
with open("./source/" + name + ".rst", "w") as fout:
|
|
t = "=" * len(name)
|
|
fout.write(name + "\n")
|
|
fout.write(t + "\n")
|
|
fout.write("\n")
|
|
fout.write(".. automodule:: " + name + "\n")
|
|
if name != "fastNLP.core" and len(m.__all__) > 0:
|
|
fout.write(" :members: " + ", ".join(m.__all__) + "\n")
|
|
short = name[len("fastNLP."):]
|
|
if not (short.startswith('models') or short.startswith('modules') or short.startswith('embeddings')):
|
|
fout.write(" :inherited-members:\n")
|
|
fout.write("\n")
|
|
if name in children:
|
|
fout.write("子模块\n------\n\n.. toctree::\n :maxdepth: 1\n\n")
|
|
for module in children[name]:
|
|
fout.write(" " + module + "\n")
|
|
|
|
|
|
def check_file(m, name):
|
|
names = name.split('.')
|
|
test_name = "test." + ".".join(names[1:-1]) + ".test_" + names[-1]
|
|
try:
|
|
__import__(test_name)
|
|
tm = sys.modules[test_name]
|
|
except ModuleNotFoundError:
|
|
tm = None
|
|
tested = tm is not None
|
|
funcs = {}
|
|
classes = {}
|
|
for item, obj in inspect.getmembers(m):
|
|
if inspect.isclass(obj) and obj.__module__ == name and not obj.__name__.startswith('_'):
|
|
this = (obj.__doc__ is not None, tested and obj.__name__ in dir(tm), {})
|
|
for i in dir(obj):
|
|
func = getattr(obj, i)
|
|
if inspect.isfunction(func) and not i.startswith('_'):
|
|
this[2][i] = (func.__doc__ is not None, False)
|
|
classes[obj.__name__] = this
|
|
if inspect.isfunction(obj) and obj.__module__ == name and not obj.__name__.startswith('_'):
|
|
this = (obj.__doc__ is not None, tested and obj.__name__ in dir(tm)) # docs
|
|
funcs[obj.__name__] = this
|
|
return funcs, classes
|
|
|
|
|
|
def check_files(modules, out=None):
|
|
for name in sorted(modules.keys()):
|
|
print(name, file=out)
|
|
funcs, classes = check_file(modules[name], name)
|
|
if out is None:
|
|
for f in funcs:
|
|
print("%-30s \t %s \t %s" % (f, gr("文档", funcs[f][0]), gr("测试", funcs[f][1])))
|
|
for c in classes:
|
|
print("%-30s \t %s \t %s" % (c, gr("文档", classes[c][0]), gr("测试", classes[c][1])))
|
|
methods = classes[c][2]
|
|
for f in methods:
|
|
print(" %-28s \t %s" % (f, gr("文档", methods[f][0])))
|
|
else:
|
|
for f in funcs:
|
|
if not funcs[f][0]:
|
|
print("缺少文档 %s" % (f), file=out)
|
|
if not funcs[f][1]:
|
|
print("缺少测试 %s" % (f), file=out)
|
|
for c in classes:
|
|
if not classes[c][0]:
|
|
print("缺少文档 %s" % (c), file=out)
|
|
if not classes[c][1]:
|
|
print("缺少测试 %s" % (c), file=out)
|
|
methods = classes[c][2]
|
|
for f in methods:
|
|
if not methods[f][0]:
|
|
print("缺少文档 %s" % (c + "." + f), file=out)
|
|
print(file=out)
|
|
|
|
|
|
def main_check():
|
|
sys.path.append("..")
|
|
print(_colored_string('Getting modules...', "Blue"))
|
|
modules, to_doc, children = find_all_modules()
|
|
print(_colored_string('Done!', "Green"))
|
|
print(_colored_string('Creating rst files...', "Blue"))
|
|
for name in to_doc:
|
|
create_rst_file(modules, name, children)
|
|
print(_colored_string('Done!', "Green"))
|
|
print(_colored_string('Checking all files...', "Blue"))
|
|
check_files(modules, out=open("results.txt", "w"))
|
|
print(_colored_string('Done!', "Green"))
|
|
|
|
|
|
def check_file_r(file_path):
|
|
with open(file_path) as fin:
|
|
content = fin.read()
|
|
index = -3
|
|
cuts = []
|
|
while index != -1:
|
|
index = content.find('"""',index+3)
|
|
cuts.append(index)
|
|
cuts = cuts[:-1]
|
|
assert len(cuts)%2 == 0
|
|
write_content = ""
|
|
last = 0
|
|
for i in range(len(cuts)//2):
|
|
start, end = cuts[i+i], cuts[i+i+1]
|
|
if content[start-1] == "r":
|
|
write_content += content[last:end+3]
|
|
else:
|
|
write_content += content[last:start] + "r"
|
|
write_content += content[start:end+3]
|
|
last = end + 3
|
|
write_content += content[last:]
|
|
with open(file_path, "w") as fout:
|
|
fout.write(write_content)
|
|
|
|
|
|
def add_r(base_path='../fastNLP'):
|
|
for path, _, files in os.walk(base_path):
|
|
for f in files:
|
|
if f.endswith(".py"):
|
|
check_file_r(os.path.abspath(os.path.join(path,f)))
|
|
# sys.exit(0)
|
|
|
|
|
|
if __name__ == "__main__":
|
|
add_r()
|