Rails 中的多个数据库连接
我正在 Rails 中编写 phpMyAdmin 的更简单版本;该 Web 应用程序将在 Web 服务器上运行(用户将能够指示同一网络上运行的数据库服务器之一的数据库名称、主机名、用户名、密码和端口号)。然后,用户将连接到该计算机,并能够使用 UI 来管理该数据库(添加或删除列、删除表等)。
我有两个相关的问题(您的帮助将极大地帮助我理解如何最好地解决这个问题):
在传统的 Rails 应用程序中,我会将数据库信息存储在 database.yml 中,但是在这里我需要动态地执行此操作。有没有一种好方法可以将database.yml 文件留空并告诉Rails 使用用户在运行时提供的连接数据?
不同的用户可能连接到不同的数据库(甚至主机)。我假设我需要跟踪已建立的数据库连接和用户会话之间的关联。实现此目的的最佳方法是什么?
先感谢您。
I'm writing a simpler version of phpMyAdmin in Rails; this web app will run on a web server (where users will be able to indicate the database name, hostname, username, password, and port number of one of the database servers running on the same network). The user will then be connected to that machine and will be able to use the UI to administer that database (add or remove columns, drop tables, etc).
I have two related questions (your help will greatly aid me in understanding how to best approach this):
In a traditional Rails application I would store the database info in database.yml, however here I need to do it dynamically. Is there a good way to leave the database.yml file empty and tell Rails to use the connection data provided by the user at run time instead?
Different users may connect to different databases (or even hosts). I assume that I need to keep track of the association between an established database connection and a user session. What's the best way to achieve this?
Thank you in advance.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
要防止Rails使用database.yml初始化ActiveRecord,您只需从config/environment.rb中的
config.frameworks
中删除:active_record
即可。然后,要手动建立连接,请使用ActiveRecord::Base.built_connection
。 (也许ActiveRecord::Base.configurations
)ActiveRecord 将所有与连接相关的内容存储在类变量中。因此,如果您想动态创建多个连接,您还必须动态子类化 ActiveRecord::Base 并对其调用建立连接。
这将是您将用于实际管理表的任何子类的抽象基类。为了让 ActiveRecord 意识到这一点,您应该在基类定义中执行
self.abstract_class = true
操作。然后,您想要管理的每个表将依次动态地子类化这个新的抽象基类。
这更困难,因为当然你无法真正保持连接。我能想到的直接解决方案是在会话中存储一个唯一的令牌,并在 before_filter 中使用它来返回动态 ActiveRecord::Base 子类,您可能会将其存储在某个哈希中。
一旦你开始运行多个 Rails 工作进程,这就会变得更有趣:
To prevent Rails from initializing ActiveRecord using database.yml, you can simply remove
:active_record
fromconfig.frameworks
in config/environment.rb. Then, to manually establish connections, you useActiveRecord::Base.establish_connection
. (And maybeActiveRecord::Base.configurations
)ActiveRecord stores everything connection related in class variables. So if you want to dynamically create multiple connections, you also have to dynamically subclass ActiveRecord::Base and call establish_connection on that.
This will be your abstract base class for any subclass you'll use to actually manage tables. To make ActiveRecord aware of this, you should do
self.abstract_class = true
within the base class definition.Then, each table you want to manage will in turn dynamically subclass this new abstract base class.
This is more difficult, because you can't really persist connections, of course. The immediate solution I can think of is storing a unique token in the session, and use that in a before_filter to get back to the dynamic ActiveRecord::Base subclass, which you'll probably be storing in a hash somewhere.
This gets more interesting once you start running multiple Rails worker processes: