Make spack graph -i environment-aware (#25599)

This allows you to run `spack graph --installed` from within an environment and get a dot graph of
its concrete specs.

- [x] make `spack graph -i` environment-aware

- [x] add code to the generated dot graph to ensure roots have min rank (i.e., they're all at the
      top or left of the DAG)
This commit is contained in:
Todd Gamblin 2021-08-25 07:41:04 -07:00 committed by GitHub
parent 3e2f890467
commit fafe1cb7e8
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 18 additions and 2 deletions

View File

@ -10,6 +10,7 @@
import spack.cmd import spack.cmd
import spack.cmd.common.arguments as arguments import spack.cmd.common.arguments as arguments
import spack.config import spack.config
import spack.environment as ev
import spack.store import spack.store
from spack.graph import graph_ascii, graph_dot from spack.graph import graph_ascii, graph_dot
@ -35,7 +36,7 @@ def setup_parser(subparser):
subparser.add_argument( subparser.add_argument(
'-i', '--installed', action='store_true', '-i', '--installed', action='store_true',
help="graph all installed specs in dot format (implies --dot)") help="graph installed specs, or specs in the active env (implies --dot)")
arguments.add_common_arguments(subparser, ['deptype', 'specs']) arguments.add_common_arguments(subparser, ['deptype', 'specs'])
@ -45,6 +46,11 @@ def graph(parser, args):
if args.specs: if args.specs:
tty.die("Can't specify specs with --installed") tty.die("Can't specify specs with --installed")
args.dot = True args.dot = True
env = ev.active_environment()
if env:
specs = env.all_specs()
else:
specs = spack.store.db.query() specs = spack.store.db.query()
else: else:

View File

@ -550,11 +550,21 @@ def dynamic_graph(spec, deptypes):
out.write(' style="rounded,filled"') out.write(' style="rounded,filled"')
out.write(' ]\n') out.write(' ]\n')
# write nodes
out.write('\n') out.write('\n')
for key, label in nodes: for key, label in nodes:
out.write(' "%s" [label="%s"]\n' % (key, label)) out.write(' "%s" [label="%s"]\n' % (key, label))
# write edges
out.write('\n') out.write('\n')
for src, dest in edges: for src, dest in edges:
out.write(' "%s" -> "%s"\n' % (src, dest)) out.write(' "%s" -> "%s"\n' % (src, dest))
# ensure that roots are all at the top of the plot
dests = set([d for _, d in edges])
roots = ['"%s"' % k for k, _ in nodes if k not in dests]
out.write('\n')
out.write(' { rank=min; %s; }' % "; ".join(roots))
out.write('\n')
out.write('}\n') out.write('}\n')