mysql2 0.3.21-x86-mingw32 → 0.4.0-x86-mingw32
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
 - data/CHANGELOG.md +1 -0
 - data/README.md +28 -6
 - data/examples/threaded.rb +4 -6
 - data/ext/mysql2/client.c +54 -46
 - data/ext/mysql2/client.h +21 -0
 - data/ext/mysql2/extconf.rb +20 -23
 - data/ext/mysql2/mysql2_ext.c +1 -0
 - data/ext/mysql2/mysql2_ext.h +1 -0
 - data/ext/mysql2/mysql_enc_name_to_ruby.h +6 -6
 - data/ext/mysql2/result.c +473 -94
 - data/ext/mysql2/result.h +8 -1
 - data/ext/mysql2/statement.c +454 -0
 - data/ext/mysql2/statement.h +22 -0
 - data/lib/mysql2.rb +2 -18
 - data/lib/mysql2/1.8/mysql2.so +0 -0
 - data/lib/mysql2/1.9/mysql2.so +0 -0
 - data/lib/mysql2/2.0/mysql2.so +0 -0
 - data/lib/mysql2/2.1/mysql2.so +0 -0
 - data/lib/mysql2/2.2/mysql2.so +0 -0
 - data/lib/mysql2/client.rb +9 -2
 - data/lib/mysql2/error.rb +8 -20
 - data/lib/mysql2/field.rb +4 -0
 - data/lib/mysql2/statement.rb +5 -0
 - data/lib/mysql2/version.rb +1 -1
 - data/spec/em/em_spec.rb +13 -13
 - data/spec/mysql2/client_spec.rb +284 -277
 - data/spec/mysql2/error_spec.rb +37 -36
 - data/spec/mysql2/result_spec.rb +184 -193
 - data/spec/mysql2/statement_spec.rb +598 -0
 - data/spec/spec_helper.rb +7 -0
 - metadata +15 -48
 - data/lib/mysql2/2.3/mysql2.so +0 -0
 
| 
         @@ -0,0 +1,22 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            #ifndef MYSQL2_STATEMENT_H
         
     | 
| 
      
 2 
     | 
    
         
            +
            #define MYSQL2_STATEMENT_H
         
     | 
| 
      
 3 
     | 
    
         
            +
             
     | 
| 
      
 4 
     | 
    
         
            +
            extern VALUE cMysql2Statement;
         
     | 
| 
      
 5 
     | 
    
         
            +
             
     | 
| 
      
 6 
     | 
    
         
            +
            typedef struct {
         
     | 
| 
      
 7 
     | 
    
         
            +
              VALUE client;
         
     | 
| 
      
 8 
     | 
    
         
            +
              MYSQL_STMT *stmt;
         
     | 
| 
      
 9 
     | 
    
         
            +
              int refcount;
         
     | 
| 
      
 10 
     | 
    
         
            +
            } mysql_stmt_wrapper;
         
     | 
| 
      
 11 
     | 
    
         
            +
             
     | 
| 
      
 12 
     | 
    
         
            +
            void init_mysql2_statement();
         
     | 
| 
      
 13 
     | 
    
         
            +
            void decr_mysql2_stmt(mysql_stmt_wrapper *stmt_wrapper);
         
     | 
| 
      
 14 
     | 
    
         
            +
             
     | 
| 
      
 15 
     | 
    
         
            +
            VALUE rb_mysql_stmt_new(VALUE rb_client, VALUE sql);
         
     | 
| 
      
 16 
     | 
    
         
            +
            VALUE rb_raise_mysql2_stmt_error2(MYSQL_STMT *stmt
         
     | 
| 
      
 17 
     | 
    
         
            +
            #ifdef HAVE_RUBY_ENCODING_H
         
     | 
| 
      
 18 
     | 
    
         
            +
              , rb_encoding* conn_enc
         
     | 
| 
      
 19 
     | 
    
         
            +
            #endif
         
     | 
| 
      
 20 
     | 
    
         
            +
              );
         
     | 
| 
      
 21 
     | 
    
         
            +
             
     | 
| 
      
 22 
     | 
    
         
            +
            #endif
         
     | 
    
        data/lib/mysql2.rb
    CHANGED
    
    | 
         @@ -31,6 +31,8 @@ require 'mysql2/error' 
     | 
|
| 
       31 
31 
     | 
    
         
             
            require 'mysql2/mysql2'
         
     | 
| 
       32 
32 
     | 
    
         
             
            require 'mysql2/result'
         
     | 
| 
       33 
33 
     | 
    
         
             
            require 'mysql2/client'
         
     | 
| 
      
 34 
     | 
    
         
            +
            require 'mysql2/field'
         
     | 
| 
      
 35 
     | 
    
         
            +
            require 'mysql2/statement'
         
     | 
| 
       34 
36 
     | 
    
         | 
| 
       35 
37 
     | 
    
         
             
            # = Mysql2
         
     | 
| 
       36 
38 
     | 
    
         
             
            #
         
     | 
| 
         @@ -61,22 +63,4 @@ module Mysql2::Util 
     | 
|
| 
       61 
63 
     | 
    
         
             
                Hash[hash.map { |k,v| [k.to_sym, v] }]
         
     | 
| 
       62 
64 
     | 
    
         
             
              end
         
     | 
| 
       63 
65 
     | 
    
         | 
| 
       64 
     | 
    
         
            -
              #
         
     | 
| 
       65 
     | 
    
         
            -
              # In Mysql2::Client#query and Mysql2::Statement#execute,
         
     | 
| 
       66 
     | 
    
         
            -
              # Thread#handle_interrupt is used to prevent Timeout#timeout
         
     | 
| 
       67 
     | 
    
         
            -
              # from interrupting query execution.
         
     | 
| 
       68 
     | 
    
         
            -
              #
         
     | 
| 
       69 
     | 
    
         
            -
              # Timeout::ExitException was removed in Ruby 2.3.0, 2.2.3, and 2.1.8,
         
     | 
| 
       70 
     | 
    
         
            -
              # but is present in earlier 2.1.x and 2.2.x, so we provide a shim.
         
     | 
| 
       71 
     | 
    
         
            -
              #
         
     | 
| 
       72 
     | 
    
         
            -
              if Thread.respond_to?(:handle_interrupt)
         
     | 
| 
       73 
     | 
    
         
            -
                require 'timeout'
         
     | 
| 
       74 
     | 
    
         
            -
                # rubocop:disable Style/ConstantName
         
     | 
| 
       75 
     | 
    
         
            -
                TimeoutError = if defined?(::Timeout::ExitException)
         
     | 
| 
       76 
     | 
    
         
            -
                  ::Timeout::ExitException
         
     | 
| 
       77 
     | 
    
         
            -
                else
         
     | 
| 
       78 
     | 
    
         
            -
                  ::Timeout::Error
         
     | 
| 
       79 
     | 
    
         
            -
                end
         
     | 
| 
       80 
     | 
    
         
            -
              end
         
     | 
| 
       81 
     | 
    
         
            -
             
     | 
| 
       82 
66 
     | 
    
         
             
            end
         
     | 
    
        data/lib/mysql2/1.8/mysql2.so
    CHANGED
    
    | 
         Binary file 
     | 
    
        data/lib/mysql2/1.9/mysql2.so
    CHANGED
    
    | 
         Binary file 
     | 
    
        data/lib/mysql2/2.0/mysql2.so
    CHANGED
    
    | 
         Binary file 
     | 
    
        data/lib/mysql2/2.1/mysql2.so
    CHANGED
    
    | 
         Binary file 
     | 
    
        data/lib/mysql2/2.2/mysql2.so
    CHANGED
    
    | 
         Binary file 
     | 
    
        data/lib/mysql2/client.rb
    CHANGED
    
    | 
         @@ -44,6 +44,12 @@ module Mysql2 
     | 
|
| 
       44 
44 
     | 
    
         
             
                  ssl_options = opts.values_at(:sslkey, :sslcert, :sslca, :sslcapath, :sslcipher)
         
     | 
| 
       45 
45 
     | 
    
         
             
                  ssl_set(*ssl_options) if ssl_options.any?
         
     | 
| 
       46 
46 
     | 
    
         | 
| 
      
 47 
     | 
    
         
            +
                  # SSL verify is a connection flag rather than a mysql_ssl_set option
         
     | 
| 
      
 48 
     | 
    
         
            +
                  flags = 0
         
     | 
| 
      
 49 
     | 
    
         
            +
                  flags |= @query_options[:connect_flags]
         
     | 
| 
      
 50 
     | 
    
         
            +
                  flags |= opts[:flags] if opts[:flags]
         
     | 
| 
      
 51 
     | 
    
         
            +
                  flags |= SSL_VERIFY_SERVER_CERT if opts[:sslverify] and ssl_options.any?
         
     | 
| 
      
 52 
     | 
    
         
            +
             
     | 
| 
       47 
53 
     | 
    
         
             
                  if [:user,:pass,:hostname,:dbname,:db,:sock].any?{|k| @query_options.has_key?(k) }
         
     | 
| 
       48 
54 
     | 
    
         
             
                    warn "============= WARNING FROM mysql2 ============="
         
     | 
| 
       49 
55 
     | 
    
         
             
                    warn "The options :user, :pass, :hostname, :dbname, :db, and :sock will be deprecated at some point in the future."
         
     | 
| 
         @@ -57,7 +63,6 @@ module Mysql2 
     | 
|
| 
       57 
63 
     | 
    
         
             
                  port     = opts[:port]
         
     | 
| 
       58 
64 
     | 
    
         
             
                  database = opts[:database] || opts[:dbname] || opts[:db]
         
     | 
| 
       59 
65 
     | 
    
         
             
                  socket   = opts[:socket] || opts[:sock]
         
     | 
| 
       60 
     | 
    
         
            -
                  flags    = opts[:flags] ? opts[:flags] | @query_options[:connect_flags] : @query_options[:connect_flags]
         
     | 
| 
       61 
66 
     | 
    
         | 
| 
       62 
67 
     | 
    
         
             
                  # Correct the data types before passing these values down to the C level
         
     | 
| 
       63 
68 
     | 
    
         
             
                  user = user.to_s unless user.nil?
         
     | 
| 
         @@ -75,8 +80,10 @@ module Mysql2 
     | 
|
| 
       75 
80 
     | 
    
         
             
                end
         
     | 
| 
       76 
81 
     | 
    
         | 
| 
       77 
82 
     | 
    
         
             
                if Thread.respond_to?(:handle_interrupt)
         
     | 
| 
      
 83 
     | 
    
         
            +
                  require 'timeout'
         
     | 
| 
      
 84 
     | 
    
         
            +
             
     | 
| 
       78 
85 
     | 
    
         
             
                  def query(sql, options = {})
         
     | 
| 
       79 
     | 
    
         
            -
                    Thread.handle_interrupt(:: 
     | 
| 
      
 86 
     | 
    
         
            +
                    Thread.handle_interrupt(::Timeout::ExitException => :never) do
         
     | 
| 
       80 
87 
     | 
    
         
             
                      _query(sql, @query_options.merge(options))
         
     | 
| 
       81 
88 
     | 
    
         
             
                    end
         
     | 
| 
       82 
89 
     | 
    
         
             
                  end
         
     | 
    
        data/lib/mysql2/error.rb
    CHANGED
    
    | 
         @@ -2,8 +2,11 @@ 
     | 
|
| 
       2 
2 
     | 
    
         | 
| 
       3 
3 
     | 
    
         
             
            module Mysql2
         
     | 
| 
       4 
4 
     | 
    
         
             
              class Error < StandardError
         
     | 
| 
       5 
     | 
    
         
            -
                 
     | 
| 
       6 
     | 
    
         
            -
             
     | 
| 
      
 5 
     | 
    
         
            +
                ENCODE_OPTS = {
         
     | 
| 
      
 6 
     | 
    
         
            +
                  :undef => :replace,
         
     | 
| 
      
 7 
     | 
    
         
            +
                  :invalid => :replace,
         
     | 
| 
      
 8 
     | 
    
         
            +
                  :replace => '?'.freeze,
         
     | 
| 
      
 9 
     | 
    
         
            +
                }.freeze
         
     | 
| 
       7 
10 
     | 
    
         | 
| 
       8 
11 
     | 
    
         
             
                attr_accessor :error_number
         
     | 
| 
       9 
12 
     | 
    
         
             
                attr_reader   :sql_state
         
     | 
| 
         @@ -20,7 +23,7 @@ module Mysql2 
     | 
|
| 
       20 
23 
     | 
    
         
             
                end
         
     | 
| 
       21 
24 
     | 
    
         | 
| 
       22 
25 
     | 
    
         
             
                def sql_state=(state)
         
     | 
| 
       23 
     | 
    
         
            -
                  @sql_state =  
     | 
| 
      
 26 
     | 
    
         
            +
                  @sql_state = state.respond_to?(:encode) ? state.encode(ENCODE_OPTS) : state
         
     | 
| 
       24 
27 
     | 
    
         
             
                end
         
     | 
| 
       25 
28 
     | 
    
         | 
| 
       26 
29 
     | 
    
         
             
                private
         
     | 
| 
         @@ -53,27 +56,12 @@ module Mysql2 
     | 
|
| 
       53 
56 
     | 
    
         
             
                #
         
     | 
| 
       54 
57 
     | 
    
         
             
                # Returns a valid UTF-8 string in Ruby 1.9+, the original string on Ruby 1.8
         
     | 
| 
       55 
58 
     | 
    
         
             
                def clean_message(message)
         
     | 
| 
       56 
     | 
    
         
            -
                  return message  
     | 
| 
      
 59 
     | 
    
         
            +
                  return message unless message.respond_to?(:encode)
         
     | 
| 
       57 
60 
     | 
    
         | 
| 
       58 
61 
     | 
    
         
             
                  if @server_version && @server_version > 50500
         
     | 
| 
       59 
62 
     | 
    
         
             
                    message.encode(ENCODE_OPTS)
         
     | 
| 
       60 
63 
     | 
    
         
             
                  else
         
     | 
| 
       61 
     | 
    
         
            -
                     
     | 
| 
       62 
     | 
    
         
            -
                      message.scrub(REPLACEMENT_CHAR).encode(ENCODE_OPTS)
         
     | 
| 
       63 
     | 
    
         
            -
                    else
         
     | 
| 
       64 
     | 
    
         
            -
                      # This is ugly as hell but Ruby 1.9 doesn't provide a way to clean a string
         
     | 
| 
       65 
     | 
    
         
            -
                      # and retain it's valid UTF-8 characters, that I know of.
         
     | 
| 
       66 
     | 
    
         
            -
             
     | 
| 
       67 
     | 
    
         
            -
                      new_message = "".force_encoding(Encoding::UTF_8)
         
     | 
| 
       68 
     | 
    
         
            -
                      message.chars.each do |char|
         
     | 
| 
       69 
     | 
    
         
            -
                        if char.valid_encoding?
         
     | 
| 
       70 
     | 
    
         
            -
                          new_message << char
         
     | 
| 
       71 
     | 
    
         
            -
                        else
         
     | 
| 
       72 
     | 
    
         
            -
                          new_message << REPLACEMENT_CHAR
         
     | 
| 
       73 
     | 
    
         
            -
                        end
         
     | 
| 
       74 
     | 
    
         
            -
                      end
         
     | 
| 
       75 
     | 
    
         
            -
                      new_message.encode(ENCODE_OPTS)
         
     | 
| 
       76 
     | 
    
         
            -
                    end
         
     | 
| 
      
 64 
     | 
    
         
            +
                    message.encode(Encoding::UTF_8, ENCODE_OPTS)
         
     | 
| 
       77 
65 
     | 
    
         
             
                  end
         
     | 
| 
       78 
66 
     | 
    
         
             
                end
         
     | 
| 
       79 
67 
     | 
    
         
             
              end
         
     | 
    
        data/lib/mysql2/field.rb
    ADDED
    
    
    
        data/lib/mysql2/version.rb
    CHANGED
    
    
    
        data/spec/em/em_spec.rb
    CHANGED
    
    | 
         @@ -4,7 +4,7 @@ begin 
     | 
|
| 
       4 
4 
     | 
    
         
             
              require 'eventmachine'
         
     | 
| 
       5 
5 
     | 
    
         
             
              require 'mysql2/em'
         
     | 
| 
       6 
6 
     | 
    
         | 
| 
       7 
     | 
    
         
            -
              describe Mysql2::EM::Client do
         
     | 
| 
      
 7 
     | 
    
         
            +
              RSpec.describe Mysql2::EM::Client do
         
     | 
| 
       8 
8 
     | 
    
         
             
                it "should support async queries" do
         
     | 
| 
       9 
9 
     | 
    
         
             
                  results = []
         
     | 
| 
       10 
10 
     | 
    
         
             
                  EM.run do
         
     | 
| 
         @@ -24,8 +24,8 @@ begin 
     | 
|
| 
       24 
24 
     | 
    
         
             
                    end
         
     | 
| 
       25 
25 
     | 
    
         
             
                  end
         
     | 
| 
       26 
26 
     | 
    
         | 
| 
       27 
     | 
    
         
            -
                  results[0].keys. 
     | 
| 
       28 
     | 
    
         
            -
                  results[1].keys. 
     | 
| 
      
 27 
     | 
    
         
            +
                  expect(results[0].keys).to include("second_query")
         
     | 
| 
      
 28 
     | 
    
         
            +
                  expect(results[1].keys).to include("first_query")
         
     | 
| 
       29 
29 
     | 
    
         
             
                end
         
     | 
| 
       30 
30 
     | 
    
         | 
| 
       31 
31 
     | 
    
         
             
                it "should support queries in callbacks" do
         
     | 
| 
         @@ -44,12 +44,12 @@ begin 
     | 
|
| 
       44 
44 
     | 
    
         
             
                    end
         
     | 
| 
       45 
45 
     | 
    
         
             
                  end
         
     | 
| 
       46 
46 
     | 
    
         | 
| 
       47 
     | 
    
         
            -
                  results[0].keys. 
     | 
| 
       48 
     | 
    
         
            -
                  results[1].keys. 
     | 
| 
      
 47 
     | 
    
         
            +
                  expect(results[0].keys).to include("first_query")
         
     | 
| 
      
 48 
     | 
    
         
            +
                  expect(results[1].keys).to include("second_query")
         
     | 
| 
       49 
49 
     | 
    
         
             
                end
         
     | 
| 
       50 
50 
     | 
    
         | 
| 
       51 
51 
     | 
    
         
             
                it "should not swallow exceptions raised in callbacks" do
         
     | 
| 
       52 
     | 
    
         
            -
                   
     | 
| 
      
 52 
     | 
    
         
            +
                  expect {
         
     | 
| 
       53 
53 
     | 
    
         
             
                    EM.run do
         
     | 
| 
       54 
54 
     | 
    
         
             
                      client = Mysql2::EM::Client.new DatabaseCredentials['root']
         
     | 
| 
       55 
55 
     | 
    
         
             
                      defer = client.query "SELECT sleep(0.1) as first_query"
         
     | 
| 
         @@ -63,13 +63,13 @@ begin 
     | 
|
| 
       63 
63 
     | 
    
         
             
                        EM.stop_event_loop
         
     | 
| 
       64 
64 
     | 
    
         
             
                      end
         
     | 
| 
       65 
65 
     | 
    
         
             
                    end
         
     | 
| 
       66 
     | 
    
         
            -
                  }. 
     | 
| 
      
 66 
     | 
    
         
            +
                  }.to raise_error('some error')
         
     | 
