Module: Activerecord::Mysql::Reconnect
- Defined in:
- lib/activerecord/mysql/reconnect/version.rb,
lib/activerecord/mysql/reconnect.rb
Constant Summary collapse
- VERSION =
'0.3.2'- DEFAULT_EXECUTION_TRIES =
3- DEFAULT_EXECUTION_RETRY_WAIT =
0.5
- WITHOUT_RETRY_KEY =
'activerecord-mysql-reconnect-without-retry'- RETRYABLE_TRANSACTION_KEY =
'activerecord-mysql-reconnect-transaction-retry'- HANDLE_ERROR =
[ ActiveRecord::StatementInvalid, Mysql2::Error, ]
- HANDLE_R_ERROR_MESSAGES =
[ 'Lost connection to MySQL server during query', ]
- HANDLE_RW_ERROR_MESSAGES =
[ 'MySQL server has gone away', 'Server shutdown in progress', 'closed MySQL connection', "Can't connect to MySQL server", 'Query execution was interrupted', 'Access denied for user', 'The MySQL server is running with the --read-only option', ]
- HANDLE_ERROR_MESSAGES =
HANDLE_R_ERROR_MESSAGES + HANDLE_RW_ERROR_MESSAGES
- READ_SQL_REGEXP =
/\A\s*(?:SELECT|SHOW|SET)\b/i- RETRY_MODES =
[:r, :rw, :force]
- DEFAULT_RETRY_MODE =
:r
Class Method Summary collapse
- .enable_retry ⇒ Object
- .execution_retry_wait ⇒ Object
- .execution_tries ⇒ Object
- .logger ⇒ Object
- .retry_mode ⇒ Object
- .retry_mode=(v) ⇒ Object
- .retryable(opts) ⇒ Object
- .retryable_transaction ⇒ Object
- .retryable_transaction_buffer ⇒ Object
- .without_retry ⇒ Object
- .without_retry? ⇒ Boolean
Class Method Details
.enable_retry ⇒ Object
62 63 64 |
# File 'lib/activerecord/mysql/reconnect.rb', line 62 def enable_retry !!ActiveRecord::Base.enable_retry end |
.execution_retry_wait ⇒ Object
58 59 60 |
# File 'lib/activerecord/mysql/reconnect.rb', line 58 def execution_retry_wait ActiveRecord::Base.execution_retry_wait || DEFAULT_EXECUTION_RETRY_WAIT end |
.execution_tries ⇒ Object
54 55 56 |
# File 'lib/activerecord/mysql/reconnect.rb', line 54 def execution_tries ActiveRecord::Base.execution_tries || DEFAULT_EXECUTION_TRIES end |
.logger ⇒ Object
112 113 114 115 116 117 118 |
# File 'lib/activerecord/mysql/reconnect.rb', line 112 def logger if defined?(Rails) Rails.logger || ActiveRecord::Base.logger || Logger.new($stderr) else ActiveRecord::Base.logger || Logger.new($stderr) end end |
.retry_mode ⇒ Object
74 75 76 |
# File 'lib/activerecord/mysql/reconnect.rb', line 74 def retry_mode @activerecord_mysql_reconnect_retry_mode || DEFAULT_RETRY_MODE end |
.retry_mode=(v) ⇒ Object
66 67 68 69 70 71 72 |
# File 'lib/activerecord/mysql/reconnect.rb', line 66 def retry_mode=(v) unless RETRY_MODES.include?(v) raise "Invalid retry_mode. Please set one of the following: #{RETRY_MODES.map {|i| i.inspect }.join(', ')}" end @activerecord_mysql_reconnect_retry_mode = v end |
.retryable(opts) ⇒ Object
78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 |
# File 'lib/activerecord/mysql/reconnect.rb', line 78 def retryable(opts) block = opts.fetch(:proc) on_error = opts[:on_error] conn = opts[:connection] tries = self.execution_tries retval = nil retryable_loop(tries) do |n| begin retval = block.call break rescue => e if enable_retry and (tries.zero? or n < tries) and should_handle?(e, opts) on_error.call if on_error wait = self.execution_retry_wait * n opt_msgs = ["cause: #{e} [#{e.class}]"] if conn and conn.kind_of?(Mysql2::Client) opt_msgs << 'connection: ' + [:host, :database, :username].map {|k| "#{k}=#{conn.query_options[k]}" }.join(";") end logger.warn("MySQL server has gone away. Trying to reconnect in #{wait} seconds. (#{opt_msgs.join(', ')})") sleep(wait) next else raise e end end end return retval end |
.retryable_transaction ⇒ Object
133 134 135 136 137 138 139 140 141 142 143 |
# File 'lib/activerecord/mysql/reconnect.rb', line 133 def retryable_transaction begin Thread.current[RETRYABLE_TRANSACTION_KEY] = [] ActiveRecord::Base.transaction do yield end ensure Thread.current[RETRYABLE_TRANSACTION_KEY] = nil end end |
.retryable_transaction_buffer ⇒ Object
145 146 147 |
# File 'lib/activerecord/mysql/reconnect.rb', line 145 def retryable_transaction_buffer Thread.current[RETRYABLE_TRANSACTION_KEY] end |
.without_retry ⇒ Object
120 121 122 123 124 125 126 127 |
# File 'lib/activerecord/mysql/reconnect.rb', line 120 def without_retry begin Thread.current[WITHOUT_RETRY_KEY] = true yield ensure Thread.current[WITHOUT_RETRY_KEY] = nil end end |
.without_retry? ⇒ Boolean
129 130 131 |
# File 'lib/activerecord/mysql/reconnect.rb', line 129 def without_retry? !!Thread.current[WITHOUT_RETRY_KEY] end |