在使用Rails应用程序时,我们所有人都必须以某种方式更改数据库列 。 您可以更改列名和列类型 ,也可以使用类型转换来更改列。
更改列名
在更改列之前,我们必须先创建它。 让我们从为配置文件创建模型开始。
class CreateProfiles < ActiveRecord::Migration
def change
create_table :profiles do |t|
t.references :user
t.string :avatar
t.string :name , null: false
end
end
end
一旦运行rake db:migrate ,概要文件数据将被迁移到数据库。 然后我们决定更改列名称 。 我们应该怎么做?
有3种不同的方法可以实现:
- 进行新的迁移。
- 修复现有的迁移。
- 进行迁移以更改表。
一定要跑
rake db :migrate
在所有示例的最后,因此更改将保存在数据库中。
进行新的迁移以更改列名
首先,您需要创建一个新的迁移 :
rails g migration rename_profile_name_to_full_name
然后,在新生成的文件中添加一个rename_column ,指定要更改的表和列:
class RenameProfileNameToFullName < ActiveRecord::Migration
def change
rename_column :profiles , :name , :full_name
end
end
您完成了!
解决现有的迁移
在开始之前,您应该回滚要修复的迁移 。 根据当迁移使你可以通过以下方式做到这一点的:
最后一次迁移:
rakedb: rollback
调用迁移版本:
rakedb: migrate: down VERSION=YOUR_MIGRATION_VERSION
回滚完成后,您可以自由编辑模型。
class CreateProfiles < ActiveRecord::Migration
def change
create_table :profiles do |t|
t.references :user
t.string :avatar
t.string :full_name , null: false
end
end
end
进行新迁移以更改表
一次将多个更改添加到表时,仅应使用此选项。
首先创建一个新的迁移:
rails g migration change_profiles
创建文件后,通过在其位置添加重命名类型来指定要更改的列:
class ChangeProfiles < ActiveRecord::Migration
def change
change_table :profiles do |t|
t.references :user
t.string :avatar
t.rename :name , :full_name # t.string -> t.rename
end
end
end
每次对数据库进行更改后,请始终运行RSpec测试 ,以确保一切正常。 另外,重命名列时,请注意Rails或SQL中的保留名称。 这是一些保留字来帮助您的列表。
更改列类型
这是每个程序员都会遇到的常见更改-从具有一个类型的属性的模型开始,然后您意识到它必须是另一种类型 。 刚开始,您可能会认为应该将配置文件名称存储为文本,而实际上它应该是字符串。
不用担心 您可以通过生成新的迁移轻松解决此问题:
rails g migration change_n ame _ to _ be _ string _ in _p rofiles
现在,打开迁移文件并按以下方式对其进行编辑:
class ChangeNameToBeStringInProfiles < ActiveRecord::Migration
def change
change_column :profiles , :name , :string
end
end
请注意, change_column是不可逆的迁移 。 如果您尝试回滚,将导致错误。 为防止这种情况,请在迁移中修改通常的更改方法,以使用两个单独的上下方法,如下所示:
class ChangeNameToBeStringInProfiles < ActiveRecord::Migration
def up
change_column :profiles , :name , :string
end
def down
change_column :profiles , :name , :text
end
end
测试一下! 首先创建一个配置文件工厂,然后将名称类型更改为字符串。
更改列类型-错误
在某些情况下,仅更改列类型将不起作用。 当您尝试编写将字符串列转换为整数的迁移时:
change_column:profile , :age , :integer
您的数据库将抱怨并引发错误:
PG::DatatypeMismatch: ERROR:column "age" cannot be cast automatically to type integer
HINT: Specify a USING expression to perform the conversion .
为了解决这个问题,我们将遵循提示并在迁移中指定如何转换数据。 有两种方法可以做到这一点:
change_column:profile , :age , 'integer USING CAST(age AS integer)'
change_column:profile , :age , :integer , using: 'age::integer'
而已! 希望这些步骤可以帮助您根据自己的喜好更改数据库列。
先前发布在 kolosek.com/rails-change-database-column/
翻译自: https://hackernoon.com/changing-database-column-in-rails-5-6y1cq3ye7