| 
       67 
67 
     | 
    
         
             
                end
         
     | 
| 
       68 
68 
     | 
    
         | 
| 
       69 
69 
     | 
    
         
             
                context 'when an exception is raised by the client' do
         
     | 
| 
       70 
70 
     | 
    
         
             
                  let(:client) { Mysql2::EM::Client.new DatabaseCredentials['root'] }
         
     | 
| 
       71 
71 
     | 
    
         
             
                  let(:error) { StandardError.new('some error') }
         
     | 
| 
       72 
     | 
    
         
            -
                  before { client. 
     | 
| 
      
 72 
     | 
    
         
            +
                  before { allow(client).to receive(:async_result).and_raise(error) }
         
     | 
| 
       73 
73 
     | 
    
         | 
| 
       74 
74 
     | 
    
         
             
                  it "should swallow exceptions raised in by the client" do
         
     | 
| 
       75 
75 
     | 
    
         
             
                    errors = []
         
     | 
| 
         @@ -85,7 +85,7 @@ begin 
     | 
|
| 
       85 
85 
     | 
    
         
             
                        EM.stop_event_loop
         
     | 
| 
       86 
86 
     | 
    
         
             
                      end
         
     | 
| 
       87 
87 
     | 
    
         
             
                    end
         
     | 
| 
       88 
     | 
    
         
            -
                    errors. 
     | 
| 
      
 88 
     | 
    
         
            +
                    expect(errors).to eq([error])
         
     | 
| 
       89 
89 
     | 
    
         
             
                  end
         
     | 
| 
       90 
90 
     | 
    
         | 
| 
       91 
91 
     | 
    
         
             
                  it "should fail the deferrable" do
         
     | 
| 
         @@ -105,7 +105,7 @@ begin 
     | 
|
| 
       105 
105 
     | 
    
         
             
                        end
         
     | 
| 
       106 
106 
     | 
    
         
             
                      end
         
     | 
| 
       107 
107 
     | 
    
         
             
                    end
         
     | 
| 
       108 
     | 
    
         
            -
                    callbacks_run. 
     | 
| 
      
 108 
     | 
    
         
            +
                    expect(callbacks_run).to eq([:errback])
         
     | 
| 
       109 
109 
     | 
    
         
             
                  end
         
     | 
| 
       110 
110 
     | 
    
         
             
                end
         
     | 
| 
       111 
111 
     | 
    
         | 
| 
         @@ -121,10 +121,10 @@ begin 
     | 
|
| 
       121 
121 
     | 
    
         
             
                      callbacks_run << :errback
         
     | 
| 
       122 
122 
     | 
    
         
             
                    end
         
     | 
| 
       123 
123 
     | 
    
         
             
                    EM.add_timer(0.1) do
         
     | 
| 
       124 
     | 
    
         
            -
                      callbacks_run. 
     | 
| 
       125 
     | 
    
         
            -
                       
     | 
| 
      
 124 
     | 
    
         
            +
                      expect(callbacks_run).to eq([:callback])
         
     | 
| 
      
 125 
     | 
    
         
            +
                      expect {
         
     | 
| 
       126 
126 
     | 
    
         
             
                        client.close
         
     | 
| 
       127 
     | 
    
         
            -
                      }. 
     | 
| 
      
 127 
     | 
    
         
            +
                      }.not_to raise_error
         
     | 
| 
       128 
128 
     | 
    
         
             
                      EM.stop_event_loop
         
     | 
| 
       129 
129 
     | 
    
         
             
                    end
         
     | 
| 
       130 
130 
     | 
    
         
             
                  end
         
     | 
    
        data/spec/mysql2/client_spec.rb
    CHANGED
    
    | 
         @@ -1,48 +1,46 @@ 
     | 
|
| 
       1 
1 
     | 
    
         
             
            # encoding: UTF-8
         
     | 
| 
       2 
2 
     | 
    
         
             
            require 'spec_helper'
         
     | 
| 
       3 
3 
     | 
    
         | 
| 
       4 
     | 
    
         
            -
            describe Mysql2::Client do
         
     | 
| 
      
 4 
     | 
    
         
            +
            RSpec.describe Mysql2::Client do
         
     | 
| 
       5 
5 
     | 
    
         
             
              context "using defaults file" do
         
     | 
| 
       6 
6 
     | 
    
         
             
                let(:cnf_file) { File.expand_path('../../my.cnf', __FILE__) }
         
     | 
| 
       7 
7 
     | 
    
         | 
| 
       8 
8 
     | 
    
         
             
                it "should not raise an exception for valid defaults group" do
         
     | 
| 
       9 
     | 
    
         
            -
                   
     | 
| 
      
 9 
     | 
    
         
            +
                  expect {
         
     | 
| 
       10 
10 
     | 
    
         
             
                    opts = DatabaseCredentials['root'].merge(:default_file => cnf_file, :default_group => "test")
         
     | 
| 
       11 
11 
     | 
    
         
             
                    @client = Mysql2::Client.new(opts)
         
     | 
| 
       12 
     | 
    
         
            -
                  }. 
     | 
| 
      
 12 
     | 
    
         
            +
                  }.not_to raise_error
         
     | 
| 
       13 
13 
     | 
    
         
             
                end
         
     | 
| 
       14 
14 
     | 
    
         | 
| 
       15 
15 
     | 
    
         
             
                it "should not raise an exception without default group" do
         
     | 
| 
       16 
     | 
    
         
            -
                   
     | 
| 
      
 16 
     | 
    
         
            +
                  expect {
         
     | 
| 
       17 
17 
     | 
    
         
             
                    @client = Mysql2::Client.new(DatabaseCredentials['root'].merge(:default_file => cnf_file))
         
     | 
| 
       18 
     | 
    
         
            -
                  }. 
     | 
| 
      
 18 
     | 
    
         
            +
                  }.not_to raise_error
         
     | 
| 
       19 
19 
     | 
    
         
             
                end
         
     | 
| 
       20 
20 
     | 
    
         
             
              end
         
     | 
| 
       21 
21 
     | 
    
         | 
| 
       22 
22 
     | 
    
         
             
              it "should raise an exception upon connection failure" do
         
     | 
| 
       23 
     | 
    
         
            -
                 
     | 
| 
      
 23 
     | 
    
         
            +
                expect {
         
     | 
| 
       24 
24 
     | 
    
         
             
                  # The odd local host IP address forces the mysql client library to
         
     | 
| 
       25 
25 
     | 
    
         
             
                  # use a TCP socket rather than a domain socket.
         
     | 
| 
       26 
26 
     | 
    
         
             
                  Mysql2::Client.new DatabaseCredentials['root'].merge('host' => '127.0.0.2', 'port' => 999999)
         
     | 
| 
       27 
     | 
    
         
            -
                }. 
     | 
| 
      
 27 
     | 
    
         
            +
                }.to raise_error(Mysql2::Error)
         
     | 
| 
       28 
28 
     | 
    
         
             
              end
         
     | 
| 
       29 
29 
     | 
    
         | 
| 
       30 
     | 
    
         
            -
               
     | 
| 
       31 
     | 
    
         
            -
                 
     | 
| 
       32 
     | 
    
         
            -
                   
     | 
| 
       33 
     | 
    
         
            -
             
     | 
| 
       34 
     | 
    
         
            -
             
     | 
| 
       35 
     | 
    
         
            -
                end
         
     | 
| 
      
 30 
     | 
    
         
            +
              it "should raise an exception on create for invalid encodings" do
         
     | 
| 
      
 31 
     | 
    
         
            +
                expect {
         
     | 
| 
      
 32 
     | 
    
         
            +
                  Mysql2::Client.new(DatabaseCredentials['root'].merge(:encoding => "fake"))
         
     | 
| 
      
 33 
     | 
    
         
            +
                }.to raise_error(Mysql2::Error)
         
     | 
| 
      
 34 
     | 
    
         
            +
              end
         
     | 
| 
       36 
35 
     | 
    
         | 
| 
       37 
     | 
    
         
            -
             
     | 
| 
       38 
     | 
    
         
            -
             
     | 
| 
       39 
     | 
    
         
            -
             
     | 
| 
       40 
     | 
    
         
            -
             
     | 
| 
      
 36 
     | 
    
         
            +
              it "should not raise an exception on create for a valid encoding" do
         
     | 
| 
      
 37 
     | 
    
         
            +
                expect {
         
     | 
| 
      
 38 
     | 
    
         
            +
                  Mysql2::Client.new(DatabaseCredentials['root'].merge(:encoding => "utf8"))
         
     | 
| 
      
 39 
     | 
    
         
            +
                }.not_to raise_error
         
     | 
| 
       41 
40 
     | 
    
         | 
| 
       42 
     | 
    
         
            -
             
     | 
| 
       43 
     | 
    
         
            -
             
     | 
| 
       44 
     | 
    
         
            -
             
     | 
| 
       45 
     | 
    
         
            -
                end
         
     | 
| 
      
 41 
     | 
    
         
            +
                expect {
         
     | 
| 
      
 42 
     | 
    
         
            +
                  Mysql2::Client.new(DatabaseCredentials['root'].merge(:encoding => "big5"))
         
     | 
| 
      
 43 
     | 
    
         
            +
                }.not_to raise_error
         
     | 
| 
       46 
44 
     | 
    
         
             
              end
         
     | 
| 
       47 
45 
     | 
    
         | 
| 
       48 
46 
     | 
    
         
             
              it "should accept connect flags and pass them to #connect" do
         
     | 
| 
         @@ -54,7 +52,7 @@ describe Mysql2::Client do 
     | 
|
| 
       54 
52 
     | 
    
         
             
                  end
         
     | 
| 
       55 
53 
     | 
    
         
             
                end
         
     | 
| 
       56 
54 
     | 
    
         
             
                client = klient.new :flags => Mysql2::Client::FOUND_ROWS
         
     | 
| 
       57 
     | 
    
         
            -
                (client.connect_args.last[6] & Mysql2::Client::FOUND_ROWS). 
     | 
| 
      
 55 
     | 
    
         
            +
                expect(client.connect_args.last[6] & Mysql2::Client::FOUND_ROWS).to be > 0
         
     | 
| 
       58 
56 
     | 
    
         
             
              end
         
     | 
| 
       59 
57 
     | 
    
         | 
| 
       60 
58 
     | 
    
         
             
              it "should default flags to (REMEMBER_OPTIONS, LONG_PASSWORD, LONG_FLAG, TRANSACTIONS, PROTOCOL_41, SECURE_CONNECTION)" do
         
     | 
| 
         @@ -72,7 +70,7 @@ describe Mysql2::Client do 
     | 
|
| 
       72 
70 
     | 
    
         
             
                               Mysql2::Client::TRANSACTIONS |
         
     | 
| 
       73 
71 
     | 
    
         
             
                               Mysql2::Client::PROTOCOL_41 |
         
     | 
| 
       74 
72 
     | 
    
         
             
                               Mysql2::Client::SECURE_CONNECTION
         
     | 
| 
       75 
     | 
    
         
            -
                client.connect_args.last[6]. 
     | 
| 
      
 73 
     | 
    
         
            +
                expect(client.connect_args.last[6]).to eql(client_flags)
         
     | 
| 
       76 
74 
     | 
    
         
             
              end
         
     | 
| 
       77 
75 
     | 
    
         | 
| 
       78 
76 
     | 
    
         
             
              it "should execute init command" do
         
     | 
| 
         @@ -80,7 +78,7 @@ describe Mysql2::Client do 
     | 
