将具有默认值的 Django 字段迁移到 PostgreSQL 数据库

Migration of Django field with default value to PostgreSQL database

https://docs.djangoproject.com/en/1.10/topics/migrations/

这里说: “就模式支持而言,PostgreSQL 是这里所有数据库中功能最强大的;唯一需要注意的是,添加具有默认值的列将导致 table 的完全重写,持续时间与其大小成正比。

"For this reason, it’s recommended you always create new columns with null=True, as this way they will be added immediately."

我在问我是否正确。 据我了解,我应该首先使用 null=True 创建字段并且没有默认值然后迁移它然后给它一个默认值并再次迁移它,这些值将立即添加, 但否则整个数据库将被重写并且 Django 迁移不想自己完成这个技巧?

据我了解,在第二次迁移时,默认值不会写入现有行。仅当创建新行且默认字段没有值时才会写入。

我认为对新列使用 null=True 的警告仅与性能有关。如果您真的希望所有现有行都具有默认值,只需使用 default= 并接受 table 重写的性能后果。

在同一页中还提到:

In addition, MySQL will fully rewrite tables for almost every schema operation and generally takes a time proportional to the number of rows in the table to add or remove columns. On slower hardware this can be worse than a minute per million rows - adding a few columns to a table with just a few million rows could lock your site up for over ten minutes.

SQLite has very little built-in schema alteration support, and so Django attempts to emulate it by:

Creating a new table with the new schema Copying the data across Dropping the old table Renaming the new table to match the original name

所以简而言之,你上面提到的那句话真正说的是

postgresql exhibits mysql like behaviour when adding a new column with a default value

您尝试的方法会奏效。添加一个空列将意味着没有 table 重写。然后您可以将该列更改为具有默认值。但是 现有的空值将继续为空值