添加迁移行

发布于 2024-07-10 11:44:31 字数 520 浏览 3 评论 0原文

我想知道在 Rails 迁移中向数据库表添加记录的首选方法是什么。 我读过 Ola Bini 的书(Jruby on Rails),他做了这样的事情:

class CreateProductCategories < ActiveRecord::Migration

  #defines the AR class
  class ProductType < ActiveRecord::Base; end

  def self.up

    #CREATE THE TABLES...

    load_data
  end
  def self.load_data
    #Use AR object to create default data
    ProductType.create(:name => "type")
  end
end

这很漂亮,很干净,但由于某种原因,不适用于最新版本的 Rails...

问题是,你怎么做使用默认数据(例如用户或其他数据)填充数据库?

谢谢!

I'd like to know which is the preferred way to add records to a database table in a Rails Migration. I've read on Ola Bini's book (Jruby on Rails) that he does something like this:

class CreateProductCategories < ActiveRecord::Migration

  #defines the AR class
  class ProductType < ActiveRecord::Base; end

  def self.up

    #CREATE THE TABLES...

    load_data
  end
  def self.load_data
    #Use AR object to create default data
    ProductType.create(:name => "type")
  end
end

This is nice and clean but for some reason, doesn't work on the lasts versions of rails...

The question is, how do you populate the database with default data (like users or something)?

Thanks!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

翻了热茶 2024-07-17 11:44:31

Rails API 迁移文档展示了实现此目的的更简单方法。

http://api.rubyonrails.org/classes/ActiveRecord/Migration.html

class CreateProductCategories < ActiveRecord::Migration
  def self.up
    create_table "product_categories" do |t|
      t.string name
      # etc.
    end

    # Now populate the category list with default data

    ProductCategory.create :name => 'Books', ...
    ProductCategory.create :name => 'Games', ... # Etc.

    # The "down" method takes care of the data because it
    # drops the whole table.

  end

  def self.down
    drop_table "product_categories"
  end
end

在 Rails 2.3.0 上进行了测试,但这也应该适用于许多早期版本。

The Rails API documentation for migrations shows a simpler way to achieve this.

http://api.rubyonrails.org/classes/ActiveRecord/Migration.html

class CreateProductCategories < ActiveRecord::Migration
  def self.up
    create_table "product_categories" do |t|
      t.string name
      # etc.
    end

    # Now populate the category list with default data

    ProductCategory.create :name => 'Books', ...
    ProductCategory.create :name => 'Games', ... # Etc.

    # The "down" method takes care of the data because it
    # drops the whole table.

  end

  def self.down
    drop_table "product_categories"
  end
end

Tested on Rails 2.3.0, but this should work for many earlier versions too.

最丧也最甜 2024-07-17 11:44:31

您可以为此使用固定装置。 这意味着在某个地方有一个 yaml 文件,其中包含要插入的数据。

这是我在我的一个应用程序中为此提交的更改集:

db/migrate/004_load_profiles.rb

require 'active_record/fixtures'

class LoadProfiles < ActiveRecord::Migration
  def self.up
    down()

    directory = File.join(File.dirname(__FILE__), "init_data")
    Fixtures.create_fixtures(directory, "profiles")
  end

  def self.down
    Profile.delete_all
  end
end

db/migrate/init_data/profiles.yaml

admin:
 name: Admin
  value: 1
normal:
 name: Normal user
  value: 2

You could use fixtures for that. It means having a yaml file somewhere with the data you want to insert.

Here is a changeset I committed for this in one of my app:

db/migrate/004_load_profiles.rb

require 'active_record/fixtures'

class LoadProfiles < ActiveRecord::Migration
  def self.up
    down()

    directory = File.join(File.dirname(__FILE__), "init_data")
    Fixtures.create_fixtures(directory, "profiles")
  end

  def self.down
    Profile.delete_all
  end
end

db/migrate/init_data/profiles.yaml

admin:
 name: Admin
  value: 1
normal:
 name: Normal user
  value: 2
长亭外,古道边 2024-07-17 11:44:31

您还可以在 seeds.rb 文件中定义,例如:

Grid.create :ref_code => 'one' , :name => 'Grade Única'

并在运行后:

rake db:seed

You could also define in your seeds.rb file, for instance:

Grid.create :ref_code => 'one' , :name => 'Grade Única'

and after run:

rake db:seed
乖乖兔^ω^ 2024-07-17 11:44:31

您的迁移可以访问所有模型,因此您不应该在迁移中创建类。

我正在使用最新的 Rails,并且我可以确认您发布的示例绝对应该工作。

然而,迁徙是一种特殊的野兽。 只要您清楚,我就看不出 ActiveRecord::Base.connection.execute("INSERT INTO Product_types (name) VALUES ('type1'), ('type2')")< 有什么问题/代码>。

这样做的优点是,您可以通过使用某种 GUI 或 Web 前端填充起始数据,然后执行 mysqldump -uroot database_name.product_types 来轻松生成它。

对于将要执行迁移和维护产品的人员来说,无论哪种方式都可以让事情变得最简单。

your migrations have access to all your models, so you shouldn't be creating a class inside the migration.

I am using the latest rails, and I can confirm that the example you posted definitely OUGHT to work.

However, migrations are a special beast. As long as you are clear, I don't see anything wrong with an ActiveRecord::Base.connection.execute("INSERT INTO product_types (name) VALUES ('type1'), ('type2')").

The advantage to this is, you can easily generate it by using some kind of GUI or web front-end to populate your starting data, and then doing a mysqldump -uroot database_name.product_types.

Whatever makes things easiest for the kind of person who's going to be executing your migrations and maintaining the product.

瀟灑尐姊 2024-07-17 11:44:31

你真的不应该

ProductType.create

在迁移中使用。

我也做过类似的事情,但从长远来看,它们不能保证有效。

当您运行迁移时,您使用的模型类是您运行迁移时的模型类,而不是您创建迁移时的模型类。 您必须确保永远不会以阻止迁移运行的方式更改模型。

例如,运行 SQL 会更好:

[{name: 'Type', ..}, .. ].each do |type|
  execute("INSERT INTO product_types (name) VALUES ('#{type[:name]} .. )
end

You should really not use

ProductType.create

in your migrations.

I have done similar but in the long run they are not guaranteed to work.

When you run the migration the model class you are using is the one at the time you run the migration, not the one at the time you created the migration. You will have to be sure you never change your model in such a way to stop you migration from running.

You are much better off running SQL for example:

[{name: 'Type', ..}, .. ].each do |type|
  execute("INSERT INTO product_types (name) VALUES ('#{type[:name]} .. )
end
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文