|
| 
       80 
78 
     | 
    
         
             
                options[:init_command] = "SET @something = 'setting_value';"
         
     | 
| 
       81 
79 
     | 
    
         
             
                client = Mysql2::Client.new(options)
         
     | 
| 
       82 
80 
     | 
    
         
             
                result = client.query("SELECT @something;")
         
     | 
| 
       83 
     | 
    
         
            -
                result.first['@something']. 
     | 
| 
      
 81 
     | 
    
         
            +
                expect(result.first['@something']).to eq('setting_value')
         
     | 
| 
       84 
82 
     | 
    
         
             
              end
         
     | 
| 
       85 
83 
     | 
    
         | 
| 
       86 
84 
     | 
    
         
             
              it "should send init_command after reconnect" do
         
     | 
| 
         @@ -90,17 +88,14 @@ describe Mysql2::Client do 
     | 
|
| 
       90 
88 
     | 
    
         
             
                client = Mysql2::Client.new(options)
         
     | 
| 
       91 
89 
     | 
    
         | 
| 
       92 
90 
     | 
    
         
             
                result = client.query("SELECT @something;")
         
     | 
| 
       93 
     | 
    
         
            -
                result.first['@something']. 
     | 
| 
      
 91 
     | 
    
         
            +
                expect(result.first['@something']).to eq('setting_value')
         
     | 
| 
       94 
92 
     | 
    
         | 
| 
       95 
93 
     | 
    
         
             
                # get the current connection id
         
     | 
| 
       96 
94 
     | 
    
         
             
                result = client.query("SELECT CONNECTION_ID()")
         
     | 
| 
       97 
95 
     | 
    
         
             
                first_conn_id = result.first['CONNECTION_ID()']
         
     | 
| 
       98 
96 
     | 
    
         | 
| 
       99 
97 
     | 
    
         
             
                # break the current connection
         
     | 
| 
       100 
     | 
    
         
            -
                 
     | 
| 
       101 
     | 
    
         
            -
                  client.query("KILL #{first_conn_id}")
         
     | 
| 
       102 
     | 
    
         
            -
                rescue Mysql2::Error
         
     | 
| 
       103 
     | 
    
         
            -
                end
         
     | 
| 
      
 98 
     | 
    
         
            +
                expect { client.query("KILL #{first_conn_id}") }.to raise_error(Mysql2::Error)
         
     | 
| 
       104 
99 
     | 
    
         | 
| 
       105 
100 
     | 
    
         
             
                client.ping # reconnect now
         
     | 
| 
       106 
101 
     | 
    
         | 
| 
         @@ -109,15 +104,15 @@ describe Mysql2::Client do 
     | 
|
| 
       109 
104 
     | 
    
         
             
                second_conn_id = result.first['CONNECTION_ID()']
         
     | 
| 
       110 
105 
     | 
    
         | 
| 
       111 
106 
     | 
    
         
             
                # confirm reconnect by checking the new connection id
         
     | 
| 
       112 
     | 
    
         
            -
                first_conn_id. 
     | 
| 
      
 107 
     | 
    
         
            +
                expect(first_conn_id).not_to eq(second_conn_id)
         
     | 
| 
       113 
108 
     | 
    
         | 
| 
       114 
109 
     | 
    
         
             
                # At last, check that the init command executed
         
     | 
| 
       115 
110 
     | 
    
         
             
                result = client.query("SELECT @something;")
         
     | 
| 
       116 
     | 
    
         
            -
                result.first['@something']. 
     | 
| 
      
 111 
     | 
    
         
            +
                expect(result.first['@something']).to eq('setting_value')
         
     | 
| 
       117 
112 
     | 
    
         
             
              end
         
     | 
| 
       118 
113 
     | 
    
         | 
| 
       119 
114 
     | 
    
         
             
              it "should have a global default_query_options hash" do
         
     | 
| 
       120 
     | 
    
         
            -
                Mysql2::Client. 
     | 
| 
      
 115 
     | 
    
         
            +
                expect(Mysql2::Client).to respond_to(:default_query_options)
         
     | 
| 
       121 
116 
     | 
    
         
             
              end
         
     | 
| 
       122 
117 
     | 
    
         | 
| 
       123 
118 
     | 
    
         
             
              it "should be able to connect via SSL options" do
         
     | 
| 
         @@ -129,7 +124,7 @@ describe Mysql2::Client do 
     | 
|
| 
       129 
124 
     | 
    
         | 
| 
       130 
125 
     | 
    
         
             
                # You may need to adjust the lines below to match your SSL certificate paths
         
     | 
| 
       131 
126 
     | 
    
         
             
                ssl_client = nil
         
     | 
| 
       132 
     | 
    
         
            -
                 
     | 
| 
      
 127 
     | 
    
         
            +
                expect {
         
     | 
| 
       133 
128 
     | 
    
         
             
                  ssl_client = Mysql2::Client.new(
         
     | 
| 
       134 
129 
     | 
    
         
             
                    :sslkey    => '/etc/mysql/client-key.pem',
         
     | 
| 
       135 
130 
     | 
    
         
             
                    :sslcert   => '/etc/mysql/client-cert.pem',
         
     | 
| 
         @@ -137,25 +132,34 @@ describe Mysql2::Client do 
     | 
|
| 
       137 
132 
     | 
    
         
             
                    :sslcapath => '/etc/mysql/',
         
     | 
| 
       138 
133 
     | 
    
         
             
                    :sslcipher => 'DHE-RSA-AES256-SHA'
         
     | 
| 
       139 
134 
     | 
    
         
             
                  )
         
     | 
| 
       140 
     | 
    
         
            -
                }. 
     | 
| 
      
 135 
     | 
    
         
            +
                }.not_to raise_error
         
     | 
| 
       141 
136 
     | 
    
         | 
| 
       142 
137 
     | 
    
         
             
                results = ssl_client.query("SHOW STATUS WHERE Variable_name = \"Ssl_version\" OR Variable_name = \"Ssl_cipher\"").to_a
         
     | 
| 
       143 
     | 
    
         
            -
                results[0]['Variable_name']. 
     | 
| 
       144 
     | 
    
         
            -
                results[0]['Value']. 
     | 
| 
       145 
     | 
    
         
            -
                results[0]['Value']. 
     | 
| 
       146 
     | 
    
         
            -
                results[0]['Value']. 
     | 
| 
      
 138 
     | 
    
         
            +
                expect(results[0]['Variable_name']).to eql('Ssl_cipher')
         
     | 
| 
      
 139 
     | 
    
         
            +
                expect(results[0]['Value']).not_to be_nil
         
     | 
| 
      
 140 
     | 
    
         
            +
                expect(results[0]['Value']).to be_kind_of(String)
         
     | 
| 
      
 141 
     | 
    
         
            +
                expect(results[0]['Value']).not_to be_empty
         
     | 
| 
       147 
142 
     | 
    
         | 
| 
       148 
     | 
    
         
            -
                results[1]['Variable_name']. 
     | 
| 
       149 
     | 
    
         
            -
                results[1]['Value']. 
     | 
| 
       150 
     | 
    
         
            -
                results[1]['Value']. 
     | 
| 
       151 
     | 
    
         
            -
                results[1]['Value']. 
     | 
| 
      
 143 
     | 
    
         
            +
                expect(results[1]['Variable_name']).to eql('Ssl_version')
         
     | 
| 
      
 144 
     | 
    
         
            +
                expect(results[1]['Value']).not_to be_nil
         
     | 
| 
      
 145 
     | 
    
         
            +
                expect(results[1]['Value']).to be_kind_of(String)
         
     | 
| 
      
 146 
     | 
    
         
            +
                expect(results[1]['Value']).not_to be_empty
         
     | 
| 
       152 
147 
     | 
    
         | 
| 
       153 
148 
     | 
    
         
             
                ssl_client.close
         
     | 
| 
       154 
149 
     | 
    
         
             
              end
         
     | 
| 
       155 
150 
     | 
    
         | 
| 
      
 151 
     | 
    
         
            +
              def run_gc
         
     | 
| 
      
 152 
     | 
    
         
            +
                if defined?(Rubinius)
         
     | 
| 
      
 153 
     | 
    
         
            +
                  GC.run(true)
         
     | 
| 
      
 154 
     | 
    
         
            +
                else
         
     | 
| 
      
 155 
     | 
    
         
            +
                  GC.start
         
     | 
| 
      
 156 
     | 
    
         
            +
                end
         
     | 
| 
      
 157 
     | 
    
         
            +
                sleep(0.5)
         
     | 
| 
      
 158 
     | 
    
         
            +
              end
         
     | 
| 
      
 159 
     | 
    
         
            +
             
     | 
| 
       156 
160 
     | 
    
         
             
              it "should not leave dangling connections after garbage collection" do
         
     | 
| 
       157 
     | 
    
         
            -
                 
     | 
| 
       158 
     | 
    
         
            -
             
     | 
| 
      
 161 
     | 
    
         
            +
                run_gc
         
     | 
| 
      
 162 
     | 
    
         
            +
             
     | 
| 
       159 
163 
     | 
    
         
             
                client = Mysql2::Client.new(DatabaseCredentials['root'])
         
     | 
| 
       160 
164 
     | 
    
         
             
                before_count = client.query("SHOW STATUS LIKE 'Threads_connected'").first['Value'].to_i
         
     | 
| 
       161 
165 
     | 
    
         | 
| 
         @@ -163,69 +167,70 @@ describe Mysql2::Client do 
     | 
|
| 
       163 
167 
     | 
    
         
             
                  Mysql2::Client.new(DatabaseCredentials['root']).query('SELECT 1')
         
     | 
| 
       164 
168 
     | 
    
         
             
                end
         
     | 
| 
       165 
169 
     | 
    
         
             
                after_count = client.query("SHOW STATUS LIKE 'Threads_connected'").first['Value'].to_i
         
     | 
| 
       166 
     | 
    
         
            -
                after_count. 
     | 
| 
      
 170 
     | 
    
         
            +
                expect(after_count).to eq(before_count + 10)
         
     | 
| 
       167 
171 
     | 
    
         | 
| 
       168 
     | 
    
         
            -
                 
     | 
| 
       169 
     | 
    
         
            -
                sleep 0.300 # Let GC do its work
         
     | 
| 
      
 172 
     | 
    
         
            +
                run_gc
         
     | 
| 
       170 
173 
     | 
    
         
             
                final_count = client.query("SHOW STATUS LIKE 'Threads_connected'").first['Value'].to_i
         
     | 
| 
       171 
     | 
    
         
            -
                final_count. 
     | 
| 
      
 174 
     | 
    
         
            +
                expect(final_count).to eq(before_count)
         
     | 
| 
       172 
175 
     | 
    
         
             
              end
         
     | 
| 
       173 
176 
     | 
    
         | 
| 
       174 
     | 
    
         
            -
               
     | 
| 
       175 
     | 
    
         
            -
                 
     | 
| 
       176 
     | 
    
         
            -
                  GC.start
         
     | 
| 
       177 
     | 
    
         
            -
                  sleep 1 if defined? Rubinius # Let the rbx GC thread do its work
         
     | 
| 
       178 
     | 
    
         
            -
                  client = Mysql2::Client.new(DatabaseCredentials['root'])
         
     | 
| 
       179 
     | 
    
         
            -
             
     | 
| 
       180 
     | 
    
         
            -
                  fork do
         
     | 
| 
       181 
     | 
    
         
            -
                    client.query('SELECT 1')
         
     | 
| 
       182 
     | 
    
         
            -
                    client = nil
         
     | 
| 
       183 
     | 
    
         
            -
                    GC.start
         
     | 
| 
       184 
     | 
    
         
            -
                    sleep 1 if defined? Rubinius # Let the rbx GC thread do its work
         
     | 
| 
       185 
     | 
    
         
            -
                  end
         
     | 
| 
      
 177 
     | 
    
         
            +
              it "should not close connections when running in a child process" do
         
     | 
| 
      
 178 
     | 
    
         
            +
                pending("fork is not available on this platform") unless Process.respond_to?(:fork)
         
     | 
| 
       186 
179 
     | 
    
         | 
| 
       187 
     | 
    
         
            -
             
     | 
| 
      
 180 
     | 
    
         
            +
                run_gc
         
     | 
| 
      
 181 
     | 
    
         
            +
                client = Mysql2::Client.new(DatabaseCredentials['root'])
         
     | 
| 
      
 182 
     | 
    
         
            +
             
     | 
| 
      
 183 
     | 
    
         
            +
                # this empty `fork` call fixes this tests on RBX; without it, the next
         
     | 
| 
      
 184 
     | 
    
         
            +
                # `fork` call hangs forever. WTF?
         
     | 
| 
      
 185 
     | 
    
         
            +
                fork { }
         
     | 
| 
       188 
186 
     | 
    
         | 
| 
       189 
     | 
    
         
            -
             
     | 
| 
       190 
     | 
    
         
            -
                   
     | 
| 
       191 
     | 
    
         
            -
                   
     | 
| 
      
 187 
     | 
    
         
            +
                fork do
         
     | 
| 
      
 188 
     | 
    
         
            +
                  client.query('SELECT 1')
         
     | 
| 
      
 189 
     | 
    
         
            +
                  client = nil
         
     | 
| 
      
 190 
     | 
    
         
            +
                  run_gc
         
     | 
| 
       192 
191 
     | 
    
         
             
                end
         
     | 
| 
      
 192 
     | 
    
         
            +
             
     | 
| 
      
 193 
     | 
    
         
            +
                Process.wait
         
     | 
| 
      
 194 
     | 
    
         
            +
             
     | 
| 
      
 195 
     | 
    
         
            +
                # this will throw an error if the underlying socket was shutdown by the
         
     | 
| 
      
 196 
     | 
    
         
            +
                # child's GC
         
     | 
| 
      
 197 
     | 
    
         
            +
                expect { client.query('SELECT 1') }.to_not raise_exception
         
     | 
| 
       193 
198 
     | 
    
         
             
              end
         
     | 
| 
       194 
199 
     | 
    
         | 
| 
       195 
200 
     | 
    
         
             
              it "should be able to connect to database with numeric-only name" do
         
     | 
| 
       196 
     | 
    
         
            -
                 
     | 
| 
       197 
     | 
    
         
            -
             
     | 
| 
       198 
     | 
    
         
            -
             
     | 
| 
       199 
     | 
    
         
            -
             
     | 
| 
       200 
     | 
    
         
            -
             
     | 
| 
       201 
     | 
    
         
            -
             
     | 
| 
       202 
     | 
    
         
            -
                 
     | 
| 
      
 201 
     | 
    
         
            +
                creds = DatabaseCredentials['numericuser']
         
     | 
| 
      
 202 
     | 
    
         
            +
                @client.query "CREATE DATABASE IF NOT EXISTS `#{creds['database']}`"
         
     | 
| 
      
 203 
     | 
    
         
            +
                @client.query "GRANT ALL ON `#{creds['database']}`.* TO #{creds['username']}@`#{creds['host']}`"
         
     | 
| 
      
 204 
     | 
    
         
            +
             
     | 
| 
      
 205 
     | 
    
         
            +
                expect { Mysql2::Client.new(creds) }.not_to raise_error
         
     | 
| 
      
 206 
     | 
    
         
            +
             
     | 
| 
      
 207 
     | 
    
         
            +
                @client.query "DROP DATABASE IF EXISTS `#{creds['database']}`"
         
     | 
| 
       203 
208 
     | 
    
         
             
              end
         
     | 
| 
       204 
209 
     | 
    
         | 
| 
       205 
210 
     | 
    
         
             
              it "should respond to #close" do
         
     | 
| 
       206 
     | 
    
         
            -
                @client. 
     | 
| 
      
 211 
     | 
    
         
            +
                expect(@client).to respond_to(:close)
         
     | 
| 
       207 
212 
     | 
    
         
             
              end
         
     | 
| 
       208 
213 
     | 
    
         | 
| 
       209 
214 
     | 
    
         
             
              it "should be able to close properly" do
         
     | 
| 
       210 
     | 
    
         
            -
                @client.close. 
     | 
| 
       211 
     | 
    
         
            -
                 
     | 
| 
      
 215 
     | 
    
         
            +
                expect(@client.close).to be_nil
         
     | 
| 
      
 216 
     | 
    
         
            +
                expect {
         
     | 
| 
       212 
217 
     | 
    
         
             
                  @client.query "SELECT 1"
         
     | 
| 
       213 
     | 
    
         
            -
                }. 
     | 
| 
      
 218 
     | 
    
         
            +
                }.to raise_error(Mysql2::Error)
         
     | 
| 
       214 
219 
     | 
    
         
             
              end
         
     | 
| 
       215 
220 
     | 
    
         | 
| 
       216 
221 
     | 
    
         
             
              it "should respond to #query" do
         
     | 
| 
       217 
     | 
    
         
            -
                @client. 
     | 
| 
      
 222 
     | 
    
         
            +
                expect(@client).to respond_to(:query)
         
     | 
| 
       218 
223 
     | 
    
         
             
              end
         
     | 
| 
       219 
224 
     | 
    
         | 
| 
       220 
225 
     | 
    
         
             
              it "should respond to #warning_count" do
         
     | 
| 
       221 
     | 
    
         
            -
                @client. 
     | 
| 
      
 226 
     | 
    
         
            +
                expect(@client).to respond_to(:warning_count)
         
     | 
| 
       222 
227 
     | 
    
         
             
              end
         
     | 
| 
       223 
228 
     | 
    
         | 
| 
       224 
229 
     | 
    
         
             
              context "#warning_count" do
         
     | 
| 
       225 
230 
     | 
    
         
             
                context "when no warnings" do
         
     | 
| 
       226 
231 
     | 
    
         
             
                  it "should 0" do
         
     | 
| 
       227 
232 
     | 
    
         
             
                    @client.query('select 1')
         
     | 
| 
       228 
     | 
    
         
            -
                    @client.warning_count. 
     | 
| 
      
 233 
     | 
    
         
            +
                    expect(@client.warning_count).to eq(0)
         
     | 
| 
       229 
234 
     | 
    
         
             
                  end
         
     | 
| 
       230 
235 
     | 
    
         
             
                end
         
     | 
| 
       231 
236 
     | 
    
         
             
                context "when has a warnings" do
         
     | 
| 
         @@ -233,21 +238,21 @@ describe Mysql2::Client do 
     | 
|
| 
       233 
238 
     | 
    
         
             
                    # "the statement produces extra information that can be viewed by issuing a SHOW WARNINGS"
         
     | 
| 
       234 
239 
     | 
    
         
             
                    # http://dev.mysql.com/doc/refman/5.0/en/explain-extended.html
         
     | 
| 
       235 
240 
     | 
    
         
             
                    @client.query("explain extended select 1")
         
     | 
| 
       236 
     | 
    
         
            -
                    @client.warning_count. 
     | 
| 
      
 241 
     | 
    
         
            +
                    expect(@client.warning_count).to be > 0
         
     | 
| 
       237 
242 
     | 
    
         
             
                  end
         
     | 
| 
       238 
243 
     | 
    
         
             
                end
         
     | 
| 
       239 
244 
     | 
    
         
             
              end
         
     | 
| 
       240 
245 
     | 
    
         | 
| 
       241 
246 
     | 
    
         
             
              it "should respond to #query_info" do
         
     | 
| 
       242 
     | 
    
         
            -
                @client. 
     | 
| 
      
 247 
     | 
    
         
            +
                expect(@client).to respond_to(:query_info)
         
     | 
| 
       243 
248 
     | 
    
         
             
              end
         
     | 
| 
       244 
249 
     | 
    
         | 
| 
       245 
250 
     | 
    
         
             
              context "#query_info" do
         
     | 
| 
       246 
251 
     | 
    
         
             
                context "when no info present" do
         
     | 
| 
       247 
252 
     | 
    
         
             
                  it "should 0" do
         
     | 
| 
       248 
253 
     | 
    
         
             
                    @client.query('select 1')
         
     | 
| 
       249 
     | 
    
         
            -
                    @client.query_info. 
     | 
| 
       250 
     | 
    
         
            -
                    @client.query_info_string. 
     | 
| 
      
 254 
     | 
    
         
            +
                    expect(@client.query_info).to be_empty
         
     | 
| 
      
 255 
     | 
    
         
            +
                    expect(@client.query_info_string).to be_nil
         
     | 
| 
       251 
256 
     | 
    
         
             
                  end
         
     | 
| 
       252 
257 
     | 
    
         
             
                end
         
     | 
| 
       253 
258 
     | 
    
         
             
                context "when has some info" do
         
     | 
| 
         @@ -259,8 +264,8 @@ describe Mysql2::Client do 
     | 
|
| 
       259 
264 
     | 
    
         
             
                    # # Note that mysql_info() returns a non-NULL value for INSERT ... VALUES only for the multiple-row form of the statement (that is, only if multiple value lists are specified).
         
     | 
| 
       260 
265 
     | 
    
         
             
                    @client.query("INSERT INTO infoTest (blah) VALUES (1234),(4535)")
         
     | 
| 
       261 
266 
     | 
    
         | 
| 
       262 
     | 
    
         
            -
                    @client.query_info. 
     | 
| 
       263 
     | 
    
         
            -
                    @client.query_info_string. 
     | 
| 
      
 267 
     | 
    
         
            +
                    expect(@client.query_info).to  eql({:records => 2, :duplicates => 0, :warnings => 0})
         
     | 
| 
      
 268 
     | 
    
         
            +
                    expect(@client.query_info_string).to eq('Records: 2  Duplicates: 0  Warnings: 0')
         
     | 
| 
       264 
269 
     | 
    
         | 
| 
       265 
270 
     | 
    
         
             
                    @client.query "DROP TABLE infoTest"
         
     | 
| 
       266 
271 
     | 
    
         
             
                  end
         
     | 
| 
         @@ -289,43 +294,43 @@ describe Mysql2::Client do 
     | 
|
| 
       289 
294 
     | 
    
         | 
| 
       290 
295 
     | 
    
         
             
                it "should raise an error when local_infile is disabled" do
         
     | 
| 
       291 
296 
     | 
    
         
             
                  client = Mysql2::Client.new DatabaseCredentials['root'].merge(:local_infile => false)
         
     | 
| 
       292 
     | 
    
         
            -
                   
     | 
| 
      
 297 
     | 
    
         
            +
                  expect {
         
     | 
| 
       293 
298 
     | 
    
         
             
                    client.query "LOAD DATA LOCAL INFILE 'spec/test_data' INTO TABLE infileTest"
         
     | 
| 
       294 
     | 
    
         
            -
                  }. 
     | 
| 
      
 299 
     | 
    
         
            +
                  }.to raise_error(Mysql2::Error, /command is not allowed/)
         
     | 
| 
       295 
300 
     | 
    
         
             
                end
         
     | 
| 
       296 
301 
     | 
    
         | 
| 
       297 
302 
     | 
    
         
             
                it "should raise an error when a non-existent file is loaded" do
         
     | 
| 
       298 
     | 
    
         
            -
                   
     | 
| 
      
 303 
     | 
    
         
            +
                  expect {
         
     | 
| 
       299 
304 
     | 
    
         
             
                    @client_i.query "LOAD DATA LOCAL INFILE 'this/file/is/not/here' INTO TABLE infileTest"
         
     | 
| 
       300 
     | 
    
         
            -
                  }. 
     | 
| 
      
 305 
     | 
    
         
            +
                  }.to raise_error(Mysql2::Error, 'No such file or directory: this/file/is/not/here')
         
     | 
| 
       301 
306 
     | 
    
         
             
                end
         
     | 
| 
       302 
307 
     | 
    
         | 
| 
       303 
308 
     | 
    
         
             
                it "should LOAD DATA LOCAL INFILE" do
         
     | 
| 
       304 
309 
     | 
    
         
             
                  @client_i.query "LOAD DATA LOCAL INFILE 'spec/test_data' INTO TABLE infileTest"
         
     | 
| 
       305 
310 
     | 
    
         
             
                  info = @client_i.query_info
         
     | 
| 
       306 
     | 
    
         
            -
                  info. 
     | 
| 
      
 311 
     | 
    
         
            +
                  expect(info).to eql({:records => 1, :deleted => 0, :skipped => 0, :warnings => 0})
         
     | 
| 
       307 
312 
     | 
    
         | 
| 
       308 
313 
     | 
    
         
             
                  result = @client_i.query "SELECT * FROM infileTest"
         
     | 
| 
       309 
     | 
    
         
            -
                  result.first. 
     | 
| 
      
 314 
     | 
    
         
            +
                  expect(result.first).to eql({'id' => 1, 'foo' => 'Hello', 'bar' => 'World'})
         
     | 
| 
       310 
315 
     | 
    
         
             
                end
         
     | 
| 
       311 
316 
     | 
    
         
             
              end
         
     | 
| 
       312 
317 
     | 
    
         | 
| 
       313 
318 
     | 
    
         
             
              it "should expect connect_timeout to be a positive integer" do
         
     | 
| 
       314 
     | 
    
         
            -
                 
     | 
| 
      
 319 
     | 
    
         
            +
                expect {
         
     | 
| 
       315 
320 
     | 
    
         
             
                  Mysql2::Client.new(:connect_timeout => -1)
         
     | 
| 
       316 
     | 
    
         
            -
                }. 
     | 
| 
      
 321 
     | 
    
         
            +
                }.to raise_error(Mysql2::Error)
         
     | 
| 
       317 
322 
     | 
    
         
             
              end
         
     | 
| 
       318 
323 
     | 
    
         | 
| 
       319 
324 
     | 
    
         
             
              it "should expect read_timeout to be a positive integer" do
         
     | 
| 
       320 
     | 
    
         
            -
                 
     | 
| 
      
 325 
     | 
    
         
            +
                expect {
         
     | 
| 
       321 
326 
     | 
    
         
             
                  Mysql2::Client.new(:read_timeout => -1)
         
     | 
| 
       322 
     | 
    
         
            -
                }. 
     | 
| 
      
 327 
     | 
    
         
            +
                }.to raise_error(Mysql2::Error)
         
     | 
| 
       323 
328 
     | 
    
         
             
              end
         
     | 
| 
       324 
329 
     | 
    
         | 
| 
       325 
330 
     | 
    
         
             
              it "should expect write_timeout to be a positive integer" do
         
     | 
| 
       326 
     | 
    
         
            -
                 
     | 
| 
      
 331 
     | 
    
         
            +
                expect {
         
     | 
| 
       327 
332 
     | 
    
         
             
                  Mysql2::Client.new(:write_timeout => -1)
         
     | 
| 
       328 
     | 
    
         
            -
                }. 
     | 
| 
      
 333 
     | 
    
         
            +
                }.to raise_error(Mysql2::Error)
         
     | 
| 
       329 
334 
     | 
    
         
             
              end
         
     | 
| 
       330 
335 
     | 
    
         | 
| 
       331 
336 
     | 
    
         
             
              context "#query" do
         
     | 
| 
         @@ -334,7 +339,7 @@ describe Mysql2::Client do 
     | 
|
| 
       334 
339 
     | 
    
         | 
| 
       335 
340 
     | 
    
         
             
                  expect {
         
     | 
| 
       336 
341 
     | 
    
         
             
                    @client.query("SELECT 1 UNION SELECT 2", :stream => true, :cache_rows => false)
         
     | 
| 
       337 
     | 
    
         
            -
                  }.to_not  
     | 
| 
      
 342 
     | 
    
         
            +
                  }.to_not raise_error
         
     | 
| 
       338 
343 
     | 
    
         
             
                end
         
     | 
| 
       339 
344 
     | 
    
         | 
| 
       340 
345 
     | 
    
         
             
                it "should not let you query again if iterating is not finished when streaming" do
         
     | 
| 
         @@ -346,126 +351,121 @@ describe Mysql2::Client do 
     | 
|
| 
       346 
351 
     | 
    
         
             
                end
         
     | 
| 
       347 
352 
     | 
    
         | 
| 
       348 
353 
     | 
    
         
             
                it "should only accept strings as the query parameter" do
         
     | 
| 
       349 
     | 
    
         
            -
                   
     | 
| 
      
 354 
     | 
    
         
            +
                  expect {
         
     | 
| 
       350 
355 
     | 
    
         
             
                    @client.query ["SELECT 'not right'"]
         
     | 
| 
       351 
     | 
    
         
            -
                  }. 
     | 
| 
      
 356 
     | 
    
         
            +
                  }.to raise_error(TypeError)
         
     | 
| 
       352 
357 
     | 
    
         
             
                end
         
     | 
| 
       353 
358 
     | 
    
         | 
| 
       354 
359 
     | 
    
         
             
                it "should not retain query options set on a query for subsequent queries, but should retain it in the result" do
         
     | 
| 
       355 
360 
     | 
    
         
             
                  result = @client.query "SELECT 1", :something => :else
         
     | 
| 
       356 
     | 
    
         
            -
                  @client.query_options[:something]. 
     | 
| 
       357 
     | 
    
         
            -
                  result.instance_variable_get('@query_options'). 
     | 
| 
       358 
     | 
    
         
            -
                  @client.instance_variable_get('@current_query_options'). 
     | 
| 
      
 361 
     | 
    
         
            +
                  expect(@client.query_options[:something]).to be_nil
         
     | 
| 
      
 362 
     | 
    
         
            +
                  expect(result.instance_variable_get('@query_options')).to eql(@client.query_options.merge(:something => :else))
         
     | 
| 
      
 363 
     | 
    
         
            +
                  expect(@client.instance_variable_get('@current_query_options')).to eql(@client.query_options.merge(:something => :else))
         
     | 
| 
       359 
364 
     | 
    
         | 
| 
       360 
365 
     | 
    
         
             
                  result = @client.query "SELECT 1"
         
     | 
| 
       361 
     | 
    
         
            -
                  result.instance_variable_get('@query_options'). 
     | 
| 
       362 
     | 
    
         
            -
                  @client.instance_variable_get('@current_query_options'). 
     | 
| 
      
 366 
     | 
    
         
            +
                  expect(result.instance_variable_get('@query_options')).to eql(@client.query_options)
         
     | 
| 
      
 367 
     | 
    
         
            +
                  expect(@client.instance_variable_get('@current_query_options')).to eql(@client.query_options)
         
     | 
| 
       363 
368 
     | 
    
         
             
                end
         
     | 
| 
       364 
369 
     | 
    
         | 
| 
       365 
370 
     | 
    
         
             
                it "should allow changing query options for subsequent queries" do
         
     | 
| 
       366 
371 
     | 
    
         
             
                  @client.query_options.merge!(:something => :else)
         
     | 
| 
       367 
372 
     | 
    
         
             
                  result = @client.query "SELECT 1"
         
     | 
| 
       368 
     | 
    
         
            -
                  @client.query_options[:something]. 
     | 
