2014-10-03 79 views
44

我知道從Django 1.7我不需要使用南或任何其他遷移系統,所以我只是使用簡單的命令python manage.py makemigrations您正在試圖添加一個不可空的字段'new_field'到用戶配置文件沒有默認

但是,我得到的是這樣的錯誤:

You are trying to add a non-nullable field 'new_field' to userprofile without a default; 
we can't do that (the database needs something to populate existing rows). 

這裏是models.py:

class UserProfile(models.Model): 
    user = models.OneToOneField(User) 
    website = models.URLField(blank=True) 
    new_field = models.CharField(max_length=140) 

有什麼選擇?

+2

我想補充說,當你改變現有的表格時,而不是當你創建一個新的表格時,會發生問題。 – 2017-05-18 10:48:00

回答

37

您需要提供一個默認值:

new_field = models.CharField(max_length=140, default='SOME STRING') 
+0

如果我需要將new_field作爲網站字段的副本,該怎麼辦?這應該看起來如何? 'default = website'不能完成這項工作 – 2014-10-03 20:17:08

+4

你會想先用假的默認值進行遷移,然後創建一個[數據遷移](https://docs.djangoproject.com/en/1.7/topics/migrations /#data-migrations)遍歷每條記錄並將'new_field'設置爲'website'。 – dgel 2014-10-03 21:32:03

4

如果「網站」可以是空的比new_field也應設置爲空。

現在,如果你想在保存如果new_field是空的,以抓住從「網站」的值,其中添加邏輯,所有你需要做的是覆蓋保存功能爲您Model這樣的:

class UserProfile(models.Model): 
    user = models.OneToOneField(User) 
    website = models.URLField(blank=True, default='DEFAULT VALUE') 
    new_field = models.CharField(max_length=140, blank=True, default='DEFAULT VALUE') 

    def save(self, *args, **kwargs): 
     if not self.new_field: 
      # Setting the value of new_field with website's value 
      self.new_field = self.website 

     # Saving the object with the default save() function 
     super(UserProfile, self).save(*args, **kwargs) 
21

一選項是聲明一個默認值「new_field」:

new_field = models.CharField(max_length=140, default='DEFAULT VALUE') 

另一種選擇是聲明「new_field」作爲一個可爲空欄:

new_field = models.CharField(max_length=140, null=True) 

如果你決定接受「new_field」,你可能要接受「沒有輸入」的「new_field」作爲有效輸入可爲空場。然後,你必須添加blank=True聲明,以及:

new_field = models.CharField(max_length=140, blank=True, null=True) 

即使null=True和/或blank=True如果必要的話,你可以添加一個默認值:

new_field = models.CharField(max_length=140, default='DEFAULT VALUE', blank=True, null=True) 
+0

«避免在基於字符串的字段(如CharField和TextField)上使用null。如果一個基於字符串的字段的值爲null = True,則意味着它有兩個可能的「無數據」值:NULL和空字符串» - [Model field reference](https://docs.djangoproject.com/en/dev/ref/models/fields /#null) – Chema 2017-10-06 07:47:10

2

在NEW_FILE添加布爾屬性無效。

new_field = models.CharField(max_length=140, null=True) 

運行./manage.py syncdb後,刷新數據庫。 最後你運行./manage.py makemigrations./manage.py migrate

38

如果你在早期的開發週期,不在乎有關當前數據庫中的數據你可以刪除它,比遷移。但首先,你需要清理遷移目錄

rm your_app/migrations/* 

rm db.sqlite3 
python manage.py makemigrations 
python manage.py migrate 
+4

還有一件事。你需要清理遷移表 例如:'mysql -u [user] [database] -e「從django_migrations刪除應用程序= [your_app]」' – helpse 2015-12-17 19:18:24

+0

我正在使用windows和rm不起作用。 – 2017-11-18 18:28:29

+0

就是這樣。我認爲Django在遷移和模型檢測等方面很糟糕。希望對此進行重大更新。 – FaithReaper 2018-03-01 10:31:53

2

你已經在表UserProfile數據庫條目?如果是這樣,當您添加新列時,數據庫不知道該如何設置,因爲它不能是NULL。因此,它會詢問您要將列new_fields中的那些字段設置爲。我不得不從該表中刪除所有行來解決這個問題。

(我知道這是前一段時間回答,但我只是碰到了這個問題,這是我的解決方案。希望這將幫助任何新的是看到這一點)

+0

我還沒有插入表中的行,仍然得到這個。正如Tomasz所建議的,我必須刪除所有的遷移歷史記錄,清除遷移表以更改模型。 – FaithReaper 2018-03-01 10:33:14

2

如果你提前進入開發週期,你可以試試這個 -

刪除/評論該模型及其所有用法。應用遷移。這將刪除該模型,然後再次添加模型,運行遷移,並且您添加了新字段的乾淨模型。

0

什麼Django的實際上說的是:

Userprofile table has data in it and there might be new_field values which are null, but I do not know, so are you sure you want to mark property as non nullable, because if you do you might get an error if there are values with NULL

如果你確信沒有在userprofile表中數值是NULL - 下跌自由和忽略警告。

在這種情況下,最好的做法是因爲它在選項2

2) Ignore for now, and let me handle existing rows with NULL myself (e.g. because you added a RunPython or RunSQL operation to handle NULL values in a previous data migration)

在RunPython遷移各國建立一個RunPython遷移來處理空值,你必須找到空new_field值都UserProfile情況下,把一個正確的值(或者Django要求你在模型中設置的默認值)。 你會得到這樣的東西:

# please keep in mind that new_value can be an empty string. You decide whether it is a correct value. 
for profile in UserProfile.objects.filter(new_value__isnull=True).iterator(): 
    profile.new_value = calculate_value(profile) 
    profile.save() # better to use batch save 

玩得開心!

相關問題