mysql2 0.2.6 → 0.2.7

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.
@@ -33,8 +33,8 @@ void init_mysql2_client();
33
33
 
34
34
  typedef struct {
35
35
  VALUE encoding;
36
- short int active;
37
- short int closed;
36
+ char active;
37
+ char closed;
38
38
  MYSQL *client;
39
39
  } mysql_client_wrapper;
40
40
 
@@ -31,7 +31,10 @@ elsif mc = (with_config('mysql-config') || Dir[GLOB].first) then
31
31
  mc = Dir[GLOB].first if mc == true
32
32
  cflags = `#{mc} --cflags`.chomp
33
33
  exit 1 if $? != 0
34
- libs = `#{mc} --libs`.chomp
34
+ libs = `#{mc} --libs_r`.chomp
35
+ if libs.empty?
36
+ libs = `#{mc} --libs`.chomp
37
+ end
35
38
  exit 1 if $? != 0
36
39
  $CPPFLAGS += ' ' + cflags
37
40
  $libs = libs + " " + $libs
@@ -62,4 +65,8 @@ unless RUBY_PLATFORM =~ /mswin/ or RUBY_PLATFORM =~ /sparc/
62
65
  end
63
66
  # $CFLAGS << ' -O0 -ggdb3 -Wextra'
64
67
 
68
+ if hard_mysql_path = $libs[%r{-L(/[^ ]+)}, 1]
69
+ $LDFLAGS << " -Wl,-rpath,#{hard_mysql_path}"
70
+ end
71
+
65
72
  create_makefile('mysql2/mysql2')
@@ -1,9 +1,19 @@
1
1
  #ifndef MYSQL2_EXT
2
2
  #define MYSQL2_EXT
3
3
 
4
+ // tell rbx not to use it's caching compat layer
5
+ // by doing this we're making a promize to RBX that
6
+ // we'll never modify the pointers we get back from RSTRING_PTR
7
+ #define RSTRING_NOT_MODIFIED
4
8
  #include <ruby.h>
5
9
  #include <fcntl.h>
6
10
 
11
+ #ifndef HAVE_UINT
12
+ #define HAVE_UINT
13
+ typedef unsigned short ushort;
14
+ typedef unsigned int uint;
15
+ #endif
16
+
7
17
  #ifdef HAVE_MYSQL_H
8
18
  #include <mysql.h>
9
19
  #include <mysql_com.h>
@@ -1,17 +1,27 @@
1
1
  #include <mysql2_ext.h>
2
2
 
3
3
  #ifdef HAVE_RUBY_ENCODING_H
4
- rb_encoding *binaryEncoding;
4
+ static rb_encoding *binaryEncoding;
5
5
  #endif
6
6
 
7
- VALUE cMysql2Result;
8
- VALUE cBigDecimal, cDate, cDateTime;
9
- VALUE opt_decimal_zero, opt_float_zero, opt_time_year, opt_time_month, opt_utc_offset;
7
+ #define MYSQL2_MAX_YEAR 2058
8
+
9
+ #ifdef NEGATIVE_TIME_T
10
+ /* 1901-12-13 20:45:52 UTC : The oldest time in 32-bit signed time_t. */
11
+ #define MYSQL2_MIN_YEAR 1902
12
+ #else
13
+ /* 1970-01-01 00:00:00 UTC : The Unix epoch - the oldest time in portable time_t. */
14
+ #define MYSQL2_MIN_YEAR 1970
15
+ #endif
16
+
17
+ static VALUE cMysql2Result;
18
+ static VALUE cBigDecimal, cDate, cDateTime;
19
+ static VALUE opt_decimal_zero, opt_float_zero, opt_time_year, opt_time_month, opt_utc_offset;
10
20
  extern VALUE mMysql2, cMysql2Client, cMysql2Error;
11
21
  static VALUE intern_encoding_from_charset;
12
22
  static ID intern_new, intern_utc, intern_local, intern_encoding_from_charset_code,
13
23
  intern_localtime, intern_local_offset, intern_civil, intern_new_offset;
14
- static ID sym_symbolize_keys, sym_as, sym_array, sym_database_timezone, sym_application_timezone,
24
+ static VALUE sym_symbolize_keys, sym_as, sym_array, sym_database_timezone, sym_application_timezone,
15
25
  sym_local, sym_utc, sym_cast_booleans, sym_cache_rows;
16
26
  static ID intern_merge;
17
27
 
@@ -53,7 +63,7 @@ static VALUE nogvl_fetch_row(void *ptr) {
53
63
 
54
64
  static VALUE rb_mysql_result_fetch_field(VALUE self, unsigned int idx, short int symbolize_keys) {
55
65
  mysql2_result_wrapper * wrapper;
56
-
66
+ VALUE rb_field;
57
67
  GetMysql2Result(self, wrapper);
58
68
 
59
69
  if (wrapper->fields == Qnil) {
@@ -61,7 +71,7 @@ static VALUE rb_mysql_result_fetch_field(VALUE self, unsigned int idx, short int
61
71
  wrapper->fields = rb_ary_new2(wrapper->numberOfFields);
62
72
  }
63
73
 
64
- VALUE rb_field = rb_ary_entry(wrapper->fields, idx);
74
+ rb_field = rb_ary_entry(wrapper->fields, idx);
65
75
  if (rb_field == Qnil) {
66
76
  MYSQL_FIELD *field = NULL;
67
77
  #ifdef HAVE_RUBY_ENCODING_H
@@ -98,12 +108,15 @@ static VALUE rb_mysql_result_fetch_row(VALUE self, ID db_timezone, ID app_timezo
98
108
  unsigned int i = 0;
99
109
  unsigned long * fieldLengths;
100
110
  void * ptr;
101
-
111
+ #ifdef HAVE_RUBY_ENCODING_H
112
+ rb_encoding *default_internal_enc;
113
+ rb_encoding *conn_enc;
114
+ #endif
102
115
  GetMysql2Result(self, wrapper);
103
116
 
104
117
  #ifdef HAVE_RUBY_ENCODING_H
105
- rb_encoding *default_internal_enc = rb_default_internal_encoding();
106
- rb_encoding *conn_enc = rb_to_encoding(wrapper->encoding);
118
+ default_internal_enc = rb_default_internal_encoding();
119
+ conn_enc = rb_to_encoding(wrapper->encoding);
107
120
  #endif
108
121
 
109
122
  ptr = wrapper->result;
@@ -190,7 +203,7 @@ static VALUE rb_mysql_result_fetch_row(VALUE self, ID db_timezone, ID app_timezo
190
203
  rb_raise(cMysql2Error, "Invalid date: %s", row[i]);
191
204
  val = Qnil;
192
205
  } else {
193
- if (year < 1902 || year+month+day > 2058) { // use DateTime instead
206
+ if (year < MYSQL2_MIN_YEAR || year+month+day > MYSQL2_MAX_YEAR) { // use DateTime instead
194
207
  VALUE offset = INT2NUM(0);
195
208
  if (db_timezone == intern_local) {
196
209
  offset = rb_funcall(cMysql2Client, intern_local_offset, 0);
@@ -248,7 +261,7 @@ static VALUE rb_mysql_result_fetch_row(VALUE self, ID db_timezone, ID app_timezo
248
261
  val = rb_str_new(row[i], fieldLengths[i]);
249
262
  #ifdef HAVE_RUBY_ENCODING_H
250
263
  // if binary flag is set, respect it's wishes
251
- if (fields[i].flags & BINARY_FLAG) {
264
+ if (fields[i].flags & BINARY_FLAG && fields[i].charsetnr == 63) {
252
265
  rb_enc_associate(val, binaryEncoding);
253
266
  } else {
254
267
  // lookup the encoding configured on this field
@@ -8,10 +8,10 @@ typedef struct {
8
8
  VALUE fields;
9
9
  VALUE rows;
10
10
  VALUE encoding;
11
- long numberOfFields;
11
+ unsigned int numberOfFields;
12
12
  unsigned long numberOfRows;
13
13
  unsigned long lastRowProcessed;
14
- short int resultFreed;
14
+ char resultFreed;
15
15
  MYSQL_RES *result;
16
16
  } mysql2_result_wrapper;
17
17
 
@@ -15,8 +15,8 @@ module ActiveRecord
15
15
  end
16
16
 
17
17
  require 'fiber'
18
- require 'eventmachine' unless defined? EventMachine
19
- require 'mysql2' unless defined? Mysql2
18
+ require 'eventmachine'
19
+ require 'mysql2'
20
20
  require 'active_record/connection_adapters/mysql2_adapter'
21
21
  require 'active_record/fiber_patches'
22
22
 
@@ -35,25 +35,26 @@ module Mysql2
35
35
  results = @client.async_result
36
36
  @deferable.succeed(results)
37
37
  rescue Exception => e
38
- puts e.backtrace.join("\n\t")
39
38
  @deferable.fail(e)
40
39
  end
41
40
  end
42
41
  end
43
42
 
44
43
  def query(sql, opts={})
45
- if EM.reactor_running?
44
+ if ::EM.reactor_running?
46
45
  super(sql, opts.merge(:async => true))
47
- deferable = ::EM::DefaultDeferrable.new
48
- ::EM.watch(self.socket, Watcher, self, deferable).notify_readable = true
46
+ deferrable = ::EM::DefaultDeferrable.new
47
+ ::EM.watch(self.socket, Watcher, self, deferrable).notify_readable = true
49
48
  fiber = Fiber.current
50
- deferable.callback do |result|
49
+ deferrable.callback do |result|
51
50
  fiber.resume(result)
52
51
  end
53
- deferable.errback do |err|
52
+ deferrable.errback do |err|
54
53
  fiber.resume(err)
55
54
  end
56
- Fiber.yield
55
+ Fiber.yield.tap do |result|
56
+ raise result if result.is_a?(Exception)
57
+ end
57
58
  else
58
59
  super(sql, opts)
59
60
  end
@@ -1,6 +1,6 @@
1
1
  # encoding: utf-8
2
2
 
3
- require 'mysql2' unless defined? Mysql2
3
+ require 'mysql2'
4
4
 
5
5
  module ActiveRecord
6
6
  class Base
@@ -18,6 +18,9 @@ module ActiveRecord
18
18
  end
19
19
 
20
20
  module ConnectionAdapters
21
+ class Mysql2IndexDefinition < Struct.new(:table, :name, :unique, :columns, :lengths) #:nodoc:
22
+ end
23
+
21
24
  class Mysql2Column < Column
22
25
  BOOL = "tinyint(1)"
23
26
  def extract_default(default)
@@ -239,10 +242,7 @@ module ActiveRecord
239
242
 
240
243
  def active?
241
244
  return false unless @connection
242
- @connection.query 'select 1'
243
- true
244
- rescue Mysql2::Error
245
- false
245
+ @connection.ping
246
246
  end
247
247
 
248
248
  def reconnect!
@@ -447,7 +447,7 @@ module ActiveRecord
447
447
  if current_index != row[:Key_name]
448
448
  next if row[:Key_name] == PRIMARY # skip the primary key
449
449
  current_index = row[:Key_name]
450
- indexes << IndexDefinition.new(row[:Table], row[:Key_name], row[:Non_unique] == 0, [], [])
450
+ indexes << Mysql2IndexDefinition.new(row[:Table], row[:Key_name], row[:Non_unique] == 0, [], [])
451
451
  end
452
452
 
453
453
  indexes.last.columns << row[:Column_name]
@@ -623,7 +623,7 @@ module ActiveRecord
623
623
 
624
624
  # increase timeout so mysql server doesn't disconnect us
625
625
  wait_timeout = @config[:wait_timeout]
626
- wait_timeout = 2592000 unless wait_timeout.is_a?(Fixnum)
626
+ wait_timeout = 2147483 unless wait_timeout.is_a?(Fixnum)
627
627
  variable_assignments << "@@wait_timeout = #{wait_timeout}"
628
628
 
629
629
  execute("SET #{variable_assignments.join(', ')}", :skip_logging)
@@ -24,7 +24,7 @@ module ActiveRecord
24
24
  fiber.resume(false)
25
25
  end
26
26
  @queue << fiber
27
- returning Fiber.yield do
27
+ Fiber.yield.tap do
28
28
  x.cancel
29
29
  end
30
30
  end
@@ -69,14 +69,8 @@ module ActiveRecord
69
69
  @checked_out = []
70
70
  end
71
71
 
72
- private
73
-
74
- def current_connection_id #:nodoc:
75
- Fiber.current.object_id
76
- end
77
-
78
- # Remove stale fibers from the cache.
79
- def remove_stale_cached_threads!(cache, &block)
72
+ def clear_stale_cached_connections!
73
+ cache = @reserved_connections
80
74
  keys = Set.new(cache.keys)
81
75
 
82
76
  ActiveRecord::ConnectionAdapters.fiber_pools.each do |pool|
@@ -87,11 +81,17 @@ module ActiveRecord
87
81
 
88
82
  keys.each do |key|
89
83
  next unless cache.has_key?(key)
90
- block.call(key, cache[key])
84
+ checkin cache[key]
91
85
  cache.delete(key)
92
86
  end
93
87
  end
94
88
 
89
+ private
90
+
91
+ def current_connection_id #:nodoc:
92
+ Fiber.current.object_id
93
+ end
94
+
95
95
  def checkout_and_verify(c)
96
96
  @checked_out << c
97
97
  c.run_callbacks :checkout
@@ -3,6 +3,7 @@ require 'date'
3
3
  require 'bigdecimal'
4
4
  require 'rational' unless RUBY_VERSION >= '1.9.2'
5
5
 
6
+ require 'mysql2/version' unless defined? Mysql2::VERSION
6
7
  require 'mysql2/error'
7
8
  require 'mysql2/mysql2'
8
9
  require 'mysql2/client'
@@ -12,5 +13,4 @@ require 'mysql2/result'
12
13
  #
13
14
  # A modern, simple and very fast Mysql library for Ruby - binding to libmysql
14
15
  module Mysql2
15
- VERSION = "0.2.6"
16
16
  end
@@ -24,6 +24,11 @@ module Mysql2
24
24
  # force the encoding to utf8
25
25
  self.charset_name = opts[:encoding] || 'utf8'
26
26
 
27
+ @read_timeout = opts[:read_timeout]
28
+ if @read_timeout and @read_timeout < 0
29
+ raise Mysql2::Error, "read_timeout must be a positive integer, you passed #{@read_timeout}"
30
+ end
31
+
27
32
  ssl_set(*opts.values_at(:sslkey, :sslcert, :sslca, :sslcapath, :sslciper))
28
33
 
29
34
  user = opts[:username]
@@ -1,7 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
- require 'eventmachine' unless defined? EventMachine
4
- require 'mysql2' unless defined? Mysql2
3
+ require 'eventmachine'
4
+ require 'mysql2'
5
5
 
6
6
  module Mysql2
7
7
  module EM
@@ -23,10 +23,14 @@ module Mysql2
23
23
  end
24
24
 
25
25
  def query(sql, opts={})
26
- super(sql, opts.merge(:async => true))
27
- deferable = ::EM::DefaultDeferrable.new
28
- ::EM.watch(self.socket, Watcher, self, deferable).notify_readable = true
29
- deferable
26
+ if ::EM.reactor_running?
27
+ super(sql, opts.merge(:async => true))
28
+ deferable = ::EM::DefaultDeferrable.new
29
+ ::EM.watch(self.socket, Watcher, self, deferable).notify_readable = true
30
+ deferable
31
+ else
32
+ super(sql, opts)
33
+ end
30
34
  end
31
35
  end
32
36
  end
@@ -0,0 +1,31 @@
1
+ # encoding: utf-8
2
+
3
+ require 'mysql2/em'
4
+ require 'fiber'
5
+
6
+ module Mysql2
7
+ module EM
8
+ module Fiber
9
+ class Client < ::Mysql2::EM::Client
10
+ def query(sql, opts={})
11
+ if ::EM.reactor_running?
12
+ deferable = super(sql, opts)
13
+
14
+ fiber = ::Fiber.current
15
+ deferable.callback do |result|
16
+ fiber.resume(result)
17
+ end
18
+ deferable.errback do |err|
19
+ fiber.resume(err)
20
+ end
21
+ ::Fiber.yield.tap do |result|
22
+ raise result if result.is_a?(::Exception)
23
+ end
24
+ else
25
+ super(sql, opts)
26
+ end
27
+ end
28
+ end
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,3 @@
1
+ module Mysql2
2
+ VERSION = "0.2.7"
3
+ end
@@ -1,89 +1,32 @@
1
- # Generated by jeweler
2
- # DO NOT EDIT THIS FILE DIRECTLY
3
- # Instead, edit Jeweler::Tasks in Rakefile, and run the gemspec command
4
- # -*- encoding: utf-8 -*-
1
+ require File.expand_path('../lib/mysql2/version', __FILE__)
5
2
 
6
3
  Gem::Specification.new do |s|
7
4
  s.name = %q{mysql2}
8
- s.version = "0.2.6"
9
-
10
- s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
5
+ s.version = Mysql2::VERSION
11
6
  s.authors = ["Brian Lopez"]
12
- s.date = %q{2010-10-19}
7
+ s.date = Time.now.utc.strftime("%Y-%m-%d")
13
8
  s.email = %q{seniorlopez@gmail.com}
14
9
  s.extensions = ["ext/mysql2/extconf.rb"]
15
10
  s.extra_rdoc_files = [
16
11
  "README.rdoc"
17
12
  ]
18
- s.files = [
19
- ".gitignore",
20
- ".rspec",
21
- "CHANGELOG.md",
22
- "MIT-LICENSE",
23
- "README.rdoc",
24
- "Rakefile",
25
- "VERSION",
26
- "benchmark/active_record.rb",
27
- "benchmark/allocations.rb",
28
- "benchmark/escape.rb",
29
- "benchmark/query_with_mysql_casting.rb",
30
- "benchmark/query_without_mysql_casting.rb",
31
- "benchmark/sequel.rb",
32
- "benchmark/setup_db.rb",
33
- "examples/eventmachine.rb",
34
- "examples/threaded.rb",
35
- "ext/mysql2/client.c",
36
- "ext/mysql2/client.h",
37
- "ext/mysql2/extconf.rb",
38
- "ext/mysql2/mysql2_ext.c",
39
- "ext/mysql2/mysql2_ext.h",
40
- "ext/mysql2/result.c",
41
- "ext/mysql2/result.h",
42
- "lib/active_record/connection_adapters/em_mysql2_adapter.rb",
43
- "lib/active_record/connection_adapters/mysql2_adapter.rb",
44
- "lib/active_record/fiber_patches.rb",
45
- "lib/arel/engines/sql/compilers/mysql2_compiler.rb",
46
- "lib/mysql2.rb",
47
- "lib/mysql2/client.rb",
48
- "lib/mysql2/em.rb",
49
- "lib/mysql2/error.rb",
50
- "lib/mysql2/result.rb",
51
- "mysql2.gemspec",
52
- "spec/em/em_spec.rb",
53
- "spec/mysql2/client_spec.rb",
54
- "spec/mysql2/error_spec.rb",
55
- "spec/mysql2/result_spec.rb",
56
- "spec/rcov.opts",
57
- "spec/spec_helper.rb",
58
- "tasks/benchmarks.rake",
59
- "tasks/compile.rake",
60
- "tasks/jeweler.rake",
61
- "tasks/rspec.rake",
62
- "tasks/vendor_mysql.rake"
63
- ]
13
+ s.files = `git ls-files`.split("\n")
64
14
  s.homepage = %q{http://github.com/brianmario/mysql2}
65
15
  s.rdoc_options = ["--charset=UTF-8"]
66
16
  s.require_paths = ["lib", "ext"]
67
- s.rubygems_version = %q{1.3.7}
17
+ s.rubygems_version = %q{1.4.2}
68
18
  s.summary = %q{A simple, fast Mysql library for Ruby, binding to libmysql}
69
- s.test_files = [
70
- "spec/em/em_spec.rb",
71
- "spec/mysql2/client_spec.rb",
72
- "spec/mysql2/error_spec.rb",
73
- "spec/mysql2/result_spec.rb",
74
- "spec/spec_helper.rb",
75
- "examples/eventmachine.rb",
76
- "examples/threaded.rb"
77
- ]
78
-
79
- if s.respond_to? :specification_version then
80
- current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
81
- s.specification_version = 3
19
+ s.test_files = `git ls-files spec examples`.split("\n")
82
20
 
83
- if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
84
- else
85
- end
86
- else
87
- end
21
+ # tests
22
+ s.add_development_dependency 'eventmachine'
23
+ s.add_development_dependency 'rake-compiler', "~> 0.7.1"
24
+ s.add_development_dependency 'rspec'
25
+ # benchmarks
26
+ s.add_development_dependency 'activerecord'
27
+ s.add_development_dependency 'mysql'
28
+ s.add_development_dependency 'do_mysql'
29
+ s.add_development_dependency 'sequel'
30
+ s.add_development_dependency 'faker'
88
31
  end
89
32