Problem
better_structure_sql sorts materialized views (and regular views) alphabetically when dumping db/schema/. This breaks when one view depends on another that sorts later alphabetically — loading the schema fails:
ERROR: relation "reconciliation_daily_summaries" does not exist
Real-world example: reconciliation_account_summaries depends on reconciliation_daily_summaries, but sorts first alphabetically, so the CREATE statement comes before its dependency exists.
Even when IF NOT EXISTS prevents hard failures, every db:migrate can flip the order, creating noisy diffs in PRs.
Root Cause
File: lib/better_structure_sql/adapters/postgresql_adapter.rb
- Line ~190:
ORDER BY matviewname — alphabetical, ignores dependencies
- Line ~165:
ORDER BY viewname — same issue for regular views
The gem already has a DependencyResolver class (lib/better_structure_sql/dependency_resolver.rb) with topological sorting. It just isn't wired into the view/materialized view fetching pipeline.
Reproduction Steps
- Create a PostgreSQL database with two materialized views where one depends on the other
- Name them such that the dependent view sorts alphabetically before its dependency
- Example:
reconciliation_account_summaries depends on reconciliation_daily_summaries
- Run
better_structure_sql to dump the schema
- Try to reload the schema:
- Result:
ERROR: relation "reconciliation_daily_summaries" does not exist
Proposed Solution
Query PostgreSQL's pg_depend + pg_rewrite catalogs to discover inter-view dependencies, then feed results into the existing DependencyResolver for topological sorting.
Steps:
- Add
sort_by_dependencies(connection, objects, relkind) helper method that queries dependencies
- Update
fetch_materialized_views to remove ORDER BY matviewname and apply sort_by_dependencies instead
- Update
fetch_views to remove ORDER BY viewname and apply sort_by_dependencies instead
- Add RSpec tests for dependency ordering scenarios (matview→matview, view→view, circular dependencies, no dependencies)
Related Files
lib/better_structure_sql/adapters/postgresql_adapter.rb - where changes are needed
lib/better_structure_sql/dependency_resolver.rb - existing class with topological sorting
Problem
better_structure_sqlsorts materialized views (and regular views) alphabetically when dumpingdb/schema/. This breaks when one view depends on another that sorts later alphabetically — loading the schema fails:Real-world example:
reconciliation_account_summariesdepends onreconciliation_daily_summaries, but sorts first alphabetically, so the CREATE statement comes before its dependency exists.Even when
IF NOT EXISTSprevents hard failures, everydb:migratecan flip the order, creating noisy diffs in PRs.Root Cause
File:
lib/better_structure_sql/adapters/postgresql_adapter.rbORDER BY matviewname— alphabetical, ignores dependenciesORDER BY viewname— same issue for regular viewsThe gem already has a
DependencyResolverclass (lib/better_structure_sql/dependency_resolver.rb) with topological sorting. It just isn't wired into the view/materialized view fetching pipeline.Reproduction Steps
reconciliation_account_summariesdepends onreconciliation_daily_summariesbetter_structure_sqlto dump the schemaERROR: relation "reconciliation_daily_summaries" does not existProposed Solution
Query PostgreSQL's
pg_depend+pg_rewritecatalogs to discover inter-view dependencies, then feed results into the existingDependencyResolverfor topological sorting.Steps:
sort_by_dependencies(connection, objects, relkind)helper method that queries dependenciesfetch_materialized_viewsto removeORDER BY matviewnameand applysort_by_dependenciesinsteadfetch_viewsto removeORDER BY viewnameand applysort_by_dependenciesinsteadRelated Files
lib/better_structure_sql/adapters/postgresql_adapter.rb- where changes are neededlib/better_structure_sql/dependency_resolver.rb- existing class with topological sorting