python - 在现有 Django 应用程序中更改主键的最佳方法是什么?

标签 python django data-migration django-south

我有一个处于 BETA 模式的应用程序。这个应用程序的模型有一些具有显式主键的类。因此 Django 使用字段并且不会自动创建 id。

class Something(models.Model):
    name = models.CharField(max_length=64, primary_key=True)

我认为这是个坏主意(请参阅 unicode error when saving an object in django admin),我想返回并为我的模型的每个类设置一个 id。

class Something(models.Model):
    name = models.CharField(max_length=64, db_index=True)

我已经对我的模型进行了更改(将每个 primary_key=True 替换为 db_index=True)并且我想使用 south 迁移数据库.

很遗憾,迁移失败并显示以下消息: ValueError: 不能添加没有默认值的 null=False 列。

我正在评估针对此问题的不同解决方法。有什么建议吗?

感谢您的帮助

最佳答案

同意,您的模型可能是错误的。

正式的主键应始终是代理键。从来没有别的。 【强词夺理。自 1980 年代以来一直是数据库设计师。重要的经验教训是:一切都是可变的,即使用户在他们母亲的坟墓上发誓值(value)无法改变,这确实是一把可以作为主要的天然 key 。这不是主要的。只有代理可以是主要的。]

您正在做心脏直视手术。不要搞乱模式迁移。您正在替换架构。​​

  1. 将您的数据卸载到 JSON 文件中。为此,请使用 Django 自己的内部 django-admin.py 工具。您应该为每个将要更改的文件和依赖于正在创建的键的每个表创建一个卸载文件。单独的文件使这更容易做到。

  2. 删除要从旧架构更改的表。

    依赖于这些表的表将更改其 FK;你可以 就地更新行,或者——它可能更简单——删除并重新插入 这些行也是。

  3. 创建新架构。这只会创建正在更改的表。

  4. 编写脚本以使用新键读取和重新加载数据。这些都很短而且非常相似。每个脚本都会使用 json.load() 从源文件中读取对象;然后,您将从为您构建的 JSON 元组行对象创建架构对象。然后您可以将它们插入到数据库中。

    你有两个案例。

    • 更改 PK 的表将被插入并获得新的 PK。这些必须“级联”到其他表,以确保其他表的 FK 也被更改。

    • 具有更改的 FK 的表必须在外部表中找到行并更新其 FK 引用。

另一种选择。

  1. 重命名所有旧表。

  2. 创建整个新架构。

  3. 编写 SQL 将所有数据从旧模式迁移到新模式。这将不得不巧妙地重新分配键。

  4. 删除重命名的旧表。

 

关于python - 在现有 Django 应用程序中更改主键的最佳方法是什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2055784/

相关文章:

sql - 如何将数据从 MongoDB 迁移到 SQL-Server?

python - 如何使用 python 检查来自 API 的数据是否在 elasticsearch 索引中,如果不在,则将其插入

python - 访问元组中值的有效方法(python)

django radioselect 渲染到表格

django - 调试自定义django管理命令

python - Django、WSGI 和 Apache 的语法错误

unit-testing - 如何对 Django South "datamigration"进行单元测试

python - 在python中迭代文件夹中的文件名后获取最新的文件名

Python,多处理 : what to do if process. join() 永远等待?

php - Doctrine 2 迁移工作流程