1 import sqlalchemy
.sql
.visitors
as visitors
3 from pokedex
.db
.tables
import metadata
5 # stolen from sqlalchemy.sql.util.sort_tables
6 def compute_dependencies(tables
):
7 """Construct a reverse dependency graph for the given tables.
9 Returns a dict which maps a table to the list of tables which depend on it.
13 def visit_foreign_key(fkey
):
16 parent_table
= fkey
.column
.table
17 if parent_table
in tables
:
18 child_table
= fkey
.parent
.table
19 if parent_table
is not child_table
:
20 graph
.setdefault(parent_table
, []).append(child_table
)
23 visitors
.traverse(table
,
24 {'schema_visitor': True},
25 {'foreign_key': visit_foreign_key
})
27 graph
.setdefault(table
, []).extend(table
._extra_dependencies
)
31 #: The dependency graph for pokedex.db.tables
32 _pokedex_graph
= compute_dependencies(metadata
.tables
.values())
34 def find_dependent_tables(tables
, graph
=None):
35 """Recursively find all tables which depend on the given tables.
37 The returned set does not include the original tables.
40 graph
= _pokedex_graph
43 def add_dependents_of(table
):
44 for dependent_table
in graph
.get(table
, []):
45 if dependent_table
not in dependents
:
46 dependents
.add(dependent_table
)
47 add_dependents_of(dependent_table
)
50 add_dependents_of(table
)
52 dependents
-= set(tables
)