2009-08-04 7 views
41

Je dois utiliser différentes connexions de base de données dans différents modèles Rails. Y a-t-il une manière pas si hacky de faire cela?Comment puis-je travailler avec deux bases de données différentes dans des rails avec des enregistrements actifs?

Tous les liens ou les mots clés de recherche serait génial :)

+0

Voulez-vous dire que différents champs d'un même modèle proviennent en réalité de différentes bases de Est-ce que les différents modèles de l'application proviennent de différentes bases de données? – mikej

+0

différents modèles de différents serveurs de base de données – gustavgans

+0

@gustavgans - J'ai édité votre question pour la rendre un peu plus claire, d'après votre réponse à 'mikej'. –

Répondre

9

mikej est juste. J'ai cependant écrit une gemme qui rend le code du modèle pour se connecter un peu plus propre, check it out.

+0

Le lien ci-dessus est cassé. Voici la bonne: http://github.com/cherring/connection_ninja – abeger

+1

@railsninja Merci. Vous savez comment exécuter des migrations dans deux bases de données. – maxiperez

112

Ajouter de nouvelles sections à votre database.yml par exemple

other_development: 
    adapter: mysql 
    database: otherdb_development 
    username: root 
    password: 
    host: localhost 

other_production: 
    adapter: mysql 
    database: otherdb_production 
    username: root 
    password: 
    host: localhost 

Ajouter une classe dans lib/other_database.rb

class OtherDatabase < ActiveRecord::Base 
    establish_connection "other_#{RAILS_ENV}" 
end 

et pour chaque modèle qui est pas dans la sous-classe de base de données par défaut de OtherDatabase .: par exemple

class MyModel < OtherDatabase 
    # my model code... 
end 
+4

J'avais besoin d'ajouter 'self.abstract_class = true' dans' lib/other_database.rb' – ybart

12

J'ai utilisé ce qui suit pour se connecter à 2 db dans la même application. Je les mets dans le dossier lib car tout y est chargé.

require 'active_record' 

class OldDatabase < ActiveRecord::Base 
    self.abstract_class = true 
    establish_connection(
    :adapter => 'mysql', 
    :database => 'weather', 
    :host  => 'localhost', 
    :username => 'root', 
    :password => 'password' 
) 
end 

class NewDatabase < ActiveRecord::Base 
    self.abstract_class = true 
    establish_connection(
    :adapter => 'mysql', 
    :database => 'redmine', 
    :host  => 'localhost', 
    :username => 'root', 
    :password => 'password' 
) 
end 

class WeatherData < OldDatabase 
end 

class Board < NewDatabase 
end 

espoir qui aide

+0

J'avais besoin de migrer des données d'une ancienne application vers une nouvelle application dans une tâche Rake, et j'ai utilisé une approche similaire. La différence était que, parce que les tâches Rake utilisent ': task_name =>: environment', l'environnement Rails est disponible, donc le modèle dans la nouvelle application peut juste être utilisé normalement et extrait de database.yml. Seul le modèle de l'ancienne application doit avoir ses informations définies comme vous le montrez. –

9

Mise à jour 3.x Rails:

class MyModel < ActiveRecord::Base 
    establish_connection "other_#{Rails.env}" 
end 
0

dans des rails 4.1+ establish_connection prend maintenant un symbole:

class OtherDbModel < ActiveRecord::Base 
    establish_connection :"other_#{Rails.env}" 
end 
1

Je pense que la plus jolie façon de se connecter à une autre base de données avec le modèle actif est la création de la classe de base pour la base de données externe, puis hériter de cette base dans votre modèle. Cette méthode fonctionne très bien avec des rails 4.2.6 et 5.0.4

Par exemple:

# in /models/external_db/base.rb 
require 'active_record' 

class ExternalDb::Base < ActiveRecord::Base 
    self.abstract_class = true 
    establish_connection "external_db_#{Rails.env}".to_sym 
end 

Et dans votre classe modèle:

# in /models/external_db/some_model.rb 
class ExternalDB::SomeModel < ExternalDb::Base 
    # your code 
end 

Mais vous devez définir la base de données externe/config /database.yml

# in /config/database.yml 
external_db_development: 
    adapter: sqlite3 
    pool: 5 
    timeout: 5000 
    database: db/external_db_development.db 

external_db_production: 
    adapter: sqlite3 
    pool: 5 
    timeout: 5000 
    database: db/external_db_production.db 
Questions connexes