Rails 迁移将数据类型从 :bigint 更改为 :integer
Rails Migration Changes Datatype from :bigint to :integer
我最近创建了一个迁移来更新一些数据,在我 运行 它之后,迁移将我的一堆 schema.rb
列定义从 :bigint
更改为 :integer
我过去曾多次注意到这一点。有时迁移会将它们从 :bigint
更改为 :integer
,其他时候反之亦然。
为什么会发生这种情况,我该如何预防?我想将它们保留为 :bigint
我 运行 Ruby Rails 7.0.2.3 和 PostgreSQL 14.2
谢谢
不确定原因,但据我所知,这个问题出现在 RoR 版本 3 或 4 中。
您需要使用这样的格式
tbl.column :really_big_int, :bigint
我想通了....
问题: 数据库类型与模式不同,因此迁移时 运行,rails 实现了实际数据库中的类型不同,所以它为我更新了架构。
为什么我们的类型不同?
我从 Heroku 中提取了一个数据库转储,以便在本地复制一个我无法复制的问题(它只发生在 Heroku 上的那个数据集)。这样做后,这个问题就开始了。
问题是 Heroku 是 运行ning Postgres 13.6,并且出于某种原因,该数据库中的列类型是 integer
。
本地我是 运行ning Postgres 14.2,本地类型是 bigint
。
如果迁移没有任何改变,为什么要更新 schema.rb 文件?
发生这种情况是因为 db:schema:dump
是自动迁移后的 运行。这发生在 Rails.
中的 database.rake
文件中
来源:https://github.com/rails/rails/blob/main/activerecord/lib/active_record/railties/databases.rake#L105
换句话说,迁移得到 运行,然后 Active Record 自动转储模式。
由于数据类型不同,新模式转储与原始模式不同。因此 schema.rb
文件已更新(如果您使用的是 annotate
gem,则还更新任何模型文件)。
我怎么知道的?
使用 psql
登录数据库并检查。
- 本地:
psql -h localhost
- Heroku:
heroku pg:psql -a your-app-name
然后检查 table:
\d table_name
你会得到这样的东西:
Table "public.account_invitations"
Column | Type | Collation | Nullable | Default
---------------+--------------------------------+-----------+----------+-------------------------------------------------
id | bigint | | not null | nextval('account_invitations_id_seq'::regclass)
account_id | integer | | not null |
invited_by_id | integer | | |
token | character varying | | not null |
在那里您可以看到列类型。在本地,它们是 bigint
使用 Postgres 14.2,但在 Heroku 上,它们是 integer
使用 Postgres 13.6。
当我拉下一个转储时,我从那个转储中恢复了本地数据库,这改变了数据库与模式中的内容。
修复:
恢复了我的数据库的原始版本,运行 迁移,没有对架构进行任何更改。
如何检验这个理论...
进入数据库控制台并将列从 integer
更改为 bigint
,反之亦然。然后 运行 迁移。您会注意到您的架构文件已更新,即使您的迁移可能与这些列无关。
我最近创建了一个迁移来更新一些数据,在我 运行 它之后,迁移将我的一堆 schema.rb
列定义从 :bigint
更改为 :integer
我过去曾多次注意到这一点。有时迁移会将它们从 :bigint
更改为 :integer
,其他时候反之亦然。
为什么会发生这种情况,我该如何预防?我想将它们保留为 :bigint
我 运行 Ruby Rails 7.0.2.3 和 PostgreSQL 14.2
谢谢
不确定原因,但据我所知,这个问题出现在 RoR 版本 3 或 4 中。 您需要使用这样的格式
tbl.column :really_big_int, :bigint
我想通了....
问题: 数据库类型与模式不同,因此迁移时 运行,rails 实现了实际数据库中的类型不同,所以它为我更新了架构。
为什么我们的类型不同?
我从 Heroku 中提取了一个数据库转储,以便在本地复制一个我无法复制的问题(它只发生在 Heroku 上的那个数据集)。这样做后,这个问题就开始了。
问题是 Heroku 是 运行ning Postgres 13.6,并且出于某种原因,该数据库中的列类型是 integer
。
本地我是 运行ning Postgres 14.2,本地类型是 bigint
。
如果迁移没有任何改变,为什么要更新 schema.rb 文件?
发生这种情况是因为 db:schema:dump
是自动迁移后的 运行。这发生在 Rails.
database.rake
文件中
来源:https://github.com/rails/rails/blob/main/activerecord/lib/active_record/railties/databases.rake#L105
换句话说,迁移得到 运行,然后 Active Record 自动转储模式。
由于数据类型不同,新模式转储与原始模式不同。因此 schema.rb
文件已更新(如果您使用的是 annotate
gem,则还更新任何模型文件)。
我怎么知道的?
使用 psql
登录数据库并检查。
- 本地:
psql -h localhost
- Heroku:
heroku pg:psql -a your-app-name
然后检查 table:
\d table_name
你会得到这样的东西:
Table "public.account_invitations"
Column | Type | Collation | Nullable | Default
---------------+--------------------------------+-----------+----------+-------------------------------------------------
id | bigint | | not null | nextval('account_invitations_id_seq'::regclass)
account_id | integer | | not null |
invited_by_id | integer | | |
token | character varying | | not null |
在那里您可以看到列类型。在本地,它们是 bigint
使用 Postgres 14.2,但在 Heroku 上,它们是 integer
使用 Postgres 13.6。
当我拉下一个转储时,我从那个转储中恢复了本地数据库,这改变了数据库与模式中的内容。
修复: 恢复了我的数据库的原始版本,运行 迁移,没有对架构进行任何更改。
如何检验这个理论...
进入数据库控制台并将列从 integer
更改为 bigint
,反之亦然。然后 运行 迁移。您会注意到您的架构文件已更新,即使您的迁移可能与这些列无关。