Ruby on Rails迁移从字符串转换为十进制

时间:2016-03-10 13:56:03

标签: ruby-on-rails ruby postgresql

我已经创建了一个数据库,并且已经输入了大约30-40个条目到数据库中但是有一个错误,我不小心将数据库的某些列设置为字符串,当我需要它们为小数时才能执行操作在他们身上。

为了更改数据库,我生成了一个包含此文件的迁移文件。

class ChangeOddsAndUnitsColumn < ActiveRecord::Migration
  def change
    change_column :bets, :units_placed, :decimal
    change_column :bets, :odds, :decimal
  end
end

但是,当我运行rake db:migrate时,我收到以下错误

PG::DatatypeMismatch: ERROR:  column "units_placed" cannot be cast automatically to type numeric

每列中的值都是十进制数,但我无法弄清楚如何将它们从字符串转换为十进制类型。

2 个答案:

答案 0 :(得分:2)

您所做的是原子操作,首先删除您不会使用的列。然后创建十进制类型的列。最后更新表并分配值。如果您不想丢失信息,那么您应该通过转换类型的SQL更新过程来支持它。我希望你能成为一个方向。问候。

  

Lo que debes hacer esunaoperaciónatómica,donde primero elimines la columna que no vas a utilizar。 Luego crear la columna de tipo decimal。由últimoactualizarla tabla y asignarle valores提供。 En caso de que no quieras perderlainformacióndeberíasrespaldarlapara luego atravésdeun procedimiento SQL actualicen convirtiendo los tipos。 Espero que te haya servido comounaindientación。 Saludos。

class ChangeOddsAndUnitsColumn < ActiveRecord::Migration
  def up
    change_table :bets do |t|
      t.decimal :units_placed, precision: 16, scale: 2
    end
    Bets.update_all ["units_placed = ?", 0.0]
  end

  def down
    remove_column :bets, :units_placed
  end
end

答案 1 :(得分:0)

在我使用Rails 6的情况下,这就是我所做的(类型铸造)

class StringToDecimalConverter < ActiveRecord::Migration[6.0]
 def up
   change_column_default :table, :attr, nil
   change_column :table, :attr, "decimal USING CAST( attr AS decimal)"
   change_column :table, :attr, :decimal, precision: 21, scale: 3, default: 0.0    
 end

 def down
   change_column :table, :attr, :string, default: "0"
 end
end

就我而言,原因

change_column_default :table, :attr, nil

如果您设置了默认值,则无法自动强制转换,因此将其设置为nil首先可以解决此问题

也不能在同一change_column行中设置精度