| 
       369 
     | 
    
         
            -
                  result.instance_variable_get('@query_options')[:something]. 
     | 
| 
      
 373 
     | 
    
         
            +
                  expect(@client.query_options[:something]).to eql(:else)
         
     | 
| 
      
 374 
     | 
    
         
            +
                  expect(result.instance_variable_get('@query_options')[:something]).to eql(:else)
         
     | 
| 
       370 
375 
     | 
    
         | 
| 
       371 
376 
     | 
    
         
             
                  # Clean up after this test
         
     | 
| 
       372 
377 
     | 
    
         
             
                  @client.query_options.delete(:something)
         
     | 
| 
       373 
     | 
    
         
            -
                  @client.query_options[:something]. 
     | 
| 
      
 378 
     | 
    
         
            +
                  expect(@client.query_options[:something]).to be_nil
         
     | 
| 
       374 
379 
     | 
    
         
             
                end
         
     | 
| 
       375 
380 
     | 
    
         | 
| 
       376 
381 
     | 
    
         
             
                it "should return results as a hash by default" do
         
     | 
| 
       377 
     | 
    
         
            -
                  @client.query("SELECT 1").first.class. 
     | 
| 
      
 382 
     | 
    
         
            +
                  expect(@client.query("SELECT 1").first.class).to eql(Hash)
         
     | 
| 
       378 
383 
     | 
    
         
             
                end
         
     | 
| 
       379 
384 
     | 
    
         | 
| 
       380 
385 
     | 
    
         
             
                it "should be able to return results as an array" do
         
     | 
| 
       381 
     | 
    
         
            -
                  @client.query("SELECT 1", :as => :array).first.class. 
     | 
| 
      
 386 
     | 
    
         
            +
                  expect(@client.query("SELECT 1", :as => :array).first.class).to eql(Array)
         
     | 
| 
       382 
387 
     | 
    
         
             
                  @client.query("SELECT 1").each(:as => :array)
         
     | 
| 
       383 
388 
     | 
    
         
             
                end
         
     | 
| 
       384 
389 
     | 
    
         | 
| 
       385 
390 
     | 
    
         
             
                it "should be able to return results with symbolized keys" do
         
     | 
| 
       386 
     | 
    
         
            -
                  @client.query("SELECT 1", :symbolize_keys => true).first.keys[0].class. 
     | 
| 
      
 391 
     | 
    
         
            +
                  expect(@client.query("SELECT 1", :symbolize_keys => true).first.keys[0].class).to eql(Symbol)
         
     | 
| 
       387 
392 
     | 
    
         
             
                end
         
     | 
| 
       388 
393 
     | 
    
         | 
| 
       389 
394 
     | 
    
         
             
                it "should require an open connection" do
         
     | 
| 
       390 
395 
     | 
    
         
             
                  @client.close
         
     | 
| 
       391 
     | 
    
         
            -
                   
     | 
| 
      
 396 
     | 
    
         
            +
                  expect {
         
     | 
| 
       392 
397 
     | 
    
         
             
                    @client.query "SELECT 1"
         
     | 
| 
       393 
     | 
    
         
            -
                  }. 
     | 
| 
      
 398 
     | 
    
         
            +
                  }.to raise_error(Mysql2::Error)
         
     | 
| 
       394 
399 
     | 
    
         
             
                end
         
     | 
| 
       395 
400 
     | 
    
         | 
| 
       396 
401 
     | 
    
         
             
                if RUBY_PLATFORM !~ /mingw|mswin/
         
     | 
| 
       397 
402 
     | 
    
         
             
                  it "should not allow another query to be sent without fetching a result first" do
         
     | 
| 
       398 
403 
     | 
    
         
             
                    @client.query("SELECT 1", :async => true)
         
     | 
| 
       399 
     | 
    
         
            -
                     
     | 
| 
      
 404 
     | 
    
         
            +
                    expect {
         
     | 
| 
       400 
405 
     | 
    
         
             
                      @client.query("SELECT 1")
         
     | 
| 
       401 
     | 
    
         
            -
                    }. 
     | 
| 
      
 406 
     | 
    
         
            +
                    }.to raise_error(Mysql2::Error)
         
     | 
| 
       402 
407 
     | 
    
         
             
                  end
         
     | 
| 
       403 
408 
     | 
    
         | 
| 
       404 
409 
     | 
    
         
             
                  it "should describe the thread holding the active query" do
         
     | 
| 
       405 
410 
     | 
    
         
             
                    thr = Thread.new { @client.query("SELECT 1", :async => true) }
         
     | 
| 
       406 
411 
     | 
    
         | 
| 
       407 
412 
     | 
    
         
             
                    thr.join
         
     | 
| 
       408 
     | 
    
         
            -
                     
     | 
| 
       409 
     | 
    
         
            -
                      @client.query("SELECT 1")
         
     | 
| 
       410 
     | 
    
         
            -
                    rescue Mysql2::Error => e
         
     | 
| 
       411 
     | 
    
         
            -
                      message = e.message
         
     | 
| 
       412 
     | 
    
         
            -
                    end
         
     | 
| 
       413 
     | 
    
         
            -
                    re = Regexp.escape(thr.inspect)
         
     | 
| 
       414 
     | 
    
         
            -
                    message.should match(Regexp.new(re))
         
     | 
| 
      
 413 
     | 
    
         
            +
                    expect { @client.query('SELECT 1') }.to raise_error(Mysql2::Error, Regexp.new(Regexp.escape(thr.inspect)))
         
     | 
| 
       415 
414 
     | 
    
         
             
                  end
         
     | 
| 
       416 
415 
     | 
    
         | 
| 
       417 
416 
     | 
    
         
             
                  it "should timeout if we wait longer than :read_timeout" do
         
     | 
| 
       418 
     | 
    
         
            -
                    client = Mysql2::Client.new(DatabaseCredentials['root'].merge(:read_timeout =>  
     | 
| 
       419 
     | 
    
         
            -
                     
     | 
| 
       420 
     | 
    
         
            -
                      client.query( 
     | 
| 
       421 
     | 
    
         
            -
                    }. 
     | 
| 
      
 417 
     | 
    
         
            +
                    client = Mysql2::Client.new(DatabaseCredentials['root'].merge(:read_timeout => 0))
         
     | 
| 
      
 418 
     | 
    
         
            +
                    expect {
         
     | 
| 
      
 419 
     | 
    
         
            +
                      client.query('SELECT SLEEP(0.1)')
         
     | 
| 
      
 420 
     | 
    
         
            +
                    }.to raise_error(Mysql2::Error)
         
     | 
| 
       422 
421 
     | 
    
         
             
                  end
         
     | 
| 
       423 
422 
     | 
    
         | 
| 
       424 
     | 
    
         
            -
                   
     | 
| 
       425 
     | 
    
         
            -
             
     | 
| 
       426 
     | 
    
         
            -
             
     | 
| 
       427 
     | 
    
         
            -
                     
     | 
| 
       428 
     | 
    
         
            -
             
     | 
| 
       429 
     | 
    
         
            -
             
     | 
| 
       430 
     | 
    
         
            -
             
     | 
| 
       431 
     | 
    
         
            -
             
     | 
| 
       432 
     | 
    
         
            -
             
     | 
| 
       433 
     | 
    
         
            -
             
     | 
| 
       434 
     | 
    
         
            -
             
     | 
| 
       435 
     | 
    
         
            -
             
     | 
| 
       436 
     | 
    
         
            -
                         
     | 
| 
       437 
     | 
    
         
            -
                         
     | 
| 
       438 
     | 
    
         
            -
                        mark[:END] = Time.now
         
     | 
| 
       439 
     | 
    
         
            -
                        mark.include?(:USR1).should be_true
         
     | 
| 
       440 
     | 
    
         
            -
                        (mark[:USR1] - mark[:START]).should >= 1
         
     | 
| 
       441 
     | 
    
         
            -
                        (mark[:USR1] - mark[:START]).should < 1.3
         
     | 
| 
       442 
     | 
    
         
            -
                        (mark[:END] - mark[:USR1]).should > 0.9
         
     | 
| 
       443 
     | 
    
         
            -
                        (mark[:END] - mark[:START]).should >= 2
         
     | 
| 
       444 
     | 
    
         
            -
                        (mark[:END] - mark[:START]).should < 2.3
         
     | 
| 
       445 
     | 
    
         
            -
                        Process.kill(:TERM, pid)
         
     | 
| 
       446 
     | 
    
         
            -
                        Process.waitpid2(pid)
         
     | 
| 
       447 
     | 
    
         
            -
                      ensure
         
     | 
| 
       448 
     | 
    
         
            -
                        trap(:USR1, 'DEFAULT')
         
     | 
| 
      
 423 
     | 
    
         
            +
                  # XXX this test is not deterministic (because Unix signal handling is not)
         
     | 
| 
      
 424 
     | 
    
         
            +
                  # and may fail on a loaded system
         
     | 
| 
      
 425 
     | 
    
         
            +
                  it "should run signal handlers while waiting for a response" do
         
     | 
| 
      
 426 
     | 
    
         
            +
                    kill_time = 0.1
         
     | 
| 
      
 427 
     | 
    
         
            +
                    query_time = 2 * kill_time
         
     | 
| 
      
 428 
     | 
    
         
            +
             
     | 
| 
      
 429 
     | 
    
         
            +
                    mark = {}
         
     | 
| 
      
 430 
     | 
    
         
            +
             
     | 
| 
      
 431 
     | 
    
         
            +
                    begin
         
     | 
| 
      
 432 
     | 
    
         
            +
                      trap(:USR1) { mark.store(:USR1, Time.now) }
         
     | 
| 
      
 433 
     | 
    
         
            +
                      pid = fork do
         
     | 
| 
      
 434 
     | 
    
         
            +
                        sleep kill_time # wait for client query to start
         
     | 
| 
      
 435 
     | 
    
         
            +
                        Process.kill(:USR1, Process.ppid)
         
     | 
| 
      
 436 
     | 
    
         
            +
                        sleep # wait for explicit kill to prevent GC disconnect
         
     | 
| 
       449 
437 
     | 
    
         
             
                      end
         
     | 
| 
      
 438 
     | 
    
         
            +
                      mark.store(:QUERY_START, Time.now)
         
     | 
| 
      
 439 
     | 
    
         
            +
                      @client.query("SELECT SLEEP(#{query_time})")
         
     | 
| 
      
 440 
     | 
    
         
            +
                      mark.store(:QUERY_END, Time.now)
         
     | 
| 
      
 441 
     | 
    
         
            +
                    ensure
         
     | 
| 
      
 442 
     | 
    
         
            +
                      Process.kill(:TERM, pid)
         
     | 
| 
      
 443 
     | 
    
         
            +
                      Process.waitpid2(pid)
         
     | 
| 
      
 444 
     | 
    
         
            +
                      trap(:USR1, 'DEFAULT')
         
     | 
| 
       450 
445 
     | 
    
         
             
                    end
         
     | 
| 
      
 446 
     | 
    
         
            +
             
     | 
| 
      
 447 
     | 
    
         
            +
                    # the query ran uninterrupted
         
     | 
| 
      
 448 
     | 
    
         
            +
                    expect(mark.fetch(:QUERY_END) - mark.fetch(:QUERY_START)).to be_within(0.02).of(query_time)
         
     | 
| 
      
 449 
     | 
    
         
            +
                    # signals fired while the query was running
         
     | 
| 
      
 450 
     | 
    
         
            +
                    expect(mark.fetch(:USR1)).to be_between(mark.fetch(:QUERY_START), mark.fetch(:QUERY_END))
         
     | 
| 
       451 
451 
     | 
    
         
             
                  end
         
     | 
| 
       452 
452 
     | 
    
         | 
| 
       453 
453 
     | 
    
         
             
                  it "#socket should return a Fixnum (file descriptor from C)" do
         
     | 
| 
       454 
     | 
    
         
            -
                    @client.socket.class. 
     | 
| 
       455 
     | 
    
         
            -
                    @client.socket. 
     | 
| 
      
 454 
     | 
    
         
            +
                    expect(@client.socket.class).to eql(Fixnum)
         
     | 
| 
      
 455 
     | 
    
         
            +
                    expect(@client.socket).not_to eql(0)
         
     | 
| 
       456 
456 
     | 
    
         
             
                  end
         
     | 
| 
       457 
457 
     | 
    
         | 
| 
       458 
458 
     | 
    
         
             
                  it "#socket should require an open connection" do
         
     | 
| 
       459 
459 
     | 
    
         
             
                    @client.close
         
     | 
| 
       460 
     | 
    
         
            -
                     
     | 
| 
      
 460 
     | 
    
         
            +
                    expect {
         
     | 
| 
       461 
461 
     | 
    
         
             
                      @client.socket
         
     | 
| 
       462 
     | 
    
         
            -
                    }. 
     | 
| 
      
 462 
     | 
    
         
            +
                    }.to raise_error(Mysql2::Error)
         
     | 
| 
       463 
463 
     | 
    
         
             
                  end
         
     | 
| 
       464 
464 
     | 
    
         | 
| 
       465 
     | 
    
         
            -
                  it 'should be impervious to connection-corrupting timeouts  
     | 
| 
      
 465 
     | 
    
         
            +
                  it 'should be impervious to connection-corrupting timeouts ' do
         
     | 
| 
       466 
466 
     | 
    
         
             
                    pending('`Thread.handle_interrupt` is not defined') unless Thread.respond_to?(:handle_interrupt)
         
     | 
| 
       467 
467 
     | 
    
         
             
                    # attempt to break the connection
         
     | 
| 
       468 
     | 
    
         
            -
                    expect { Timeout.timeout(0.1) { @client.query('SELECT SLEEP( 
     | 
| 
      
 468 
     | 
    
         
            +
                    expect { Timeout.timeout(0.1) { @client.query('SELECT SLEEP(0.2)') } }.to raise_error(Timeout::Error)
         
     | 
| 
       469 
469 
     | 
    
         | 
| 
       470 
470 
     | 
    
         
             
                    # expect the connection to not be broken
         
     | 
| 
       471 
471 
     | 
    
         
             
                    expect { @client.query('SELECT 1') }.to_not raise_error
         
     | 
| 
         @@ -478,13 +478,21 @@ describe Mysql2::Client do 
     | 
|
| 
       478 
478 
     | 
    
         
             
                    end
         
     | 
| 
       479 
479 
     | 
    
         | 
| 
       480 
480 
     | 
    
         
             
                    it "should handle Timeouts without leaving the connection hanging if reconnect is true" do
         
     | 
| 
      
 481 
     | 
    
         
            +
                      if RUBY_PLATFORM.include?('darwin') && Mysql2::Client.info.fetch(:version).start_with?('5.5')
         
     | 
| 
      
 482 
     | 
    
         
            +
                        pending('libmysqlclient 5.5 on OSX is afflicted by an unknown bug that breaks this test. See #633 and #634.')
         
     | 
| 
      
 483 
     | 
    
         
            +
                      end
         
     | 
| 
      
 484 
     | 
    
         
            +
             
     | 
| 
       481 
485 
     | 
    
         
             
                      client = Mysql2::Client.new(DatabaseCredentials['root'].merge(:reconnect => true))
         
     | 
| 
       482 
486 
     | 
    
         | 
| 
       483 
487 
     | 
    
         
             
                      expect { Timeout.timeout(0.1, ArgumentError) { client.query('SELECT SLEEP(1)') } }.to raise_error(ArgumentError)
         
     | 
| 
       484 
488 
     | 
    
         
             
                      expect { client.query('SELECT 1') }.to_not raise_error
         
     | 
| 
       485 
489 
     | 
    
         
             
                    end
         
     | 
| 
       486 
490 
     | 
    
         | 
| 
       487 
     | 
    
         
            -
                    it "should handle Timeouts without leaving the connection hanging if reconnect is set to true after construction 
     | 
| 
      
 491 
     | 
    
         
            +
                    it "should handle Timeouts without leaving the connection hanging if reconnect is set to true after construction" do
         
     | 
| 
      
 492 
     | 
    
         
            +
                      if RUBY_PLATFORM.include?('darwin') && Mysql2::Client.info.fetch(:version).start_with?('5.5')
         
     | 
| 
      
 493 
     | 
    
         
            +
                        pending('libmysqlclient 5.5 on OSX is afflicted by an unknown bug that breaks this test. See #633 and #634.')
         
     | 
| 
      
 494 
     | 
    
         
            +
                      end
         
     | 
| 
      
 495 
     | 
    
         
            +
             
     | 
| 
       488 
496 
     | 
    
         
             
                      client = Mysql2::Client.new(DatabaseCredentials['root'])
         
     | 
| 
       489 
497 
     | 
    
         | 
| 
       490 
498 
     | 
    
         
             
                      expect { Timeout.timeout(0.1, ArgumentError) { client.query('SELECT SLEEP(1)') } }.to raise_error(ArgumentError)
         
     | 
| 
         @@ -498,28 +506,27 @@ describe Mysql2::Client do 
     | 
|
| 
       498 
506 
     | 
    
         
             
                  end
         
     | 
| 
       499 
507 
     | 
    
         | 
| 
       500 
508 
     | 
    
         
             
                  it "threaded queries should be supported" do
         
     | 
| 
       501 
     | 
    
         
            -
                     
     | 
| 
       502 
     | 
    
         
            -
             
     | 
| 
       503 
     | 
    
         
            -
                     
     | 
| 
       504 
     | 
    
         
            -
             
     | 
| 
       505 
     | 
    
         
            -
             
     | 
| 
       506 
     | 
    
         
            -
             
     | 
| 
       507 
     | 
    
         
            -
             
     | 
| 
       508 
     | 
    
         
            -
                         
     | 
| 
       509 
     | 
    
         
            -
             
     | 
| 
       510 
     | 
    
         
            -
                          lock.synchronize do
         
     | 
| 
       511 
     | 
    
         
            -
                            results[Thread.current.object_id] = result
         
     | 
| 
       512 
     | 
    
         
            -
                          end
         
     | 
| 
       513 
     | 
    
         
            -
                        end
         
     | 
| 
       514 
     | 
    
         
            -
                      }
         
     | 
| 
      
 509 
     | 
    
         
            +
                    sleep_time = 0.5
         
     | 
| 
      
 510 
     | 
    
         
            +
             
     | 
| 
      
 511 
     | 
    
         
            +
                    # Note that each thread opens its own database connection
         
     | 
| 
      
 512 
     | 
    
         
            +
                    threads = 5.times.map do
         
     | 
| 
      
 513 
     | 
    
         
            +
                      Thread.new do
         
     | 
| 
      
 514 
     | 
    
         
            +
                        client = Mysql2::Client.new(DatabaseCredentials.fetch('root'))
         
     | 
| 
      
 515 
     | 
    
         
            +
                        client.query("SELECT SLEEP(#{sleep_time})")
         
     | 
| 
      
 516 
     | 
    
         
            +
                        Thread.current.object_id
         
     | 
| 
      
 517 
     | 
    
         
            +
                      end
         
     | 
| 
       515 
518 
     | 
    
         
             
                    end
         
     | 
| 
       516 
     | 
    
         
            -
             
     | 
| 
       517 
     | 
    
         
            -
                     
     | 
| 
      
 519 
     | 
    
         
            +
             
     | 
| 
      
 520 
     | 
    
         
            +
                    # This timeout demonstrates that the threads are sleeping concurrently:
         
     | 
| 
      
 521 
     | 
    
         
            +
                    # In the serial case, the timeout would fire and the test would fail
         
     | 
| 
      
 522 
     | 
    
         
            +
                    values = Timeout.timeout(sleep_time * 1.1) { threads.map(&:value) }
         
     | 
| 
      
 523 
     | 
    
         
            +
             
     | 
| 
      
 524 
     | 
    
         
            +
                    expect(values).to match_array(threads.map(&:object_id))
         
     | 
| 
       518 
525 
     | 
    
         
             
                  end
         
     | 
| 
       519 
526 
     | 
    
         | 
| 
       520 
527 
     | 
    
         
             
                  it "evented async queries should be supported" do
         
     | 
| 
       521 
528 
     | 
    
         
             
                    # should immediately return nil
         
     | 
| 
       522 
     | 
    
         
            -
                    @client.query("SELECT sleep(0.1)", :async => true). 
     | 
| 
      
 529 
     | 
    
         
            +
                    expect(@client.query("SELECT sleep(0.1)", :async => true)).to eql(nil)
         
     | 
| 
       523 
530 
     | 
    
         | 
| 
       524 
531 
     | 
    
         
             
                    io_wrapper = IO.for_fd(@client.socket)
         
     | 
| 
       525 
532 
     | 
    
         
             
                    loops = 0
         
     | 
| 
         @@ -532,10 +539,10 @@ describe Mysql2::Client do 
     | 
|
| 
       532 
539 
     | 
    
         
             
                    end
         
     | 
| 
       533 
540 
     | 
    
         | 
| 
       534 
541 
     | 
    
         
             
                    # make sure we waited some period of time
         
     | 
| 
       535 
     | 
    
         
            -
                    (loops >= 1). 
     | 
| 
      
 542 
     | 
    
         
            +
                    expect(loops >= 1).to be true
         
     | 
| 
       536 
543 
     | 
    
         | 
| 
       537 
544 
     | 
    
         
             
                    result = @client.async_result
         
     | 
| 
       538 
     | 
    
         
            -
                    result.class. 
     | 
| 
      
 545 
     | 
    
         
            +
                    expect(result.class).to eql(Mysql2::Result)
         
     | 
| 
       539 
546 
     | 
    
         
             
                  end
         
     | 
| 
       540 
547 
     | 
    
         
             
                end
         
     | 
| 
       541 
548 
     | 
    
         | 
| 
         @@ -546,20 +553,20 @@ describe Mysql2::Client do 
     | 
|
| 
       546 
553 
     | 
    
         | 
| 
       547 
554 
     | 
    
         
             
                  it "should raise an exception when one of multiple statements fails" do
         
     | 
| 
       548 
555 
     | 
    
         
             
                    result = @multi_client.query("SELECT 1 AS 'set_1'; SELECT * FROM invalid_table_name; SELECT 2 AS 'set_2';")
         
     | 
| 
       549 
     | 
    
         
            -
                    result.first['set_1']. 
     | 
| 
       550 
     | 
    
         
            -
                     
     | 
| 
      
 556 
     | 
    
         
            +
                    expect(result.first['set_1']).to be(1)
         
     | 
| 
      
 557 
     | 
    
         
            +
                    expect {
         
     | 
| 
       551 
558 
     | 
    
         
             
                      @multi_client.next_result
         
     | 
| 
       552 
     | 
    
         
            -
                    }. 
     | 
| 
       553 
     | 
    
         
            -
                    @multi_client.next_result. 
     | 
| 
      
 559 
     | 
    
         
            +
                    }.to raise_error(Mysql2::Error)
         
     | 
| 
      
 560 
     | 
    
         
            +
                    expect(@multi_client.next_result).to be false
         
     | 
| 
       554 
561 
     | 
    
         
             
                  end
         
     | 
| 
       555 
562 
     | 
    
         | 
| 
       556 
563 
     | 
    
         
             
                  it "returns multiple result sets" do
         
     | 
| 
       557 
     | 
    
         
            -
                    @multi_client.query("SELECT 1 AS 'set_1'; SELECT 2 AS 'set_2'").first. 
     | 
| 
      
 564 
     | 
    
         
            +
                    expect(@multi_client.query("SELECT 1 AS 'set_1'; SELECT 2 AS 'set_2'").first).to eql({ 'set_1' => 1 })
         
     | 
| 
       558 
565 
     | 
    
         | 
| 
       559 
     | 
    
         
            -
                    @multi_client.next_result. 
     | 
| 
       560 
     | 
    
         
            -
                    @multi_client.store_result.first. 
     | 
| 
      
 566 
     | 
    
         
            +
                    expect(@multi_client.next_result).to be true
         
     | 
| 
      
 567 
     | 
    
         
            +
                    expect(@multi_client.store_result.first).to eql({ 'set_2' => 2 })
         
     | 
| 
       561 
568 
     | 
    
         | 
| 
       562 
     | 
    
         
            -
                    @multi_client.next_result. 
     | 
| 
      
 569 
     | 
    
         
            +
                    expect(@multi_client.next_result).to be false
         
     | 
| 
       563 
570 
     | 
    
         
             
                  end
         
     | 
| 
       564 
571 
     | 
    
         | 
| 
       565 
572 
     | 
    
         
             
                  it "does not interfere with other statements" do
         
     | 
| 
         @@ -568,133 +575,133 @@ describe Mysql2::Client do 
     | 
|
| 
       568 
575 
     | 
    
         
             
                      @multi_client.store_result
         
     | 
| 
       569 
576 
     | 
    
         
             
                    end
         
     | 
| 
       570 
577 
     | 
    
         | 
| 
       571 
     | 
    
         
            -
                    @multi_client.query("SELECT 3 AS 'next'").first. 
     | 
| 
      
 578 
     | 
    
         
            +
                    expect(@multi_client.query("SELECT 3 AS 'next'").first).to eq({ 'next' => 3 })
         
     | 
| 
       572 
579 
     | 
    
         
             
                  end
         
     | 
| 
       573 
580 
     | 
    
         | 
| 
       574 
581 
     | 
    
         
             
                  it "will raise on query if there are outstanding results to read" do
         
     | 
| 
       575 
582 
     | 
    
         
             
                    @multi_client.query("SELECT 1; SELECT 2; SELECT 3")
         
     | 
| 
       576 
     | 
    
         
            -
                     
     | 
| 
      
 583 
     | 
    
         
            +
                    expect {
         
     | 
| 
       577 
584 
     | 
    
         
             
                      @multi_client.query("SELECT 4")
         
     | 
| 
       578 
     | 
    
         
            -
                    }. 
     | 
| 
      
 585 
     | 
    
         
            +
                    }.to raise_error(Mysql2::Error)
         
     | 
| 
       579 
586 
     | 
    
         
             
                  end
         
     | 
| 
       580 
587 
     | 
    
         | 
| 
       581 
588 
     | 
    
         
             
                  it "#abandon_results! should work" do
         
     | 
| 
       582 
589 
     | 
    
         
             
                    @multi_client.query("SELECT 1; SELECT 2; SELECT 3")
         
     | 
| 
       583 
590 
     | 
    
         
             
                    @multi_client.abandon_results!
         
     | 
| 
       584 
     | 
    
         
            -
                     
     | 
| 
      
 591 
     | 
    
         
            +
                    expect {
         
     | 
| 
       585 
592 
     | 
    
         
             
                      @multi_client.query("SELECT 4")
         
     | 
| 
       586 
     | 
    
         
            -
                    }. 
     | 
| 
      
 593 
     | 
    
         
            +
                    }.not_to raise_error
         
     | 
| 
       587 
594 
     | 
    
         
             
                  end
         
     | 
| 
       588 
595 
     | 
    
         | 
| 
       589 
596 
     | 
    
         
             
                  it "#more_results? should work" do
         
     | 
| 
       590 
597 
     | 
    
         
             
                    @multi_client.query("SELECT 1 AS 'set_1'; SELECT 2 AS 'set_2'")
         
     | 
| 
       591 
     | 
    
         
            -
                    @multi_client.more_results 
     | 
| 
      
 598 
     | 
    
         
            +
                    expect(@multi_client.more_results?).to be true
         
     | 
| 
       592 
599 
     | 
    
         | 
| 
       593 
600 
     | 
    
         
             
                    @multi_client.next_result
         
     | 
| 
       594 
601 
     | 
    
         
             
                    @multi_client.store_result
         
     | 
| 
       595 
602 
     | 
    
         | 
| 
       596 
     | 
    
         
            -
                    @multi_client.more_results 
     | 
| 
      
 603 
     | 
    
         
            +
                    expect(@multi_client.more_results?).to be false
         
     | 
| 
       597 
604 
     | 
    
         
             
                  end
         
     | 
| 
       598 
605 
     | 
    
         | 
| 
       599 
606 
     | 
    
         
             
                  it "#more_results? should work with stored procedures" do
         
     | 
| 
       600 
607 
     | 
    
         
             
                    @multi_client.query("DROP PROCEDURE IF EXISTS test_proc")
         
     | 
| 
       601 
608 
     | 
    
         
             
                    @multi_client.query("CREATE PROCEDURE test_proc() BEGIN SELECT 1 AS 'set_1'; SELECT 2 AS 'set_2'; END")
         
     | 
| 
       602 
     | 
    
         
            -
                    @multi_client.query("CALL test_proc()").first. 
     | 
| 
       603 
     | 
    
         
            -
                    @multi_client.more_results 
     | 
| 
      
 609 
     | 
    
         
            +
                    expect(@multi_client.query("CALL test_proc()").first).to eql({ 'set_1' => 1 })
         
     | 
| 
      
 610 
     | 
    
         
            +
                    expect(@multi_client.more_results?).to be true
         
     | 
| 
       604 
611 
     | 
    
         | 
| 
       605 
612 
     | 
    
         
             
                    @multi_client.next_result
         
     | 
| 
       606 
     | 
    
         
            -
                    @multi_client.store_result.first. 
     | 
| 
      
 613 
     | 
    
         
            +
                    expect(@multi_client.store_result.first).to eql({ 'set_2' => 2 })
         
     | 
| 
       607 
614 
     | 
    
         | 
| 
       608 
615 
     | 
    
         
             
                    @multi_client.next_result
         
     | 
| 
       609 
     | 
    
         
            -
                    @multi_client.store_result. 
     | 
| 
      
 616 
     | 
    
         
            +
                    expect(@multi_client.store_result).to be_nil # this is the result from CALL itself
         
     | 
| 
       610 
617 
     | 
    
         | 
| 
       611 
     | 
    
         
            -
                    @multi_client.more_results 
     | 
| 
      
 618 
     | 
    
         
            +
                    expect(@multi_client.more_results?).to be false
         
     | 
| 
       612 
619 
     | 
    
         
             
                  end
         
     | 
| 
       613 
620 
     | 
    
         
             
                end
         
     | 
| 
       614 
621 
     | 
    
         
             
              end
         
     | 
| 
       615 
622 
     | 
    
         | 
| 
       616 
623 
     | 
    
         
             
              it "should respond to #socket" do
         
     | 
| 
       617 
     | 
    
         
            -
                @client. 
     | 
| 
      
 624 
     | 
    
         
            +
                expect(@client).to respond_to(:socket)
         
     | 
| 
       618 
625 
     | 
    
         
             
              end
         
     | 
| 
       619 
626 
     | 
    
         | 
| 
       620 
627 
     | 
    
         
             
              if RUBY_PLATFORM =~ /mingw|mswin/
         
     | 
| 
       621 
628 
     | 
    
         
             
                it "#socket should raise as it's not supported" do
         
     | 
| 
       622 
     | 
    
         
            -
                   
     | 
| 
      
 629 
     | 
    
         
            +
                  expect {
         
     | 
| 
       623 
630 
     | 
    
         
             
                    @client.socket
         
     | 
| 
       624 
     | 
    
         
            -
                  }. 
     | 
| 
      
 631 
     | 
    
         
            +
                  }.to raise_error(Mysql2::Error)
         
     | 
| 
       625 
632 
     | 
    
         
             
                end
         
     | 
| 
       626 
633 
     | 
    
         
             
              end
         
     | 
| 
       627 
634 
     | 
    
         | 
| 
       628 
635 
     | 
    
         
             
              it "should respond to escape" do
         
     | 
| 
       629 
     | 
    
         
            -
                Mysql2::Client. 
     | 
| 
      
 636 
     | 
    
         
            +
                expect(Mysql2::Client).to respond_to(:escape)
         
     | 
| 
       630 
637 
     | 
    
         
             
              end
         
     | 
| 
       631 
638 
     | 
    
         | 
| 
       632 
639 
     | 
    
         
             
              context "escape" do
         
     | 
| 
       633 
640 
     | 
    
         
             
                it "should return a new SQL-escape version of the passed string" do
         
     | 
| 
       634 
     | 
    
         
            -
                  Mysql2::Client.escape("abc'def\"ghi\0jkl%mno"). 
     | 
| 
      
 641 
     | 
    
         
            +
                  expect(Mysql2::Client.escape("abc'def\"ghi\0jkl%mno")).to eql("abc\\'def\\\"ghi\\0jkl%mno")
         
     | 
| 
       635 
642 
     | 
    
         
             
                end
         
     | 
| 
       636 
643 
     | 
    
         | 
| 
       637 
644 
     | 
    
         
             
                it "should return the passed string if nothing was escaped" do
         
     | 
| 
       638 
645 
     | 
    
         
             
                  str = "plain"
         
     | 
| 
       639 
     | 
    
         
            -
                  Mysql2::Client.escape(str).object_id. 
     | 
| 
      
 646 
     | 
    
         
            +
                  expect(Mysql2::Client.escape(str).object_id).to eql(str.object_id)
         
     | 
| 
       640 
647 
     | 
    
         
             
                end
         
     | 
| 
       641 
648 
     | 
    
         | 
| 
       642 
649 
     | 
    
         
             
                it "should not overflow the thread stack" do
         
     | 
| 
       643 
     | 
    
         
            -
                   
     | 
| 
      
 650 
     | 
    
         
            +
                  expect {
         
     | 
| 
       644 
651 
     | 
    
         
             
                    Thread.new { Mysql2::Client.escape("'" * 256 * 1024) }.join
         
     | 
| 
       645 
     | 
    
         
            -
                  }. 
     | 
| 
      
 652 
     | 
    
         
            +
                  }.not_to raise_error
         
     | 
| 
       646 
653 
     | 
    
         
             
                end
         
     | 
| 
       647 
654 
     | 
    
         | 
| 
       648 
655 
     | 
    
         
             
                it "should not overflow the process stack" do
         
     | 
| 
       649 
     | 
    
         
            -
                   
     | 
| 
      
 656 
     | 
    
         
            +
                  expect {
         
     | 
| 
       650 
657 
     | 
    
         
             
                    Thread.new { Mysql2::Client.escape("'" * 1024 * 1024 * 4) }.join
         
     | 
| 
       651 
     | 
    
         
            -
                  }. 
     | 
| 
      
 658 
     | 
    
         
            +
                  }.not_to raise_error
         
     | 
| 
       652 
659 
     | 
    
         
             
                end
         
     | 
| 
       653 
660 
     | 
    
         | 
| 
       654 
661 
     | 
    
         
             
                unless RUBY_VERSION =~ /1.8/
         
     | 
| 
       655 
662 
     | 
    
         
             
                  it "should carry over the original string's encoding" do
         
     | 
| 
       656 
663 
     | 
    
         
             
                    str = "abc'def\"ghi\0jkl%mno"
         
     | 
| 
       657 
664 
     | 
    
         
             
                    escaped = Mysql2::Client.escape(str)
         
     | 
| 
       658 
     | 
    
         
            -
                    escaped.encoding. 
     | 
| 
      
 665 
     | 
    
         
            +
                    expect(escaped.encoding).to eql(str.encoding)
         
     | 
| 
       659 
666 
     | 
    
         | 
| 
       660 
667 
     | 
    
         
             
                    str.encode!('us-ascii')
         
     | 
| 
       661 
668 
     | 
    
         
             
                    escaped = Mysql2::Client.escape(str)
         
     | 
| 
       662 
     | 
    
         
            -
                    escaped.encoding. 
     | 
| 
      
 669 
     | 
    
         
            +
                    expect(escaped.encoding).to eql(str.encoding)
         
     | 
| 
       663 
670 
     | 
    
         
             
                  end
         
     | 
| 
       664 
671 
     | 
    
         
             
                end
         
     | 
| 
       665 
672 
     | 
    
         
             
              end
         
     | 
| 
       666 
673 
     | 
    
         | 
| 
       667 
674 
     | 
    
         
             
              it "should respond to #escape" do
         
     | 
| 
       668 
     | 
    
         
            -
                @client. 
     | 
| 
      
 675 
     | 
    
         
            +
                expect(@client).to respond_to(:escape)
         
     | 
| 
       669 
676 
     | 
    
         
             
              end
         
     | 
| 
       670 
677 
     | 
    
         | 
| 
       671 
678 
     | 
    
         
             
              context "#escape" do
         
     | 
| 
       672 
679 
     | 
    
         
             
                it "should return a new SQL-escape version of the passed string" do
         
     | 
| 
       673 
     | 
    
         
            -
                  @client.escape("abc'def\"ghi\0jkl%mno"). 
     | 
| 
      
 680 
     | 
    
         
            +
                  expect(@client.escape("abc'def\"ghi\0jkl%mno")).to eql("abc\\'def\\\"ghi\\0jkl%mno")
         
     | 
| 
       674 
681 
     | 
    
         
             
                end
         
     | 
| 
       675 
682 
     | 
    
         | 
| 
       676 
683 
     | 
    
         
             
                it "should return the passed string if nothing was escaped" do
         
     | 
| 
       677 
684 
     | 
    
         
             
                  str = "plain"
         
     | 
| 
       678 
     | 
    
         
            -
                  @client.escape(str).object_id. 
     | 
| 
      
 685 
     | 
    
         
            +
                  expect(@client.escape(str).object_id).to eql(str.object_id)
         
     | 
| 
       679 
686 
     | 
    
         
             
                end
         
     | 
| 
       680 
687 
     | 
    
         | 
| 
       681 
688 
     | 
    
         
             
                it "should not overflow the thread stack" do
         
     | 
| 
       682 
     | 
    
         
            -
                   
     | 
| 
      
 689 
     | 
    
         
            +
                  expect {
         
     | 
| 
       683 
690 
     | 
    
         
             
                    Thread.new { @client.escape("'" * 256 * 1024) }.join
         
     | 
| 
       684 
     | 
    
         
            -
                  }. 
     | 
| 
      
 691 
     | 
    
         
            +
                  }.not_to raise_error
         
     | 
| 
       685 
692 
     | 
    
         
             
                end
         
     | 
| 
       686 
693 
     | 
    
         | 
| 
       687 
694 
     | 
    
         
             
                it "should not overflow the process stack" do
         
     | 
| 
       688 
     | 
    
         
            -
                   
     | 
| 
      
 695 
     | 
    
         
            +
                  expect {
         
     | 
| 
       689 
696 
     | 
    
         
             
                    Thread.new { @client.escape("'" * 1024 * 1024 * 4) }.join
         
     | 
| 
       690 
     | 
    
         
            -
                  }. 
     | 
| 
      
 697 
     | 
    
         
            +
                  }.not_to raise_error
         
     | 
| 
       691 
698 
     | 
    
         
             
                end
         
     | 
| 
       692 
699 
     | 
    
         | 
| 
       693 
700 
     | 
    
         
             
                it "should require an open connection" do
         
     | 
| 
       694 
701 
     | 
    
         
             
                  @client.close
         
     | 
| 
       695 
     | 
    
         
            -
                   
     | 
| 
      
 702 
     | 
    
         
            +
                  expect {
         
     | 
| 
       696 
703 
     | 
    
         
             
                    @client.escape ""
         
     | 
| 
       697 
     | 
    
         
            -
                  }. 
     | 
| 
      
 704 
     | 
    
         
            +
                  }.to raise_error(Mysql2::Error)
         
     | 
| 
       698 
705 
     | 
    
         
             
                end
         
     | 
| 
       699 
706 
     | 
    
         | 
| 
       700 
707 
     | 
    
         
             
                context 'when mysql encoding is not utf8' do
         
     | 
| 
         @@ -704,32 +711,32 @@ describe Mysql2::Client do 
     | 
|
| 
       704 
711 
     | 
    
         | 
| 
       705 
712 
     | 
    
         
             
                  it 'should return a internal encoding string if Encoding.default_internal is set' do
         
     | 
| 
       706 
713 
     | 
    
         
             
                    with_internal_encoding Encoding::UTF_8 do
         
     | 
| 
       707 
     | 
    
         
            -
                      client.escape("\u{30C6}\u{30B9}\u{30C8}"). 
     | 
| 
       708 
     | 
    
         
            -
                      client.escape("\u{30C6}'\u{30B9}\"\u{30C8}"). 
     | 
| 
      
 714 
     | 
    
         
            +
                      expect(client.escape("\u{30C6}\u{30B9}\u{30C8}")).to eq "\u{30C6}\u{30B9}\u{30C8}"
         
     | 
| 
      
 715 
     | 
    
         
            +
                      expect(client.escape("\u{30C6}'\u{30B9}\"\u{30C8}")).to eq "\u{30C6}\\'\u{30B9}\\\"\u{30C8}"
         
     | 
| 
       709 
716 
     | 
    
         
             
                    end
         
     | 
| 
       710 
717 
     | 
    
         
             
                  end
         
     | 
| 
       711 
718 
     | 
    
         
             
                end
         
     | 
| 
       712 
719 
     | 
    
         
             
              end
         
     | 
| 
       713 
720 
     | 
    
         | 
| 
       714 
721 
     | 
    
         
             
              it "should respond to #info" do
         
     | 
| 
       715 
     | 
    
         
            -
                @client. 
     | 
| 
      
 722 
     | 
    
         
            +
                expect(@client).to respond_to(:info)
         
     | 
| 
       716 
723 
     | 
    
         
             
              end
         
     | 
| 
       717 
724 
     | 
    
         | 
| 
       718 
725 
     | 
    
         
             
              it "#info should return a hash containing the client version ID and String" do
         
     | 
| 
       719 
726 
     | 
    
         
             
                info = @client.info
         
     | 
| 
       720 
     | 
    
         
            -
                info.class. 
     | 
| 
       721 
     | 
    
         
            -
                info. 
     | 
| 
       722 
     | 
    
         
            -
                info[:id].class. 
     | 
| 
       723 
     | 
    
         
            -
                info. 
     | 
| 
       724 
     | 
    
         
            -
                info[:version].class. 
     | 
| 
      
 727 
     | 
    
         
            +
                expect(info.class).to eql(Hash)
         
     | 
| 
      
 728 
     | 
    
         
            +
                expect(info).to have_key(:id)
         
     | 
| 
      
 729 
     | 
    
         
            +
                expect(info[:id].class).to eql(Fixnum)
         
     | 
| 
      
 730 
     | 
    
         
            +
                expect(info).to have_key(:version)
         
     | 
| 
      
 731 
     | 
    
         
            +
                expect(info[:version].class).to eql(String)
         
     | 
| 
       725 
732 
     | 
    
         
             
              end
         
     | 
| 
       726 
733 
     | 
    
         | 
| 
       727 
734 
     | 
    
         
             
              context "strings returned by #info" do
         
     | 
| 
       728 
735 
     | 
    
         
             
                before { pending('Encoding is undefined') unless defined?(Encoding) }
         
     | 
| 
       729 
736 
     | 
    
         | 
| 
       730 
737 
     | 
    
         
             
                it "should be tagged as ascii" do
         
     | 
| 
       731 
     | 
    
         
            -
                  @client.info[:version].encoding. 
     | 
| 
       732 
     | 
    
         
            -
                  @client.info[:header_version].encoding. 
     | 
| 
      
 738 
     | 
    
         
            +
                  expect(@client.info[:version].encoding).to eql(Encoding::US_ASCII)
         
     | 
| 
      
 739 
     | 
    
         
            +
                  expect(@client.info[:header_version].encoding).to eql(Encoding::US_ASCII)
         
     | 
| 
       733 
740 
     | 
    
         
             
                end
         
     | 
| 
       734 
741 
     | 
    
         
             
              end
         
     | 
| 
       735 
742 
     | 
    
         | 
| 
         @@ -737,62 +744,62 @@ describe Mysql2::Client do 
     | 
|
| 
       737 
744 
     | 
    
         
             
                before { pending('Encoding is undefined') unless defined?(Encoding) }
         
     | 
| 
       738 
745 
     | 
    
         | 
| 
       739 
746 
     | 
    
         
             
                it "should be tagged as ascii" do
         
     | 
| 
       740 
     | 
    
         
            -
                  Mysql2::Client.info[:version].encoding. 
     | 
| 
       741 
     | 
    
         
            -
                  Mysql2::Client.info[:header_version].encoding. 
     | 
| 
      
 747 
     | 
    
         
            +
                  expect(Mysql2::Client.info[:version].encoding).to eql(Encoding::US_ASCII)
         
     | 
| 
      
 748 
     | 
    
         
            +
                  expect(Mysql2::Client.info[:header_version].encoding).to eql(Encoding::US_ASCII)
         
     | 
| 
       742 
749 
     | 
    
         
             
                end
         
     | 
| 
       743 
750 
     | 
    
         
             
              end
         
     | 
| 
       744 
751 
     | 
    
         | 
| 
       745 
752 
     | 
    
         
             
              it "should respond to #server_info" do
         
     | 
| 
       746 
     | 
    
         
            -
                @client. 
     | 
| 
      
 753 
     | 
    
         
            +
                expect(@client).to respond_to(:server_info)
         
     | 
| 
       747 
754 
     | 
    
         
             
              end
         
     | 
| 
       748 
755 
     | 
    
         | 
| 
       749 
756 
     | 
    
         
             
              it "#server_info should return a hash containing the client version ID and String" do
         
     | 
| 
       750 
757 
     | 
    
         
             
                server_info = @client.server_info
         
     | 
| 
       751 
     | 
    
         
            -
                server_info.class. 
     | 
| 
       752 
     | 
    
         
            -
                server_info. 
     | 
| 
       753 
     | 
    
         
            -
                server_info[:id].class. 
     | 
| 
       754 
     | 
    
         
            -
                server_info. 
     | 
| 
       755 
     | 
    
         
            -
                server_info[:version].class. 
     | 
| 
      
 758 
     | 
    
         
            +
                expect(server_info.class).to eql(Hash)
         
     | 
| 
      
 759 
     | 
    
         
            +
                expect(server_info).to have_key(:id)
         
     | 
| 
      
 760 
     | 
    
         
            +
                expect(server_info[:id].class).to eql(Fixnum)
         
     | 
| 
      
 761 
     | 
    
         
            +
                expect(server_info).to have_key(:version)
         
     | 
