首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >如何在两个Django应用程序之间移动模型(Django 1.7)

如何在两个Django应用程序之间移动模型(Django 1.7)
EN

Stack Overflow用户
提问于 2014-09-03 23:36:37
回答 4查看 36.2K关注 0票数 143

所以大约一年前我开始了一个项目,像所有的新开发人员一样,我并没有太关注结构,但是现在我随着Django的深入,我的项目布局主要是我的模型在结构上很糟糕。

我有模型主要持有在一个单一的应用程序,真的这些模型中的大多数应该在自己的个人应用程序,我确实试图解决这个问题,并将它们向南移动,但我发现由于外键等原因,它很棘手,真的很难。

然而,由于Django 1.7和对迁移的内置支持,现在有没有更好的方法来做到这一点?

EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2014-09-04 03:13:09

我正在删除旧答案,因为这可能会导致数据丢失。作为ozan mentioned,我们可以在每个应用程序中创建2个迁移。这篇文章下面的评论引用了我以前的答案。

从第一个应用程序中删除模型的第一个迁移。

代码语言:javascript
复制
$ python manage.py makemigrations old_app --empty

编辑迁移文件以包含这些操作。

代码语言:javascript
复制
class Migration(migrations.Migration):

    database_operations = [migrations.AlterModelTable('TheModel', 'newapp_themodel')]

    state_operations = [migrations.DeleteModel('TheModel')]

    operations = [
      migrations.SeparateDatabaseAndState(
        database_operations=database_operations,
        state_operations=state_operations)
    ]

第二次迁移依赖于第一次迁移,并在第二个应用程序中创建新表。将模型代码移动到第二个应用程序后

代码语言:javascript
复制
$ python manage.py makemigrations new_app 

并将迁移文件编辑为类似下面这样的内容。

代码语言:javascript
复制
class Migration(migrations.Migration):

    dependencies = [
        ('old_app', 'above_migration')
    ]

    state_operations = [
        migrations.CreateModel(
            name='TheModel',
            fields=[
                ('id', models.AutoField(verbose_name='ID', serialize=False, auto_created=True, primary_key=True)),
            ],
            options={
                'db_table': 'newapp_themodel',
            },
            bases=(models.Model,),
        )
    ]

    operations = [
        migrations.SeparateDatabaseAndState(state_operations=state_operations)
    ]
票数 27
EN

Stack Overflow用户

发布于 2014-10-21 02:30:12

使用migrations.SeparateDatabaseAndState可以相当容易地做到这一点。基本上,我们使用一个数据库操作来同时重命名表,同时使用两个状态操作来从一个应用程序的历史记录中删除模型,并在另一个应用程序的历史记录中创建模型。

从旧应用中删除

代码语言:javascript
复制
python manage.py makemigrations old_app --empty

在迁移中:

代码语言:javascript
复制
class Migration(migrations.Migration):

    dependencies = []

    database_operations = [
        migrations.AlterModelTable('TheModel', 'newapp_themodel')
    ]

    state_operations = [
        migrations.DeleteModel('TheModel')
    ]

    operations = [
        migrations.SeparateDatabaseAndState(
            database_operations=database_operations,
            state_operations=state_operations)
    ]

添加到新应用

首先,将模型复制到新应用程序的model.py中,然后:

代码语言:javascript
复制
python manage.py makemigrations new_app

这将生成一个迁移,将一个简单的CreateModel操作作为唯一的操作。将其包装在SeparateDatabaseAndState操作中,这样我们就不会尝试重新创建表。还要将之前的迁移作为依赖项包括在内:

代码语言:javascript
复制
class Migration(migrations.Migration):

    dependencies = [
        ('old_app', 'above_migration')
    ]

    state_operations = [
        migrations.CreateModel(
            name='TheModel',
            fields=[
                ('id', models.AutoField(verbose_name='ID', serialize=False, auto_created=True, primary_key=True)),
            ],
            options={
                'db_table': 'newapp_themodel',
            },
            bases=(models.Model,),
        )
    ]

    operations = [
        migrations.SeparateDatabaseAndState(state_operations=state_operations)
    ]
票数 356
EN

Stack Overflow用户

发布于 2017-11-20 21:23:03

抄袭自我在https://stackoverflow.com/a/47392970/8971048的回答

如果您需要移动模型,并且您不再具有应用程序的访问权限(或者您不想要访问权限),您可以创建一个新的操作,并仅当迁移的模型不存在时才考虑创建新的模型。

在本例中,我将'MyModel‘从old_app传递给我的应用程序。

代码语言:javascript
复制
class MigrateOrCreateTable(migrations.CreateModel):
    def __init__(self, source_table, dst_table, *args, **kwargs):
        super(MigrateOrCreateTable, self).__init__(*args, **kwargs)
        self.source_table = source_table
        self.dst_table = dst_table

    def database_forwards(self, app_label, schema_editor, from_state, to_state):
        table_exists = self.source_table in schema_editor.connection.introspection.table_names()
        if table_exists:
            with schema_editor.connection.cursor() as cursor:
                cursor.execute("RENAME TABLE {} TO {};".format(self.source_table, self.dst_table))
        else:
            return super(MigrateOrCreateTable, self).database_forwards(app_label, schema_editor, from_state, to_state)


class Migration(migrations.Migration):

    dependencies = [
        ('myapp', '0002_some_migration'),
    ]

    operations = [
        MigrateOrCreateTable(
            source_table='old_app_mymodel',
            dst_table='myapp_mymodel',
            name='MyModel',
            fields=[
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
                ('name', models.CharField(max_length=18))
            ],
        ),
    ]
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/25648393

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档