gpt4 book ai didi

python - 如何修改数据库中已经迁移的模型?

转载 作者:行者123 更新时间:2023-12-02 09:45:55 24 4
gpt4 key购买 nike

我是 django 新手,我想修改我的模型(它已经在我的 sqlite3 数据库中)而不妨碍我的整个项目。上次我修改模型时花了几个小时才修复它,因为我对整个项目进行了窃听。所以我不想犯同样的错误,你们能帮我处理命令吗?感谢您的帮助

models.py(目前)

from django.db import models

THE_GENDER = [
("Monsieur", "Monsieur"),
("Madame", "Madame")
]


class Post(models.Model):


name = models.CharField(max_length=100)
email = models.CharField(max_length=100)
gender = models.CharField(max_length=8, choices=THE_GENDER)
number = models.CharField(max_length=100)


def __str__(self):
return self.name

我想要对模型进行的编辑(我想将作者用户添加到模型中。这样我就知道谁在制作表单。)

from django.db import models
from django.contrib.auth.models import User

THE_GENDER = [
("Monsieur", "Monsieur"),
("Madame", "Madame")
]


class Post(models.Model):


name = models.CharField(max_length=100)
email = models.CharField(max_length=100)
gender = models.CharField(max_length=8, choices=THE_GENDER)
number = models.CharField(max_length=100)
author = models.ForeignKey(User, on_delete=models.CASCADE)


def __str__(self):
return self.name

我的 admin.py 文件(不确定是否需要保持不变或修改它)

from django.contrib import admin
from .models import Post

admin.site.register(Post)

我的 forms.py 文件

from django import forms
from .models import Post
from crispy_forms.helper import FormHelper


class post_form(forms.ModelForm):

def __init__(self, *args, **kwargs):
super(post_form, self).__init__(*args, **kwargs)

self.helper = FormHelper(self)

class Meta:
model = Post
fields = ["name", "email", "gender", "number"]


View .py

from django.shortcuts import render
from django.http import HttpResponse
from .forms import post_form


# Create your views here.
def home(request):
form = post_form(request.POST or None)
if form.is_valid():
form.save()

context = {
"form": form
}


return render(request, "sms/home.html", context)

最佳答案

详细说明我上面的评论...

在 Django 中添加新的不可为 null 的外键通常需要三个步骤。

  1. 首先,使用 null=True 将新的foreignKey 添加到模型定义中,然后运行makemigrations。这将创建一个将添加该字段的迁移,没有什么特别的。执行此迁移将添加一个列,其中所有行的值都为 NULL
  2. 其次,为同一应用创建一个新的空迁移 (makemigrations --empty),然后编辑该迁移以包含数据迁移步骤。您需要在此处根据您的业务逻辑为新外键选择一些值。
  3. 第三,修改模型定义中的ForeignKey 以设置null=False 并使用makemigrations 创建第三个迁移。 Django 会询问您是否以某种方式处理过 null - 您需要说“是的,我发誓我已经处理过”(因为您已经这样做了,在上面的步骤 2 中)。

实际上,对于OP问题的简化版本,我们需要添加用户外键:

原始状态

class Post(models.Model):
name = models.CharField(max_length=100)

1a。添加可为空的字段。

class Post(models.Model):
name = models.CharField(max_length=100)
author = models.ForeignKey(User, null=True, on_delete=models.CASCADE))

1b。运行 makemigrations。

$ python manage.py makemigrations
Migrations for 'something':
something/migrations/0002_post_author.py
- Add field author to post

2a。创建一个新的空迁移。

$ python manage.py makemigrations something --empty -n assign_author
Migrations for 'something':
something/migrations/0003_assign_author.py

2b。编辑迁移文件。

有关数据迁移的更多信息,一如既往,in the manual .

from django.db import migrations


def assign_author(apps, schema_editor):
User = apps.get_model('auth', 'User') # or whatever is your User model
Post = apps.get_model('something', 'Post') # or wherever your Post model is
user = User.objects.filter(is_superuser=True).first() # Choose some user...
assert user # ... and ensure it exists...
Post.objects.all().update(author=user) # and bulk update all posts.


class Migration(migrations.Migration):

dependencies = [...]

operations = [
migrations.RunPython(assign_author, migrations.RunPython.noop),
]

3a。使该字段不可为空。

class Post(models.Model):
name = models.CharField(max_length=100)
author = models.ForeignKey(User, null=False, on_delete=models.CASCADE))

3b。运行 Makemigrations。

如实回答问题 - 您刚刚添加了一个 RunPython 操作。

$ python manage.py makemigrations something -n post_author_non_null
You are trying to change the nullable field 'author' on something. to non-nullable 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) 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)
3) Quit, and let me add a default in models.py
Select an option: 2
Migrations for 'something':
something/migrations/0004_post_author_non_null.py
- Alter field author on post

全部完成!

运行 migrate 现在将运行这三个迁移,并且您的模型将具有 author 而不会丢失数据。

关于python - 如何修改数据库中已经迁移的模型?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60191615/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com