【问题标题】:How to create migrations for Rails with multiple databases如何使用多个数据库为 Rails 创建迁移
【发布时间】:2018-03-16 22:39:38
【问题描述】:

我发现this question 非常有趣,我想了解如何生成迁移以在我的项目中使用的其他数据库中创建表。

我怎样才能使这样的迁移在第二个数据库中生成表?

class CreateOriginalCompanies < ActiveRecord::Migration
  def change
    create_table :original_companies do |t|
      t.string :CompanyName
      t.string :RegAddress_AddressLine1
      t.string :RegAddress_AddressLine2
      t.string :RegAddress_PostTown
      t.string :RegAddress_Country
      t.string :RegAddress_PostCode
      t.string :CompanyCategory
      t.string :CompanyStatus

      t.timestamps null: false
    end
  end
end

有什么线索吗?

【问题讨论】:

    标签: mysql ruby-on-rails ruby


    【解决方案1】:

    耙任务

    让我们开始吧。显然我们想要处理两个数据库的迁移,所以我们需要两个单独的 Rake 任务来处理它:

    desc "Migrate the database through scripts in db/migrate."
    namespace :db do
      task :migrate do
        Rake::Task["db:migrate_db1"].invoke
        Rake::Task["db:migrate_db2"].invoke
      end
    
      task :migrate_db1 do
        ActiveRecord::Base.establish_connection DB1_CONF
        ActiveRecord::Migrator.migrate("db/migrate/db1/")
      end
    
      task :migrate_db2 do
        ActiveRecord::Base.establish_connection DB2_CONF
        ActiveRecord::Migrator.migrate("db/migrate/db2/")
      end
    end
    

    我们在这里的第一个任务是db:migrate,它委托给db:migrate_db1db:migrate_db2

    每个都建立与数据库的连接,然后从各自的单独文件夹运行迁移。这允许您将迁移存储在单独的文件夹中,以便您轻松管理它们。

    您的迁移与正常情况完全相同。

    数据库连接

    为了让这些迁移工作,我们需要配置数据库连接。我们将像往常一样定义 database.yml 中的所有内容,但使用不同的命名约定:

    db1:
      development:
        adapter: mysql2
        database: db1_dev
        username: root
    
      test:
        adapter: mysql2
        database: db1_test
        username: root
    
      production:
        adapter: mysql2
        database: db1_prod
        username: root
    
    
    db2:
      development:
        adapter: mysql2
        database: db2_dev
        username: root
    
      test:
        adapter: mysql2
        database: db2_test
        username: root
    
      production:
        adapter: mysql2
        database: db2_prod
        username: root
    

    这里我们配置了两个独立的数据库db1db2

    我们现在需要配置我们的应用来加载这些。我通常在 boot.rb 中执行此操作,但如果您使用的是 Rails,则可能会在您的 application.rb 或环境文件中。

    ENV['ENV'] ||= 'development'
    
      db_conf = YAML::load(File.open(File.join(APP_PATH,'config','database.yml')))
    
      DB1_CONF = db_conf["db1"][ENV['ENV']]
      DB2_CONF = db_conf["db2"][ENV['ENV']]
    

    那么在这里,让我们来看看发生了什么:

    1. 我们设置要使用的数据库配置。 Rails 用户可以在这里使用 Rails.env 而不是 ENV['ENV']
    2. 其次,我们加载 database.yml 配置并使用 YAML 解析它
    3. 最后,我们从文件中获取每个数据库的配置以及我们正在运行的正确环境。

    连接您的模型

    当您使用多个数据库时,我喜欢在模型内部显式设置连接,而不是从 ActiveRecord::Base 继承并使用子类。

    class Message < ActiveRecord::Base
      establish_connection DB1_CONF
    end
    

    我们在另一个数据库中的第二个模型:

    class User < ActiveRecord::Base
      establish_connection DB2_CONF
    end
    

    结论

    就这么简单。您真正需要做的就是加载配置,正确建立数据库连接,并将迁移设置为从每个数据库的特定文件夹加载。

    我确信有更好的方法来处理这个问题,所以如果您有任何建议,请在 cmets 中告诉我!

    【讨论】:

    • 谢谢,好东西,虽然我得到了一个ActiveRecord::AdapterNotSpecified 异常,由activerecord (4.2.0) lib/active_record/connection_adapters/connection_specification.rb:248:in resolve_symbol_connection'`引起
    • 源丢失:excid3.com/blog/… 有人遇到了同样的问题:excid3.com/blog/…
    • @sriharisairamVentrapragada 通常在您的Rakefile 中,位于项目根目录中。
    猜你喜欢
    • 1970-01-01
    • 2013-02-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-02-28
    • 1970-01-01
    相关资源
    最近更新 更多