-
Notifications
You must be signed in to change notification settings - Fork 45
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
If create or replace fails for a view, drop and recreate? #5
Comments
I think what you're asking for is
That may still fail if the view has dependencies, but it will increase the chances of the migration succeeding. That strategy could work for both upgrades and downgrades. |
Example of what would need to be emitted to have that effect -- Starting with a 2 column view
create or replace view myview as
select 1 val1, 2 val2;
-- Begin migration to remove "val2" column
do $$
begin
/* First try to replace the view,
which may succeed, even if there
are dependent views */
create or replace view myview as
select 1 val1;
-- If replacing the view raises an exception
exception when others then
/* Drop the existing view
which will raise another exception
and fail if there is a dependent view */
drop view myview;
-- Recreate the view however you want
create view myview as
select 1 val1;
end;
$$ language 'plpgsql' |
My concern is that people may rely migrations to protect them from deleting columns in a view. If you want that behavior now, you can get it by tweaking the autogenerated migration like this From this def downgrade():
myview = PGView(
schema='public',
signature='myview',
definition='select 1 as val1'
)
op.replace_entity(myview) To this def downgrade():
myview = PGView(
schema='public',
signature='myview',
definition='select 1 as val1'
)
op.drop_entity(myview)
op.create_entity(myview) I'd like to think more about if this is a problem that should be solved at the framework level before committing to anything. hope that workaround helps in the meantime |
It always make sense to think about what will have to be lived with. Trying create or replace before dropping makes sense. A configuration switch might be helpful. Putting this situation in the documentation might also be helpful. I'm ok regardless, thanks again. |
Retested with 0.2.6 and it worked. |
Any further thoughts on this? If the default behavior is to drop the view and give a readable error when the view has dependents, that seems hard to beat. A configuration option that can modulate that behavior also seems like a maintainable solution. |
While I agree that the change would make a migration work by default more frequently, I’m not comfortable with that change b/c a new user would be surprised by it. They also may rely on certain failure conditions. To this point I haven't introduced and configuration options & and I'd like to avoid that for as long as possible. But, here's what you can do: from alembic_utils.pg_view import PGView
class SuperPGView(PGView):
def to_sql_statement_create_or_replace(self) -> str:
"""Generates a SQL "create or replace view" statement"""
return sql_text(f"""
do $$
begin
CREATE OR REPLACE VIEW {self.literal_schema}."{self.signature}" AS {self.definition};
exception when others then
DROP VIEW {self.literal_schema}."{self.signature}";
CREATE VIEW {self.literal_schema}."{self.signature}" AS {self.definition}
end;
$$ language 'plpgsql'
"""
) I haven't tested that snippet. If you do go that route please post and changes you have to make for others who might end up here. Here's a link to that method's current implementation
|
Were you able to get that working? |
I'm very sorry for the delay in getting back to you, thanks very much for the suggestion. Yes, that worked on the first try! |
Great! closing |
It looks like the two approaches both have pros and cons:
The proposal is to create a 3rd approach that combines them: The other approach I could suggest is to pass a flag (e.g. |
release 0.2.12 is now live on pypi and fails over from |
Great! Thank you:-) |
quoted from @mfsjr in #4
The text was updated successfully, but these errors were encountered: