简体   繁体   中英

Django makemigrations tool fails if i change the foreign key / other relationships at models

I have a problem with Djang makemigrations / migrate tool

  1. I have a Withdraw model with foreignkey to an Employee table. Everything is working fine

models.py

from django.contrib.auth.models import User

class Withdraw(models.Model):
    employee_id = models.ForeignKey(Employee, on_delete = models.PROTECT)
    amount = models.IntegerField(default=0)
    withdraw_date = models.DateTimeField(default=timezone.now)
    is_confirmed_by_employer = models.BooleanField(default=False)
  1. I want to change it and have user as a foreignkey to user:

    user = models.ForeignKey(User, on_delete=models.CASCADE)

  2. I run makemigrations and I have this errormessage:

You are trying to add a non-nullable field 'user' to withdraw without a default; we can't do that (the database needs something to populate existing rows). Please select a fix: 1) Provide a one-off default now (will be set on all existing rows with a null value for this column) 2) Quit, and let me add a default in models.py

  1. If I press 1, then I have the following message, what I dont really get, why shall I put datetime or timezone.now to user??

Select an option: 1 Please enter the default value now, as valid Python The datetime and django.utils.timezone modules are available, so you can do eg timezone.now Type 'exit' to exit this prompt

  1. I tried to delete migrates folder and recreate migration files as was adviced in some other forum posts. When I recreate the migrations with createmigrations Withdraw command and migrate it to postgresSql the Withdraw table is not created however the tool is writing that the table is created and migrated.

So Either way, Im not able to migrate this small change to the DB. Do you have any opinions? Thx!

Not adding a default or making the field null, requires to populate all your exiting entries. You can just make the field be able to be Null.

user = models.ForeignKey(User, null=True, blank=True, on_delete=models.CASCADE)

or on step 4 you could just input any existing user's id. (1 would be your first account created if you didn't remove it.)

Yes this is natural behavior.

What happened here is, When first you made other rows in database (earlier before making User field) User field was not there, and now when you are adding a User field in this database you are not setting it to null or blank so Django asks "what about previous saved rows? They can't be null." So best option was to fill those fields by providing one off default value. To do that you had to choose option 1 and then fill those missing spaces.

I do not recommend answer given by @jTiKey as if you allow users field to be blank or null, user could withdraw without giving in Users field and I think you'll not want that.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM