Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix column renames for indexes #147

Merged
merged 1 commit into from
Jul 19, 2024

Conversation

bplunkett-stripe
Copy link
Collaborator

Description

Index columns effectively have two occurrences in pg_attribute, one is a "virtual column" created for the index and the other is the actual referenced column. For our purposes, we care about the latter, i.e., ensuring an index is deleted before its owning column is dropped, otherwise the index will be implicitly deleted (and not concurrently).

When a column is renamed, the virtual column name stays the same, but the underlying column name obviously changes. pg-schema-diff contained a bug where it referenced the virtual column name. Effectively, a column would be renamed but the column names in the fetched index would not change, leading to incorrectly generated dependencies.

I found this thread in the Postgres maling list to be very useful.

What I did:

  • Updated pg-schema-diff to reference the actual column name
  • (added benefit) Index columns are now fetched in the same query as the indexes, reducing round trips to the database

Motivation

Bug fix

Testing

See added test case

@bplunkett-stripe bplunkett-stripe added the bug Something isn't working label Jul 19, 2024
@@ -1718,6 +1718,7 @@ func (isg *indexSQLVertexGenerator) addDepsOnTableAddAlterIfNecessary(index sche
}
}

// Otherwise, we can drop the index whenever we want.
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Initially was debugging this problem and thought adding a comment helped document it a little better

Indexes: []Index{
{
OwningTable: SchemaQualifiedName{SchemaName: "public", EscapedName: "\"foo\""},
Name: "foo_value_idx", Columns: []string{"renamed_value"},
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Previously, it would have fetched the column as "value" instead of "renamed_value"

@bplunkett-stripe bplunkett-stripe force-pushed the bplunkett/fix-column-renames-for-indexes branch from fdaed98 to 8320e14 Compare July 19, 2024 07:43
Copy link
Collaborator

@alexaub-stripe alexaub-stripe left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Amazing catch

Comment on lines +99 to +100
SELECT ARRAY_AGG(att.attname ORDER BY indkey_ord.ord)
FROM UNNEST(i.indkey) WITH ORDINALITY AS indkey_ord (attnum, ord)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The ordinality here is just to make it explicit that the unnested array should be aggregated back in the same order after converting to column names right? And this isn't technically necessary since that should be the order anyways?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yep exactly. It's to enforce the order. I don't think it's technically necessary, but I definitely feel more comfortable with explicit ORDER BY

@@ -95,6 +95,13 @@ SELECT
i.indisunique AS index_is_unique,
COALESCE(parent_c.relname, '')::TEXT AS parent_index_name,
COALESCE(parent_namespace.nspname, '')::TEXT AS parent_index_schema_name,
(
SELECT ARRAY_AGG(att.attname ORDER BY indkey_ord.ord)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I almost wonder if it's worth a comment on this block here that this is just i.indkey.map(attnum -> column_name(attnum)) but in sql.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Might leave out the comment, since it's probably best to read from the docs on it. Pretty nifty SQL function!

@bplunkett-stripe bplunkett-stripe merged commit 4fc0bff into main Jul 19, 2024
9 checks passed
@bplunkett-stripe bplunkett-stripe deleted the bplunkett/fix-column-renames-for-indexes branch July 19, 2024 16:15
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants