drizzle-kit push inconsistent with database with migrations already applied
Hi team
Just wanting to sanity check something here to make sure that I am not barking up the wrong tree...From my understanding, the
drizzle-kit push
command should look at changes that I have made and push these up to the database before I make a migration
to commit that change for good? Anyway, here's my issue...
So, I've got a pg_enum
defined:
These were generated over time using migration
's and I've recently upgraded to the new Drizzle Kit version (v0.21.4
) (ORM: v0.30.10
)
If I run the drizzle-kit generate
command I get: No schema changes, nothing to migrate π΄
But then, when I run drizzle-kit push
:
I've also removed some logs from the above around dropping/adding FK's - but appears unrelated to this inconsistency40 Replies
Just re-tested this and it's still an issue on the latest version. Any advice folks?
facing same issue
kit is not updating an existing enum as well as not creating new enum
hey @Andrew Sherman (really sorry if I shouldn't ping!) just wondering if you could advise here?
π
so that's a bug and I think it's a regression
@alexblokh is working on fixing all such issues
he can take it, so we can release it tomorrow
we already have a few things fixed and ready to be released in 0.21.5
Hi Andrew, nice one, thanks! if you need me to file a proper GitHub issue or similar (or provide any help to test!) let me know π
we are fine with this thread for now
I guess a drizzle schema code would be helpful
it can be even a part of it
just so we can reproduce this issue and add a proper test cases for it
alright, let's give this a go...
to note here, this table did start off with a different name in the migrations, and the values in the enum have been added and removed over time (as you can see the original message)
let me know if there is anything more i can provide here - unsure if this in isolation will trigger/cause the same issues, so if you need my migration files and full schema, happy to send that over email/discord dm's if needed - just not wanting to expose my full db structure in public
https://github.com/drizzle-team/drizzle-orm/issues/2389 looks like this has been reported on the GitHub
GitHub
[BUG]: drizzle-kit push is not detecting Postgres enum label alread...
What version of drizzle-orm are you using? 0.30.9 What version of drizzle-kit are you using? 0.21.2 Describe the Bug This bug happens every so often. Is there a work around? pnpm drizzle-kit push d...
hey @Andrii Sherman, just to let you know the latest update unfortunately has not resolved this issue
I agree we have the same issue with push. It's making our transition from Prisma to Drizzle feel ill-advised.
Hi @Andrew Sherman! Hope youβre well, just wondering if we expect the latest updates to have resolved this regression?
Let me know if I can help push this forward
let me ping @alexblokh, he was working on fixing kit regressions
can you try with latest drizzle-kit?
give me 2 mins
we are trying to reproduce, but seeing no diffs in push
Same issue;
do you have the same enum values in database and ts schema?
Also note, I have stripped a bunch of other changes to do with constraints from the above log e.g
No, the values do not match - due to me evolving the
enum
over time
There are migrations where I have;
1. Renamed the table
where the enum
is attached
2. enum
values have been amended over timeyou did those changes manually in database?
or by generate+migrate from drizzle
nope, only ran in via migrations
i can try and spin up a new instance of db and run everything in again with a fresh
migrate
?it will work then, it should
I guess we can reproduce it
trying now
have an idea
yeah, reproduced it
working on improving this experience
Some context for everyone in this thread
There is no way to remove a value from an enum in PostgreSQL itself. Here is a great article about it: https://supabase.com/docs/guides/database/postgres/enums#removing-enum-values
Therefore, Drizzle Kit can't do this either. The behavior you experienced is a bug, and we will handle it such that if we detect any attempt to delete an enum value or change the order of values, you will see an error. You will then be asked to remove the enum and create a new one with the set of values you need. You can still add values to an enum and place them in a specific order within the array.
What you encountered was a combination of us not catching that you removed an enum value and the limitations of PostgreSQL enums.
If you remove the enum and create it again, there should be no issues.
cc @Cal
thanks @Andrew Sherman, just for clarification then, with the existing migrations, they are currently set up so that they will
add
values to an enum
and keep the existing ones in place - I did read that article in my attempt at debugging this before reaching out for the support π
So that means if I were to use migrate
on a new DB instance, then use push
to manage further testing/updates, this issue would pop up again surely?
just wondering what the DX would look like;
migrate
on a new db instance
drop
enum (and all columns
that depend on it)
then run push
to add the enum
values back in and then also re-create the columns that are missing?
i suppose, instead of throwing an error
, if we detect that an enum value is already in the pg_enum
, it is essentially a no-op and does not attempt to insert?i suppose, instead of throwing an error, if we detect that an enum value is already in the pg_enum, it is essentially a no-op and does not attempt to insert?We are doing exactly it, so push is reading pg_enum and other tables for all needed info and then read ts schema and search for a difference. As long as you have 3 values in ts schema and 5 enum values in database - it means you removed 2 of them
So that means if I were to use migrate on a new DB instance, then use push to manage further testing/updates, this issue would pop up again surely?push vs generate+migrate are 2 different concepts actually small explanation: https://orm.drizzle.team/kit-docs/faq#should-i-use-generate-or-push https://orm.drizzle.team/kit-docs/overview#prototyping-with-db-push I guess we need to have some big turorial and blog post explaining the difference
I suppose that's the scenario that I was referencing, was a quick-setup of the database with good known migrations, then
push
to test out local changes thereafter, but is that something that you'd not recommend and just push
straight from the schema?this flow is good actually
so you push as much as you need to test your schema and when you are ready with you schema -> generate the migration
and then push to stage/prod/etc.
We are doing exactly it, so push is reading pg_enum and other tables for all needed info and then read ts schema and search for a difference. As long as you have 3 values in ts schema and 5 enum values in database - it means you removed 2 of themSo in this case, correct that I removed the value from the
enum
on the drizzle-orm
side of things, generated migrations with generate
then migrate
'd them into the db at some point over the evolution of the application as my needs changed
I think the problem is that the push
is now trying to re-insert the enum value even though it's in the db? (and I agree, there are more values in db due to the limitations of pg_enum
etc)
good stuff, I am glad that the flow makes sense as it feels like a natural DX to do that πI guess I now understand what happened, and our update should make it straightforward for users to understand what happened. Let me explain
Push is trying to reinsert because there are more enum values in the database than in the code.
The reason why:
- You changed enums and generated a migration.
- Kit can't handle deletion or reordering of enums because PostgreSQL can't do it itself.
- You
migrate
'd, but your generated SQL statements didn't include statements to reorder or remove values from the enum.
- You tried to push, and as long as the new enum order was not updated in the database, we saw the error you encountered.
We will:
- Properly detect that some values were removed or reordered.
- On generate
, prompt you that we didn't generate some migration statements due to limitations and suggest ways to fix that yourself.
- On push
, fail with an error and explanation, asking you to push without the enum and then repush with the enum
btw, we are not using enums on all our projects, we instead are doing this:
column will be of type "active" | "non_active"
And then we can change the type as much as we need; it's just a TypeScript helper for usthank you @Andrew Sherman for the explanation here; the crux of this issue stems from the fact that
generate
/migrate
allowed the DB to get into this state in the first place (due to the out of sync enum values - of course you should error, because otherwise developers would be relying on the fact they could have value A
/B
but some one could insert value C
if they did it directly in the DB and cause all sorts of issues)
So in terms of rectifying already broken migration files, what do you think the best cause of action should be here? Given that a temp fix to manually sort it is fine, although if other developers are working on the platform, I'd hate to explain that after the migrate
they need to run a random script to fix the issue?and you can use $type with text, varchar or any other type
this looks very appealing indeed,
enum
's always seem to cause issues hey? πyes
outside of drizzle as well
oh 100%
you can use enum, if you are sure values won't change
So in terms of rectifying already broken migration files, what do you think the best cause of action should be here? Given that a temp fix to manually sort it is fine, although if other developers are working on the platform, I'd hate to explain that after the migrate they need to run a random script to fix the issue?Do you have such issues now? or you just asking?
Well I think I am in this scenario now, given that the
migrate
has brought me here and I'll have to write a script to correct the issue or am I missing something here?you would need to add values from database to a ts schema
so it will also have 5 enum values
and then handle it in a way we discussed
π thought so π
remove enum and then create needed one
We will provide errors with explanations, so that won't happen. We will release that tomorrow.
If you don't have such issues now, then the best answer would be: 'That won't happen again π
.'
and thanks a lot for his case
helped us to make an improvement
no worries at all, was fun to get more of an understanding, awesome stuff, thanks!
sorry to be back so soon π
I've re-added the enum values, and
push
still has the same error?ah, order is important as stated π
ignore me, order of enums fixed everything, thanks for all the help folks