关于python:Django 1.8:删除/重命名数据迁移中的模型字段

Django 1.8: Delete/rename a model field in data migration

我需要将模型字段的关系从foreignkey更改为manytomanyfield。这伴随着数据迁移,以更新预先存在的数据。

以下是原始模型(models.py):

1
2
3
4
5
6
7
class DealBase(models.Model):

    [...]
    categoria = models.ForeignKey('Categoria')
    [...]

    )

我需要模型字段"categoria"与应用程序"deal"中的模型"categoria"建立许多关系。

我所做的:

  • 在DealBase中创建一个新字段"categoria_tmp"

    1
    2
    3
    class DealBase(models.Model):
         categoria = models.ForeignKey('Categoria')
         categoria_tmp = models.ManyToManyField('Categoria',related_name='categoria-temp')

  • 进行架构迁移


    python manage.py makemigrations

  • 编辑migrationfile.py将数据从categoria迁移到categoria tmp

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    def copy_deal_to_dealtmp(apps, schema_editor):
        DealBase = apps.get_model('deal', 'DealBase')

        for deal in DealBase.objects.all():
            deal.categoria_tmp.add(deal.categoria)
            deal.save()

    class Migration(migrations.Migration):

        dependencies = [
          ('deal', '0017_dealbase_indirizzo'),
        ]

        operations = [
           migrations.AddField(
           model_name='dealbase',
           name='categoria_tmp',
           field=models.ManyToManyField(related_name='categoria-temp', to='deal.Categoria'),
           preserve_default=True,
          ),

           migrations.RunPython(
            copy_deal_to_dealtmp
           )
          ]
  • 进行数据迁移


    python manage.py migrate

  • 最后,我需要删除列"dealbase.categoria",并将列"dealbase.categoria tmp"重命名为"dealbase.categoria"

  • 我被困在第五步。

    有人能帮我吗?我在网上找不到答案,我用的是django 1.8。

    谢谢!


    您只需要创建两个额外的迁移:一个用于删除旧字段,另一个用于更改新字段。

    首先删除dealbase.categoria并创建迁移,然后将dealbase.categoria-tmp重命名为dealbase.categoria并创建另一个迁移。

    这将删除第一个字段,然后将tmp字段更改为正确的名称。


    试试这个,可能对你有帮助。

  • 第一步作为你的

    1
    python manage.py makemigrations && python manage.py migrate
  • 打开shell

    1
    2
    for i in DealBase.objects.all()
        i.categoria_tmp.add(i.categoria)

  • 删除你的字段categoria

    1
    python manage.py makemigrations && python manage.py migrate
  • 添加字段

    1
    categoria = models.ManyToManyField('Categoria',related_name='categoria-temp')

    然后

    1
    python manage.py makemigrations && python manage.py migrate
  • 打开shell

    1
    2
    3
    for i in DealBase.objects.all():
        for j in i.categoria_tmp.all():
            i.categoria.add(j)

  • 删除字段categoria_tmp

    1
    python manage.py makemigrations && python manage.py migrate