in scripts/compare_pysa_models_to_json.py [0:0]
def main() -> None:
parser = argparse.ArgumentParser(
description="A script to compare models in a .pysa file "
"to the JSON model dump generated by Pysa."
)
parser.add_argument(
"-j",
"--json",
required=True,
type=str,
help="Path of the JSON file containing Pysa's taint output dump.",
)
parser.add_argument(
"-p",
"--pysa",
required=True,
type=str,
help=("Path of the .pysa model file."),
)
arguments = parser.parse_args()
logging.basicConfig(
format="[%(asctime)s][%(levelname)s]: %(message)s", level=logging.INFO
)
json_models: Dict[str, TargetModel] = get_models_from_json_file(arguments.json)
pysa_models: Dict[str, TargetModel] = get_models_from_pysa_file(arguments.pysa)
# Models in .json that differ from the .pysa
diff_json = {
k: v
for k, v in json_models.items()
if not (k in pysa_models and json_models[k] == pysa_models[k])
}
# Models in the .pysa that differ from the .json
diff_pysa = {
k: v
for k, v in pysa_models.items()
if not (k in json_models and pysa_models[k] == json_models[k])
}
# Pysa skips analyzing things that inherit from e.g. testing.unittest.UnitTest by
# default, which is why the model query results are missing a few models compared to
# the Python model generator. Here we move assume all callables with 'test' in their
# name are tests and move them to a separate section to not clutter the diff
# results.
diff_pysa_test = {k: v for k, v in diff_pysa.items() if "test" in k}
diff_pysa_non_test = {k: v for k, v in diff_pysa.items() if "test" not in k}
# Print the results.
diff_json_message = "\n".join(
[
"{}\nIn JSON: {}\nIn .pysa: {}\n".format(
callable_name,
json_models[callable_name],
pysa_models[callable_name] if callable_name in pysa_models else {},
)
for callable_name in sorted(diff_json.keys())
]
)
diff_pysa_test_message = "\n".join(
[
"{}\nIn .pysa: {}\nIn JSON: {}\n".format(
callable_name,
pysa_models[callable_name],
json_models[callable_name] if callable_name in json_models else {},
)
for callable_name in sorted(diff_pysa_test.keys())
]
)
diff_pysa_non_test_message = "\n".join(
[
"{}\nIn .pysa: {}\nIn JSON: {}\n".format(
callable_name,
pysa_models[callable_name],
json_models[callable_name] if callable_name in json_models else {},
)
for callable_name in sorted(diff_pysa_non_test.keys())
]
)
LOG.info(
f""""