正如u/heppy
Reddit 上指出的那样,我最初的实现存在错误。我在填充书籍的新作者外键之前删除了作者的 ID,这意味着该书对作者 ID 的引用不再具有任何意义。我已经修复了这个问题。请参阅此处的原始评论。
这是一个棘手的操作,特别是当其他模型具有目标模型的外键时。一个简短的例子:
from django.db import models
class Author(models.Model):
name = models.CharField(max_length=255)
class Book(models.Model):
title = models.CharField(max_length=255)
author = models.ForeignKey(Author, on_delete=models.CASCADE)
这很棘手,因为Book
引用了Author
via id
,而它目前是一个整数。当它变为uuid
though时,Book
将对字段有一个整数引用,数据库将引发错误。我们通过将外键降级为常规并慢慢调整它以使用新的主键来uuid
解决这个问题。IntegerField
uuid
Book
步骤:冷库 www.cqzlsb.com
-
添加
uuid
字段,Author
同时将该字段保留id
为整数 -
按照https://docs.djangoproject.com/en/5.0/howto/writing-migrations/#migrations-that-add-unique-fields进行
uuid
迁移 -
Book
将author
外键引用更改Author
为整数 -
将 设
uuid
为主Author
键 -
重
Book
命名author
为author_old
-
添加新的
author
外键字段Book
-
创建新的空迁移
python
manage.pymakemigrations --empty library
-
添加一个
RunPython
步骤来清空迁移,填充author
每author_old
本书的行 -
消除
Author'sid
-
重
Author
命名uuid
为id
-
降低
author_old
-
再次使为
Book
空author
-
压缩新的迁移(Migrations | Django documentation | Django)。这可确保如果只应用了一半的迁移,数据库不会处于奇怪的状态。
-
python
manage.pysquashmigrations library 0002 0012
-
按照命令输出和迁移文件中所述的步骤将自定义
populate_*
函数复制到压缩的迁移中 -
删除压缩迁移所替换的旧迁移
-
重命名压缩的迁移
-
使用ulid
(Python libs that I wish were part of the standard library)而不是标准可获得奖励积分uuid.uuid4
!
查看我的示例存储库的 git 提交历史记录,可在https://github.com/thuibr/django-uuid-migration-example找到。这是查看每个步骤结果的好方法