如何从Rails调用MySQL存储过程?

ohh*_*hho 6 mysql stored-procedures ruby-on-rails

MySQL中的一个简单存储过程:

CREATE PROCEDURE `proc01`()
BEGIN
 SELECT * FROM users;
END
Run Code Online (Sandbox Code Playgroud)

启动Rails控制台:

$ script/console
Loading development environment (Rails 2.3.5)
>> User.connection.execute("CALL proc01")
=> #<Mysql::Result:0x10343efa0>
Run Code Online (Sandbox Code Playgroud)

看起来不错.但是,通过现有连接再次调用同一存储过程将导致命令不同步错误:

>> User.connection.execute("CALL proc01")
ActiveRecord::StatementInvalid: Mysql::Error: Commands out of sync; you can't run this command now: CALL proc01
    from /Library/Ruby/Gems/1.8/gems/activerecord-2.3.5/lib/active_record/connection_adapters/abstract_adapter.rb:219:in `log'
    from /Library/Ruby/Gems/1.8/gems/activerecord-2.3.5/lib/active_record/connection_adapters/mysql_adapter.rb:323:in `execute'
    from (irb):2
Run Code Online (Sandbox Code Playgroud)

可以通过"重新加载"清除错误!控制台中的命令:

>> reload!
Reloading...
=> true
>> User.connection.execute("CALL proc01")
=> #<Mysql::Result:0x1033f14d0>
>> 
Run Code Online (Sandbox Code Playgroud)

如何从Rails调用MySQL存储过程?

Top*_*her 5

编辑:

-

使用ActiveRecord::Base.connections.exec_query()是据我可以告诉MUCH更好的办法,只是因为它返回哈希数组作为人们所期望的,这ActiveRecord::Base.connections.execute没有.

文档

-

请阅读上面的编辑,我将离开以下作为参考.

虽然我意识到这个问题已经很老了,并且发布的链接ohho有404'd,但我最近也遇到了同样的错误.

我能够通过执行以下操作来修复它:

result = ActiveRecord::Base.connection.execute("call example_proc()") ActiveRecord::Base.clear_active_connections!

一旦清除了连接,就可以运行任何其他查询,就像之前尝试通过rails或其他存储过程访问数据库一样失败.

http://apidock.com/rails/v3.2.13/ActiveRecord/Base/clear_active_connections%21/class

- 编辑:

还值得一提的是,根据leente在此链接上的帖子,不应将ActiveRecord连接存储在变量中

"不要缓存它!

不要在变量中存储连接,因为当另一个线程已经重新连接到连接池时,它可能会尝试使用它.请参阅:ConnectionPool "

connection = ActiveRecord::Base.connection   #WRONG

threads = (1..100).map do
 Thread.new do
begin
  10.times do
    connection.execute("SELECT SLEEP(1)")  # WRONG
    ActiveRecord::Base.connection.execute("SELECT SLEEP(1)")  # CORRECT
  end
  puts "success"
rescue => e
  puts e.message
   end
  end
end

threads.each(&:join) 
Run Code Online (Sandbox Code Playgroud)