| 
      
 762 
     | 
    
         
            +
                expect(server_info[:version].class).to eql(String)
         
     | 
| 
       756 
763 
     | 
    
         
             
              end
         
     | 
| 
       757 
764 
     | 
    
         | 
| 
       758 
765 
     | 
    
         
             
              it "#server_info should require an open connection" do
         
     | 
| 
       759 
766 
     | 
    
         
             
                @client.close
         
     | 
| 
       760 
     | 
    
         
            -
                 
     | 
| 
      
 767 
     | 
    
         
            +
                expect {
         
     | 
| 
       761 
768 
     | 
    
         
             
                  @client.server_info
         
     | 
| 
       762 
     | 
    
         
            -
                }. 
     | 
| 
      
 769 
     | 
    
         
            +
                }.to raise_error(Mysql2::Error)
         
     | 
| 
       763 
770 
     | 
    
         
             
              end
         
     | 
| 
       764 
771 
     | 
    
         | 
| 
       765 
     | 
    
         
            -
               
     | 
| 
       766 
     | 
    
         
            -
                 
     | 
| 
       767 
     | 
    
         
            -
                  it "should default to the connection's encoding if Encoding.default_internal is nil" do
         
     | 
| 
       768 
     | 
    
         
            -
                    with_internal_encoding nil do
         
     | 
| 
       769 
     | 
    
         
            -
                      @client.server_info[:version].encoding.should eql(Encoding.find('utf-8'))
         
     | 
| 
      
 772 
     | 
    
         
            +
              context "strings returned by #server_info" do
         
     | 
| 
      
 773 
     | 
    
         
            +
                before { pending('Encoding is undefined') unless defined?(Encoding) }
         
     | 
| 
       770 
774 
     | 
    
         | 
| 
       771 
     | 
    
         
            -
             
     | 
| 
       772 
     | 
    
         
            -
             
     | 
| 
       773 
     | 
    
         
            -
                     
     | 
| 
      
 775 
     | 
    
         
            +
                it "should default to the connection's encoding if Encoding.default_internal is nil" do
         
     | 
| 
      
 776 
     | 
    
         
            +
                  with_internal_encoding nil do
         
     | 
| 
      
 777 
     | 
    
         
            +
                    expect(@client.server_info[:version].encoding).to eql(Encoding::UTF_8)
         
     | 
| 
      
 778 
     | 
    
         
            +
             
     | 
| 
      
 779 
     | 
    
         
            +
                    client2 = Mysql2::Client.new(DatabaseCredentials['root'].merge(:encoding => 'ascii'))
         
     | 
| 
      
 780 
     | 
    
         
            +
                    expect(client2.server_info[:version].encoding).to eql(Encoding::ASCII)
         
     | 
| 
       774 
781 
     | 
    
         
             
                  end
         
     | 
| 
      
 782 
     | 
    
         
            +
                end
         
     | 
| 
       775 
783 
     | 
    
         | 
| 
       776 
     | 
    
         
            -
             
     | 
| 
       777 
     | 
    
         
            -
             
     | 
| 
       778 
     | 
    
         
            -
             
     | 
| 
       779 
     | 
    
         
            -
             
     | 
| 
      
 784 
     | 
    
         
            +
                it "should use Encoding.default_internal" do
         
     | 
| 
      
 785 
     | 
    
         
            +
                  with_internal_encoding Encoding::UTF_8 do
         
     | 
| 
      
 786 
     | 
    
         
            +
                    expect(@client.server_info[:version].encoding).to eql(Encoding.default_internal)
         
     | 
| 
      
 787 
     | 
    
         
            +
                  end
         
     | 
| 
       780 
788 
     | 
    
         | 
| 
       781 
     | 
    
         
            -
             
     | 
| 
       782 
     | 
    
         
            -
             
     | 
| 
       783 
     | 
    
         
            -
                    end
         
     | 
| 
      
 789 
     | 
    
         
            +
                  with_internal_encoding Encoding::ASCII do
         
     | 
| 
      
 790 
     | 
    
         
            +
                    expect(@client.server_info[:version].encoding).to eql(Encoding.default_internal)
         
     | 
| 
       784 
791 
     | 
    
         
             
                  end
         
     | 
| 
       785 
792 
     | 
    
         
             
                end
         
     | 
| 
       786 
793 
     | 
    
         
             
              end
         
     | 
| 
       787 
794 
     | 
    
         | 
| 
       788 
795 
     | 
    
         
             
              it "should raise a Mysql2::Error exception upon connection failure" do
         
     | 
| 
       789 
     | 
    
         
            -
                 
     | 
| 
      
 796 
     | 
    
         
            +
                expect {
         
     | 
| 
       790 
797 
     | 
    
         
             
                  Mysql2::Client.new :host => "localhost", :username => 'asdfasdf8d2h', :password => 'asdfasdfw42'
         
     | 
| 
       791 
     | 
    
         
            -
                }. 
     | 
| 
      
 798 
     | 
    
         
            +
                }.to raise_error(Mysql2::Error)
         
     | 
| 
       792 
799 
     | 
    
         | 
| 
       793 
     | 
    
         
            -
                 
     | 
| 
      
 800 
     | 
    
         
            +
                expect {
         
     | 
| 
       794 
801 
     | 
    
         
             
                  Mysql2::Client.new DatabaseCredentials['root']
         
     | 
| 
       795 
     | 
    
         
            -
                }. 
     | 
| 
      
 802 
     | 
    
         
            +
                }.not_to raise_error
         
     | 
| 
       796 
803 
     | 
    
         
             
              end
         
     | 
| 
       797 
804 
     | 
    
         | 
| 
       798 
805 
     | 
    
         
             
              context 'write operations api' do
         
     | 
| 
         @@ -806,46 +813,46 @@ describe Mysql2::Client do 
     | 
|
| 
       806 
813 
     | 
    
         
             
                end
         
     | 
| 
       807 
814 
     | 
    
         | 
| 
       808 
815 
     | 
    
         
             
                it "should respond to #last_id" do
         
     | 
| 
       809 
     | 
    
         
            -
                  @client. 
     | 
| 
      
 816 
     | 
    
         
            +
                  expect(@client).to respond_to(:last_id)
         
     | 
| 
       810 
817 
     | 
    
         
             
                end
         
     | 
| 
       811 
818 
     | 
    
         | 
| 
       812 
819 
     | 
    
         
             
                it "#last_id should return a Fixnum, the from the last INSERT/UPDATE" do
         
     | 
| 
       813 
     | 
    
         
            -
                  @client.last_id. 
     | 
| 
      
 820 
     | 
    
         
            +
                  expect(@client.last_id).to eql(0)
         
     | 
| 
       814 
821 
     | 
    
         
             
                  @client.query "INSERT INTO lastIdTest (blah) VALUES (1234)"
         
     | 
| 
       815 
     | 
    
         
            -
                  @client.last_id. 
     | 
| 
      
 822 
     | 
    
         
            +
                  expect(@client.last_id).to eql(1)
         
     | 
| 
       816 
823 
     | 
    
         
             
                end
         
     | 
| 
       817 
824 
     | 
    
         | 
| 
       818 
825 
     | 
    
         
             
                it "should respond to #last_id" do
         
     | 
| 
       819 
     | 
    
         
            -
                  @client. 
     | 
| 
      
 826 
     | 
    
         
            +
                  expect(@client).to respond_to(:last_id)
         
     | 
| 
       820 
827 
     | 
    
         
             
                end
         
     | 
| 
       821 
828 
     | 
    
         | 
| 
       822 
829 
     | 
    
         
             
                it "#last_id should return a Fixnum, the from the last INSERT/UPDATE" do
         
     | 
| 
       823 
830 
     | 
    
         
             
                  @client.query "INSERT INTO lastIdTest (blah) VALUES (1234)"
         
     | 
| 
       824 
     | 
    
         
            -
                  @client.affected_rows. 
     | 
| 
      
 831 
     | 
    
         
            +
                  expect(@client.affected_rows).to eql(1)
         
     | 
| 
       825 
832 
     | 
    
         
             
                  @client.query "UPDATE lastIdTest SET blah=4321 WHERE id=1"
         
     | 
| 
       826 
     | 
    
         
            -
                  @client.affected_rows. 
     | 
| 
      
 833 
     | 
    
         
            +
                  expect(@client.affected_rows).to eql(1)
         
     | 
| 
       827 
834 
     | 
    
         
             
                end
         
     | 
| 
       828 
835 
     | 
    
         | 
| 
       829 
836 
     | 
    
         
             
                it "#last_id should handle BIGINT auto-increment ids above 32 bits" do
         
     | 
| 
       830 
837 
     | 
    
         
             
                  # The id column type must be BIGINT. Surprise: INT(x) is limited to 32-bits for all values of x.
         
     | 
| 
       831 
838 
     | 
    
         
             
                  # Insert a row with a given ID, this should raise the auto-increment state
         
     | 
| 
       832 
839 
     | 
    
         
             
                  @client.query "INSERT INTO lastIdTest (id, blah) VALUES (5000000000, 5000)"
         
     | 
| 
       833 
     | 
    
         
            -
                  @client.last_id. 
     | 
| 
      
 840 
     | 
    
         
            +
                  expect(@client.last_id).to eql(5000000000)
         
     | 
| 
       834 
841 
     | 
    
         
             
                  @client.query "INSERT INTO lastIdTest (blah) VALUES (5001)"
         
     | 
| 
       835 
     | 
    
         
            -
                  @client.last_id. 
     | 
| 
      
 842 
     | 
    
         
            +
                  expect(@client.last_id).to eql(5000000001)
         
     | 
| 
       836 
843 
     | 
    
         
             
                end
         
     | 
| 
       837 
844 
     | 
    
         
             
              end
         
     | 
| 
       838 
845 
     | 
    
         | 
| 
       839 
846 
     | 
    
         
             
              it "should respond to #thread_id" do
         
     | 
| 
       840 
     | 
    
         
            -
                @client. 
     | 
| 
      
 847 
     | 
    
         
            +
                expect(@client).to respond_to(:thread_id)
         
     | 
| 
       841 
848 
     | 
    
         
             
              end
         
     | 
| 
       842 
849 
     | 
    
         | 
| 
       843 
850 
     | 
    
         
             
              it "#thread_id should be a Fixnum" do
         
     | 
| 
       844 
     | 
    
         
            -
                @client.thread_id.class. 
     | 
| 
      
 851 
     | 
    
         
            +
                expect(@client.thread_id.class).to eql(Fixnum)
         
     | 
| 
       845 
852 
     | 
    
         
             
              end
         
     | 
| 
       846 
853 
     | 
    
         | 
| 
       847 
854 
     | 
    
         
             
              it "should respond to #ping" do
         
     | 
| 
       848 
     | 
    
         
            -
                @client. 
     | 
| 
      
 855 
     | 
    
         
            +
                expect(@client).to respond_to(:ping)
         
     | 
| 
       849 
856 
     | 
    
         
             
              end
         
     | 
| 
       850 
857 
     | 
    
         | 
| 
       851 
858 
     | 
    
         
             
              context "select_db" do
         
     | 
| 
         @@ -864,38 +871,38 @@ describe Mysql2::Client do 
     | 
|
| 
       864 
871 
     | 
    
         
             
                end
         
     | 
| 
       865 
872 
     | 
    
         | 
| 
       866 
873 
     | 
    
         
             
                it "should respond to #select_db" do
         
     | 
| 
       867 
     | 
    
         
            -
                  @client. 
     | 
| 
      
 874 
     | 
    
         
            +
                  expect(@client).to respond_to(:select_db)
         
     | 
| 
       868 
875 
     | 
    
         
             
                end
         
     | 
| 
       869 
876 
     | 
    
         | 
| 
       870 
877 
     | 
    
         
             
                it "should switch databases" do
         
     | 
| 
       871 
878 
     | 
    
         
             
                  @client.select_db("test_selectdb_0")
         
     | 
| 
       872 
     | 
    
         
            -
                  @client.query("SHOW TABLES").first.values.first. 
     | 
| 
      
 879 
     | 
    
         
            +
                  expect(@client.query("SHOW TABLES").first.values.first).to eql("test0")
         
     | 
| 
       873 
880 
     | 
    
         
             
                  @client.select_db("test_selectdb_1")
         
     | 
| 
       874 
     | 
    
         
            -
                  @client.query("SHOW TABLES").first.values.first. 
     | 
| 
      
 881 
     | 
    
         
            +
                  expect(@client.query("SHOW TABLES").first.values.first).to eql("test1")
         
     | 
| 
       875 
882 
     | 
    
         
             
                  @client.select_db("test_selectdb_0")
         
     | 
| 
       876 
     | 
    
         
            -
                  @client.query("SHOW TABLES").first.values.first. 
     | 
| 
      
 883 
     | 
    
         
            +
                  expect(@client.query("SHOW TABLES").first.values.first).to eql("test0")
         
     | 
| 
       877 
884 
     | 
    
         
             
                end
         
     | 
| 
       878 
885 
     | 
    
         | 
| 
       879 
886 
     | 
    
         
             
                it "should raise a Mysql2::Error when the database doesn't exist" do
         
     | 
| 
       880 
     | 
    
         
            -
                   
     | 
| 
      
 887 
     | 
    
         
            +
                  expect {
         
     | 
| 
       881 
888 
     | 
    
         
             
                    @client.select_db("nopenothere")
         
     | 
| 
       882 
     | 
    
         
            -
                  }. 
     | 
| 
      
 889 
     | 
    
         
            +
                  }.to raise_error(Mysql2::Error)
         
     | 
| 
       883 
890 
     | 
    
         
             
                end
         
     | 
| 
       884 
891 
     | 
    
         | 
| 
       885 
892 
     | 
    
         
             
                it "should return the database switched to" do
         
     | 
| 
       886 
     | 
    
         
            -
                  @client.select_db("test_selectdb_1"). 
     | 
| 
      
 893 
     | 
    
         
            +
                  expect(@client.select_db("test_selectdb_1")).to eq("test_selectdb_1")
         
     | 
| 
       887 
894 
     | 
    
         
             
                end
         
     | 
| 
       888 
895 
     | 
    
         
             
              end
         
     | 
| 
       889 
896 
     | 
    
         | 
| 
       890 
897 
     | 
    
         
             
              it "#thread_id should return a boolean" do
         
     | 
| 
       891 
     | 
    
         
            -
                @client.ping. 
     | 
| 
      
 898 
     | 
    
         
            +
                expect(@client.ping).to eql(true)
         
     | 
| 
       892 
899 
     | 
    
         
             
                @client.close
         
     | 
| 
       893 
     | 
    
         
            -
                @client.ping. 
     | 
| 
      
 900 
     | 
    
         
            +
                expect(@client.ping).to eql(false)
         
     | 
| 
       894 
901 
     | 
    
         
             
              end
         
     | 
| 
       895 
902 
     | 
    
         | 
| 
       896 
903 
     | 
    
         
             
              unless RUBY_VERSION =~ /1.8/
         
     | 
| 
       897 
904 
     | 
    
         
             
                it "should respond to #encoding" do
         
     | 
| 
       898 
     | 
    
         
            -
                  @client. 
     | 
| 
      
 905 
     | 
    
         
            +
                  expect(@client).to respond_to(:encoding)
         
     | 
| 
       899 
906 
     | 
    
         
             
                end
         
     | 
| 
       900 
907 
     | 
    
         
             
              end
         
     | 
| 
       901 
908 
     | 
    
         
             
            end
         
     |