graph-tool 2.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475
  1. #!/usr/bin/env python3
  2. # Simple graph query utility
  3. # useful for getting answers from .dot files produced by bitbake -g
  4. #
  5. # Written by: Paul Eggleton <paul.eggleton@linux.intel.com>
  6. #
  7. # Copyright 2013 Intel Corporation
  8. #
  9. # SPDX-License-Identifier: GPL-2.0-only
  10. #
  11. import sys
  12. import os
  13. import argparse
  14. scripts_lib_path = os.path.abspath(os.path.join(os.path.dirname(os.path.realpath(__file__)), '..', 'lib'))
  15. sys.path.insert(0, scripts_lib_path)
  16. import argparse_oe
  17. def get_path_networkx(dotfile, fromnode, tonode):
  18. try:
  19. import networkx
  20. except ImportError:
  21. print('ERROR: Please install the networkx python module')
  22. sys.exit(1)
  23. graph = networkx.DiGraph(networkx.nx_pydot.read_dot(dotfile))
  24. def node_missing(node):
  25. import difflib
  26. close_matches = difflib.get_close_matches(node, graph.nodes(), cutoff=0.7)
  27. if close_matches:
  28. print('ERROR: no node "%s" in graph. Close matches:\n %s' % (node, '\n '.join(close_matches)))
  29. sys.exit(1)
  30. if not fromnode in graph:
  31. node_missing(fromnode)
  32. if not tonode in graph:
  33. node_missing(tonode)
  34. return networkx.all_simple_paths(graph, source=fromnode, target=tonode)
  35. def find_paths(args):
  36. path = None
  37. for path in get_path_networkx(args.dotfile, args.fromnode, args.tonode):
  38. print(" -> ".join(map(str, path)))
  39. if not path:
  40. print("ERROR: no path from %s to %s in graph" % (args.fromnode, args.tonode))
  41. return 1
  42. def main():
  43. parser = argparse_oe.ArgumentParser(description='Small utility for working with .dot graph files')
  44. subparsers = parser.add_subparsers(title='subcommands', metavar='<subcommand>')
  45. subparsers.required = True
  46. parser_find_paths = subparsers.add_parser('find-paths',
  47. help='Find all of the paths between two nodes in a dot graph',
  48. description='Finds all of the paths between two nodes in a dot graph')
  49. parser_find_paths.add_argument('dotfile', help='.dot graph to search in')
  50. parser_find_paths.add_argument('fromnode', help='starting node name')
  51. parser_find_paths.add_argument('tonode', help='ending node name')
  52. parser_find_paths.set_defaults(func=find_paths)
  53. args = parser.parse_args()
  54. ret = args.func(args)
  55. return ret
  56. if __name__ == "__main__":
  57. ret = main()
  58. sys.exit(ret)