Last active
January 14, 2022 15:55
-
-
Save district10/ec85779895f3d838d57ee3a8275b65b1 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from typing import Union, Set, Dict, List, Any, Tuple, Optional | |
from collections import defaultdict | |
from pprint import pprint | |
import glob | |
from functools import lru_cache | |
def update_deps_info(*, deps_info: Dict[str, Set[str]], lines: List[str]): | |
''' | |
deps_info { | |
module -> [deps] | |
} | |
lines := | |
absl_cc_library( | |
NAME | |
bad_any_cast_impl | |
SRCS | |
"bad_any_cast.h" | |
"bad_any_cast.cc" | |
COPTS | |
${ABSL_DEFAULT_COPTS} | |
DEPS | |
absl::config | |
absl::raw_logging_internal | |
) | |
''' | |
lines = [l.strip() for l in lines] | |
idx, N = 0, len(lines) | |
while idx < N: | |
line = lines[idx] | |
if not line.startswith('absl_cc_library('): | |
idx += 1 | |
continue | |
assert lines[idx + 1] == 'NAME' | |
curr = lines[idx + 2] | |
deps = deps_info[f'absl::{curr}'] | |
idx += 3 | |
collecting_dep = False | |
while idx < N and lines[idx] != ')': | |
line = lines[idx] | |
if not collecting_dep and line == 'DEPS': | |
collecting_dep = True | |
elif collecting_dep: | |
if line.isupper(): | |
collecting_dep = False | |
else: | |
deps.add(line) | |
idx += 1 | |
assert idx < N and lines[idx] == ')' | |
@lru_cache(maxsize=None) | |
def should_strip(module_name: str) -> bool: | |
# return False | |
return module_name.endswith('_test') or 'internal' in module_name or 'testing' in module_name | |
def strip(deps_info: Dict[str, Set[str]]): | |
for k in list(deps_info.keys()): | |
if should_strip(k): | |
deps_info.pop(k) | |
continue | |
for v in list(deps_info[k]): | |
if should_strip(v): | |
deps_info[k].remove(v) | |
paths = sorted(glob.glob('absl/**/CMakeLists.txt', recursive=True)) | |
# pprint(paths) | |
deps_info = defaultdict(set) | |
for path in paths: | |
with open(path) as f: | |
update_deps_info(deps_info=deps_info, lines=f.readlines()) | |
pprint(deps_info) | |
strip(deps_info) | |
import graphviz as gv | |
dot = gv.Digraph() | |
def ID(text): | |
return text.replace(':', '_') | |
nodes = set(deps_info.keys()) | |
for deps in deps_info.values(): | |
nodes |= deps | |
for n in nodes: | |
dot.node(ID(n), n) | |
for f, tos in deps_info.items(): | |
for t in tos: | |
dot.edge(ID(f), ID(t)) | |
output_path = 'absl_module_deps.svg' | |
filename, format = output_path.rsplit('.', 1) | |
dot.format = format | |
dot.render(filename) | |
print(f'wrote to {output_path}') |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment