#!/usr/bin/env python3 """Owner-aware diff of two `javap -public` dumps (one per JDK). Usage: api_diff.py OLD.txt NEW.txt""" import sys def load(p): cur, d = None, {} for line in open(p): line = line.rstrip("\n") if not line.strip(): continue if not line.startswith(" "): cur = line.rstrip(" {").split(" extends ")[0].split(" implements ")[0].rsplit(" ", 1)[-1] d[cur] = {"__header__": line} elif line.strip() != "}": d[cur][line.strip()] = True return d a, b = load(sys.argv[1]), load(sys.argv[2]) changes = 0 for c in sorted(set(a) | set(b)): if c not in a: print(f"+ class {c}"); changes += 1; continue if c not in b: print(f"- class {c}"); changes += 1; continue if a[c]["__header__"] != b[c]["__header__"]: print(f"~ {c}\n was: {a[c]['__header__']}\n now: {b[c]['__header__']}"); changes += 1 for m in sorted(set(a[c]) - set(b[c]) - {"__header__"}): print(f"- {c}: {m}"); changes += 1 for m in sorted(set(b[c]) - set(a[c]) - {"__header__"}): print(f"+ {c}: {m}"); changes += 1 print(f"{len(a)} classes in old, {len(b)} in new, {changes} difference(s)")