activerecord-jdbc-adapter 1.2.9.1 → 1.3.0.beta1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (231) hide show
  1. data/.travis.yml +3 -0
  2. data/Appraisals +12 -4
  3. data/Gemfile +3 -3
  4. data/Gemfile.lock +19 -19
  5. data/History.txt +90 -16
  6. data/LICENSE.txt +2 -1
  7. data/README.md +14 -1
  8. data/activerecord-jdbc-adapter.gemspec +2 -2
  9. data/gemfiles/rails23.gemfile +5 -5
  10. data/gemfiles/rails23.gemfile.lock +27 -27
  11. data/gemfiles/rails30.gemfile +3 -3
  12. data/gemfiles/rails30.gemfile.lock +8 -8
  13. data/gemfiles/rails31.gemfile +4 -4
  14. data/gemfiles/rails31.gemfile.lock +18 -18
  15. data/gemfiles/rails32.gemfile +4 -4
  16. data/gemfiles/rails32.gemfile.lock +17 -17
  17. data/gemfiles/rails40.gemfile +17 -0
  18. data/gemfiles/rails40.gemfile.lock +126 -0
  19. data/lib/activerecord-jdbc-adapter.rb +0 -7
  20. data/lib/arjdbc.rb +6 -5
  21. data/lib/arjdbc/db2.rb +1 -1
  22. data/lib/arjdbc/db2/adapter.rb +52 -29
  23. data/lib/arjdbc/db2/connection_methods.rb +13 -14
  24. data/lib/arjdbc/derby.rb +1 -1
  25. data/lib/arjdbc/derby/adapter.rb +29 -9
  26. data/lib/arjdbc/derby/connection_methods.rb +17 -20
  27. data/lib/arjdbc/firebird.rb +1 -1
  28. data/lib/arjdbc/h2.rb +2 -2
  29. data/lib/arjdbc/h2/adapter.rb +1 -1
  30. data/lib/arjdbc/h2/connection_methods.rb +12 -16
  31. data/lib/arjdbc/hsqldb.rb +1 -1
  32. data/lib/arjdbc/hsqldb/connection_methods.rb +13 -16
  33. data/lib/arjdbc/informix.rb +1 -1
  34. data/lib/arjdbc/informix/connection_methods.rb +8 -10
  35. data/lib/arjdbc/jdbc.rb +1 -1
  36. data/lib/arjdbc/jdbc/adapter.rb +125 -53
  37. data/lib/arjdbc/jdbc/adapter_java.jar +0 -0
  38. data/lib/arjdbc/jdbc/base_ext.rb +34 -9
  39. data/lib/arjdbc/jdbc/column.rb +15 -2
  40. data/lib/arjdbc/jdbc/connection.rb +0 -2
  41. data/lib/arjdbc/jdbc/connection_methods.rb +10 -3
  42. data/lib/arjdbc/jdbc/driver.rb +2 -2
  43. data/lib/arjdbc/jdbc/extension.rb +35 -21
  44. data/lib/arjdbc/jdbc/java.rb +0 -2
  45. data/lib/arjdbc/jdbc/missing_functionality_helper.rb +35 -25
  46. data/lib/arjdbc/jdbc/railtie.rb +2 -9
  47. data/lib/arjdbc/mimer.rb +1 -1
  48. data/lib/arjdbc/mssql.rb +2 -2
  49. data/lib/arjdbc/mssql/adapter.rb +271 -92
  50. data/lib/arjdbc/mssql/connection_methods.rb +30 -32
  51. data/lib/arjdbc/mssql/explain_support.rb +107 -0
  52. data/lib/arjdbc/mssql/limit_helpers.rb +48 -18
  53. data/lib/arjdbc/mysql.rb +1 -1
  54. data/lib/arjdbc/mysql/adapter.rb +63 -14
  55. data/lib/arjdbc/mysql/connection_methods.rb +22 -24
  56. data/lib/arjdbc/mysql/explain_support.rb +2 -5
  57. data/lib/arjdbc/oracle.rb +1 -1
  58. data/lib/arjdbc/oracle/adapter.rb +78 -38
  59. data/lib/arjdbc/oracle/connection_methods.rb +9 -10
  60. data/lib/arjdbc/postgresql.rb +1 -1
  61. data/lib/arjdbc/postgresql/adapter.rb +964 -380
  62. data/lib/arjdbc/postgresql/column_cast.rb +136 -0
  63. data/lib/arjdbc/postgresql/connection_methods.rb +19 -21
  64. data/lib/arjdbc/postgresql/explain_support.rb +3 -6
  65. data/lib/arjdbc/railtie.rb +9 -0
  66. data/lib/arjdbc/sqlite3.rb +1 -1
  67. data/lib/arjdbc/sqlite3/adapter.rb +73 -26
  68. data/lib/arjdbc/sqlite3/connection_methods.rb +27 -28
  69. data/lib/arjdbc/sqlite3/explain_support.rb +2 -5
  70. data/lib/arjdbc/sybase.rb +1 -1
  71. data/lib/arjdbc/version.rb +5 -4
  72. data/pom.xml +8 -0
  73. data/rakelib/02-test.rake +57 -51
  74. data/rakelib/compile.rake +17 -5
  75. data/rakelib/rails.rake +42 -31
  76. data/src/java/arjdbc/db2/DB2RubyJdbcConnection.java +4 -3
  77. data/src/java/arjdbc/derby/DerbyModule.java +98 -85
  78. data/src/java/arjdbc/derby/DerbyRubyJdbcConnection.java +70 -0
  79. data/src/java/arjdbc/h2/H2RubyJdbcConnection.java +0 -4
  80. data/src/java/arjdbc/jdbc/AdapterJavaService.java +26 -15
  81. data/src/java/arjdbc/jdbc/Callable.java +44 -0
  82. data/src/java/arjdbc/jdbc/JdbcConnectionFactory.java +10 -2
  83. data/src/java/arjdbc/jdbc/RubyJdbcConnection.java +1675 -834
  84. data/src/java/arjdbc/jdbc/SQLBlock.java +9 -3
  85. data/src/java/arjdbc/mssql/MSSQLRubyJdbcConnection.java +73 -36
  86. data/src/java/arjdbc/mysql/MySQLModule.java +11 -10
  87. data/src/java/arjdbc/mysql/MySQLRubyJdbcConnection.java +86 -80
  88. data/src/java/arjdbc/oracle/OracleRubyJdbcConnection.java +27 -7
  89. data/src/java/arjdbc/postgresql/PostgreSQLRubyJdbcConnection.java +214 -0
  90. data/src/java/arjdbc/postgresql/PostgresqlRubyJdbcConnection.java +25 -67
  91. data/src/java/arjdbc/sqlite3/SQLite3RubyJdbcConnection.java +52 -49
  92. data/src/java/arjdbc/util/QuotingUtils.java +6 -6
  93. data/test/abstract_db_create.rb +11 -11
  94. data/test/activerecord/connection_adapters/type_conversion_test.rb +18 -12
  95. data/test/db/db2.rb +1 -1
  96. data/test/{db2_binary_test.rb → db/db2/binary_test.rb} +0 -0
  97. data/test/db/db2/has_many_through_test.rb +6 -0
  98. data/test/{db2_reset_column_information_test.rb → db/db2/reset_column_information_test.rb} +1 -2
  99. data/test/{db2_serialize_test.rb → db/db2/serialize_test.rb} +0 -0
  100. data/test/{db2_simple_test.rb → db/db2/simple_test.rb} +1 -8
  101. data/test/db/db2/test_helper.rb +6 -0
  102. data/test/{db2_test.rb → db/db2/unit_test.rb} +1 -1
  103. data/test/db/derby.rb +1 -1
  104. data/test/{derby_binary_test.rb → db/derby/binary_test.rb} +0 -0
  105. data/test/{derby_migration_test.rb → db/derby/migration_test.rb} +0 -0
  106. data/test/{derby_reset_column_information_test.rb → db/derby/reset_column_information_test.rb} +0 -0
  107. data/test/{derby_row_locking_test.rb → db/derby/row_locking_test.rb} +1 -4
  108. data/test/db/derby/schema_dump_test.rb +5 -0
  109. data/test/{derby_serialize_test.rb → db/derby/serialize_test.rb} +0 -0
  110. data/test/{derby_simple_test.rb → db/derby/simple_test.rb} +23 -38
  111. data/test/db/derby/test_helper.rb +6 -0
  112. data/test/db/derby/unit_test.rb +32 -0
  113. data/test/db/derby/xml_column_test.rb +17 -0
  114. data/test/db/h2.rb +1 -1
  115. data/test/{h2_binary_test.rb → db/h2/binary_test.rb} +0 -0
  116. data/test/{h2_change_column_test.rb → db/h2/change_column_test.rb} +1 -0
  117. data/test/{h2_schema_dump_test.rb → db/h2/schema_dump_test.rb} +0 -0
  118. data/test/{h2_serialize_test.rb → db/h2/serialize_test.rb} +0 -0
  119. data/test/{h2_simple_test.rb → db/h2/simple_test.rb} +3 -1
  120. data/test/db/hsqldb.rb +1 -1
  121. data/test/{hsqldb_binary_test.rb → db/hsqldb/binary_test.rb} +0 -0
  122. data/test/{hsqldb_schema_dump_test.rb → db/hsqldb/schema_dump_test.rb} +0 -0
  123. data/test/{hsqldb_serialize_test.rb → db/hsqldb/serialize_test.rb} +0 -0
  124. data/test/{hsqldb_simple_test.rb → db/hsqldb/simple_test.rb} +3 -1
  125. data/test/db/informix.rb +1 -1
  126. data/test/db/jdbc.rb +3 -2
  127. data/test/db/jdbc_derby.rb +1 -1
  128. data/test/db/jdbc_h2.rb +1 -1
  129. data/test/db/jdbc_mysql.rb +1 -1
  130. data/test/db/jdbc_postgres.rb +1 -1
  131. data/test/db/jndi_config.rb +1 -2
  132. data/test/db/jndi_pooled_config.rb +2 -3
  133. data/test/db/mssql.rb +2 -2
  134. data/test/{mssql_binary_test.rb → db/mssql/binary_test.rb} +0 -0
  135. data/test/{mssql_db_create_test.rb → db/mssql/db_create_test.rb} +1 -1
  136. data/test/db/mssql/exec_proc_test.rb +46 -0
  137. data/test/{mssql_identity_insert_test.rb → db/mssql/identity_insert_test.rb} +0 -0
  138. data/test/db/mssql/ignore_system_views_test.rb +40 -0
  139. data/test/{mssql_limit_offset_test.rb → db/mssql/limit_offset_test.rb} +10 -1
  140. data/test/{mssql_multibyte_test.rb → db/mssql/multibyte_test.rb} +0 -0
  141. data/test/db/mssql/multiple_connections_test.rb +71 -0
  142. data/test/{mssql_reset_column_information_test.rb → db/mssql/reset_column_information_test.rb} +0 -0
  143. data/test/{mssql_row_locking_test.rb → db/mssql/row_locking_test.rb} +0 -0
  144. data/test/{mssql_serialize_test.rb → db/mssql/serialize_test.rb} +1 -1
  145. data/test/db/mssql/simple_test.rb +140 -0
  146. data/test/db/mssql/transaction_test.rb +6 -0
  147. data/test/db/mssql/types_test.rb +205 -0
  148. data/test/{mssql_test.rb → db/mssql/unit_test.rb} +2 -2
  149. data/test/db/mysql.rb +1 -2
  150. data/test/db/mysql/_rails_test_mysql.32.out +6768 -0
  151. data/test/{mysql_binary_test.rb → db/mysql/binary_test.rb} +0 -0
  152. data/test/db/mysql/connection_test.rb +51 -0
  153. data/test/{mysql_db_create_test.rb → db/mysql/db_create_test.rb} +0 -0
  154. data/test/{mysql_index_length_test.rb → db/mysql/index_length_test.rb} +0 -0
  155. data/test/{mysql_multibyte_test.rb → db/mysql/multibyte_test.rb} +0 -0
  156. data/test/{mysql_nonstandard_primary_key_test.rb → db/mysql/nonstandard_primary_key_test.rb} +0 -0
  157. data/test/{mysql_reset_column_information_test.rb → db/mysql/reset_column_information_test.rb} +0 -0
  158. data/test/{mysql_schema_dump_test.rb → db/mysql/schema_dump_test.rb} +9 -1
  159. data/test/{mysql_serialize_test.rb → db/mysql/serialize_test.rb} +0 -0
  160. data/test/{mysql_simple_test.rb → db/mysql/simple_test.rb} +16 -8
  161. data/test/db/mysql/transaction_test.rb +6 -0
  162. data/test/db/mysql/types_test.rb +30 -0
  163. data/test/{mysql_test.rb → db/mysql/unit_test.rb} +1 -1
  164. data/test/db/mysql_config.rb +1 -1
  165. data/test/db/oracle.rb +1 -1
  166. data/test/{oracle_binary_test.rb → db/oracle/binary_test.rb} +0 -0
  167. data/test/{oracle_limit_test.rb → db/oracle/limit_test.rb} +0 -0
  168. data/test/db/oracle/multibyte_test.rb +22 -0
  169. data/test/{oracle_reset_column_information_test.rb → db/oracle/reset_column_information_test.rb} +0 -0
  170. data/test/{oracle_serialize_test.rb → db/oracle/serialize_test.rb} +0 -0
  171. data/test/{oracle_simple_test.rb → db/oracle/simple_test.rb} +14 -19
  172. data/test/{oracle_specific_test.rb → db/oracle/specific_test.rb} +62 -16
  173. data/test/db/oracle/transaction_test.rb +31 -0
  174. data/test/db/oracle/unit_test.rb +31 -0
  175. data/test/db/postgres.rb +1 -1
  176. data/test/db/postgres/_rails_test_postgres.32.out +6777 -0
  177. data/test/db/postgres/a_custom_primary_key_test.rb +50 -0
  178. data/test/db/postgres/array_type_test.rb +101 -0
  179. data/test/{postgres_binary_test.rb → db/postgres/binary_test.rb} +0 -0
  180. data/test/db/postgres/connection_test.rb +55 -0
  181. data/test/db/postgres/data_types_test.rb +703 -0
  182. data/test/{postgres_db_create_test.rb → db/postgres/db_create_test.rb} +1 -1
  183. data/test/{postgres_drop_db_test.rb → db/postgres/db_drop_test.rb} +2 -0
  184. data/test/db/postgres/hstore_test.rb +200 -0
  185. data/test/db/postgres/information_schema_leak_test.rb +30 -0
  186. data/test/db/postgres/json_test.rb +86 -0
  187. data/test/db/postgres/ltree_test.rb +50 -0
  188. data/test/{postgres_mixed_case_test.rb → db/postgres/mixed_case_test.rb} +0 -0
  189. data/test/db/postgres/native_types_test.rb +128 -0
  190. data/test/{postgres_reserved_test.rb → db/postgres/reserved_test.rb} +0 -0
  191. data/test/{postgres_reset_column_information_test.rb → db/postgres/reset_column_information_test.rb} +0 -0
  192. data/test/{postgres_row_locking_test.rb → db/postgres/row_locking_test.rb} +0 -0
  193. data/test/{postgres_schema_dump_test.rb → db/postgres/schema_dump_test.rb} +4 -4
  194. data/test/db/postgres/schema_test.rb +113 -0
  195. data/test/{postgres_simple_test.rb → db/postgres/simple_test.rb} +48 -8
  196. data/test/{postgres_table_alias_length_test.rb → db/postgres/table_alias_length_test.rb} +2 -1
  197. data/test/db/postgres/transaction_test.rb +6 -0
  198. data/test/{postgres_test.rb → db/postgres/unit_test.rb} +3 -3
  199. data/test/db/sqlite3.rb +1 -1
  200. data/test/db/sqlite3/_rails_test_sqlite3.32.out +6502 -0
  201. data/test/db/sqlite3/has_many_though_test.rb +6 -0
  202. data/test/{sqlite3_reset_column_information_test.rb → db/sqlite3/reset_column_information_test.rb} +0 -0
  203. data/test/{sqlite3_schema_dump_test.rb → db/sqlite3/schema_dump_test.rb} +0 -0
  204. data/test/{sqlite3_serialize_test.rb → db/sqlite3/serialize_test.rb} +0 -0
  205. data/test/{sqlite3_simple_test.rb → db/sqlite3/simple_test.rb} +63 -63
  206. data/test/db/sqlite3/transaction_test.rb +32 -0
  207. data/test/{sqlite3_type_conversion_test.rb → db/sqlite3/type_conversion_test.rb} +0 -0
  208. data/test/has_many_through.rb +29 -64
  209. data/test/jdbc/oracle.rb +11 -0
  210. data/test/jndi_test.rb +16 -4
  211. data/test/models/auto_id.rb +1 -1
  212. data/test/models/rights_and_roles.rb +57 -0
  213. data/test/row_locking.rb +3 -0
  214. data/test/schema_dump.rb +24 -10
  215. data/test/simple.rb +359 -104
  216. data/test/test_helper.rb +4 -2
  217. data/test/transaction.rb +109 -0
  218. metadata +119 -86
  219. data/lib/arjdbc/jdbc/compatibility.rb +0 -51
  220. data/lib/arjdbc/jdbc/core_ext.rb +0 -24
  221. data/lib/arjdbc/jdbc/discover.rb +0 -18
  222. data/test/derby_schema_dump_test.rb +0 -9
  223. data/test/mssql_ignore_system_views_test.rb +0 -30
  224. data/test/mssql_legacy_types_test.rb +0 -58
  225. data/test/mssql_null_test.rb +0 -14
  226. data/test/mssql_simple_test.rb +0 -51
  227. data/test/postgres_information_schema_leak_test.rb +0 -28
  228. data/test/postgres_native_type_mapping_test.rb +0 -93
  229. data/test/postgres_nonseq_pkey_test.rb +0 -38
  230. data/test/postgres_schema_search_path_test.rb +0 -48
  231. data/test/postgres_type_conversion_test.rb +0 -33
@@ -7,11 +7,8 @@ module ::ArJdbc
7
7
 
8
8
  def explain(arel, binds = [])
9
9
  sql = "EXPLAIN QUERY PLAN #{to_sql(arel, binds)}"
10
- raw_result = execute(sql, "EXPLAIN", binds)
11
- # TODO we should refactor to exce_query once it returns Result ASAP :
12
- keys = raw_result[0] ? raw_result[0].keys : {}
13
- rows = raw_result.map { |hash| hash.values }
14
- ExplainPrettyPrinter.new.pp ActiveRecord::Result.new(keys, rows)
10
+ result = exec_query(sql, "EXPLAIN", binds)
11
+ ExplainPrettyPrinter.new.pp result
15
12
  end
16
13
 
17
14
  class ExplainPrettyPrinter # :nodoc:
data/lib/arjdbc/sybase.rb CHANGED
@@ -1,2 +1,2 @@
1
- require 'arjdbc/jdbc'
1
+ require 'arjdbc'
2
2
  require 'arjdbc/sybase/adapter.rb'
@@ -1,8 +1,9 @@
1
1
  module ArJdbc
2
- module Version
3
- VERSION = "1.2.9.1"
2
+ VERSION = "1.3.0.beta1"
3
+ module Version # :nodoc:
4
+ VERSION = ArJdbc::VERSION # :nodoc: 1.2.x compatibility
4
5
  end
5
6
  end
6
7
  # Compatibility with older versions of ar-jdbc for other extensions out there
7
- JdbcAdapter = ArJdbc
8
- JdbcSpec = ArJdbc
8
+ JdbcAdapter = ArJdbc # :nodoc:
9
+ JdbcSpec = ArJdbc # :nodoc:
data/pom.xml CHANGED
@@ -37,6 +37,14 @@
37
37
  <artifactId>jruby-complete</artifactId>
38
38
  <version>1.6.8</version>
39
39
  </dependency>
40
+ <!-- e.g.
41
+ mvn install:install-file -DgroupId=org.postgresql -DartifactId=pgjdbc -Dversion=9.2-1002 -Dpackaging=jar -Dfile=./jdbc-postgres/lib/postgresql-9.2-1002.jdbc4.jar
42
+ -->
43
+ <dependency>
44
+ <groupId>org.postgresql</groupId>
45
+ <artifactId>pgjdbc</artifactId>
46
+ <version>9.2-1002</version>
47
+ </dependency>
40
48
  </dependencies>
41
49
 
42
50
  <build>
data/rakelib/02-test.rake CHANGED
@@ -20,47 +20,67 @@ def set_compat_version(task)
20
20
  end
21
21
  end
22
22
 
23
- def declare_test_task_for(adapter, options = {})
24
- driver = options[:driver] || adapter
25
- prereqs = options[:prereqs] || []
26
- prereqs = [ prereqs ].flatten
23
+ %w(derby h2 hsqldb mysql sqlite3 postgres mssql oracle db2 informix sybase).each do
24
+ |adapter|
27
25
  task "test_#{adapter}_pre" do
28
26
  unless (ENV['BUNDLE_GEMFILE'] rescue '') =~ /gemfiles\/.*?\.gemfile/
29
27
  appraisals = []; Appraisal::File.each { |file| appraisals << file.name }
30
28
  puts "Specify AR version with `rake appraisal:{version} test_#{adapter}'" +
31
29
  " where version=(#{appraisals.join('|')})"
32
30
  end
33
- end
31
+ end
32
+ end
33
+
34
+ Rake::TestTask.class_eval { attr_reader :test_files }
35
+
36
+ def declare_test_task_for(adapter, options = {}, &block)
37
+ driver = options[:driver] || adapter
38
+ prereqs = options[:prereqs] || []
39
+ prereqs = [ prereqs ].flatten
34
40
  prereqs << "test_#{adapter}_pre"
35
- test_task = lambda do |t|
36
- task_name = t.name.keys.first
37
- files = FileList["test/#{adapter}*test.rb"]
38
- files.unshift "test/db/#{task_name.sub('test_','')}.rb"
39
- if adapter == "derby"
40
- files << 'test/activerecord/connection_adapters/type_conversion_test.rb'
41
- end
42
- t.test_files = files
43
- t.libs = []
44
- set_compat_version(t)
41
+ Rake::TestTask.new("test_#{adapter}" => prereqs) do |task|
42
+ files = FileList["test/#{adapter}*_test.rb"]
43
+ files += FileList["test/db/#{adapter}/*_test.rb"]
44
+ #task_name = task.name.keys.first.to_s
45
+ #files.unshift "test/db/#{task_name.sub('test_','')}.rb"
46
+ task.test_files = files
47
+ task.libs = []
45
48
  if defined?(JRUBY_VERSION)
46
- t.libs << "lib" << "jdbc-#{driver}/lib"
47
- t.libs.push *FileList["activerecord-jdbc#{adapter}*/lib"]
49
+ task.libs << "lib" << "jdbc-#{driver}/lib"
50
+ task.libs.push *FileList["activerecord-jdbc#{adapter}*/lib"]
48
51
  end
49
- t.libs << "test"
50
- t.verbose = true if $VERBOSE
52
+ task.libs << "test"
53
+ set_compat_version(task)
54
+ task.verbose = true if $VERBOSE
55
+ yield(task) if block_given?
51
56
  end
52
- Rake::TestTask.new("test_#{adapter}" => prereqs) { |t| test_task.call t }
53
- Rake::TestTask.new("test_jdbc_#{adapter}" => prereqs) { |t| test_task.call t }
54
57
  end
55
58
 
56
- declare_test_task_for :derby
59
+ declare_test_task_for :derby do |task|
60
+ task.test_files << 'test/activerecord/connection_adapters/type_conversion_test.rb'
61
+ end
57
62
  declare_test_task_for :h2
58
63
  declare_test_task_for :hsqldb
59
64
  declare_test_task_for :mssql, :driver => :jtds
60
65
  declare_test_task_for :mysql, :prereqs => "db:mysql"
61
66
  declare_test_task_for :postgres, :prereqs => "db:postgres"
67
+ task :test_postgresql => :test_postgres # alias
68
+ task :test_pgsql => :test_postgres # alias
62
69
  declare_test_task_for :sqlite3
63
70
 
71
+ # ensure driver for these DBs is on your class-path
72
+ [ :oracle, :db2, :informix, :cachedb ].each do |adapter|
73
+ Rake::TestTask.new("test_#{adapter}") do |task|
74
+ test_files = FileList["test/#{adapter}*_test.rb"]
75
+ test_files += FileList["test/db/#{adapter}/*_test.rb"]
76
+ task.test_files = test_files
77
+ task.libs = []
78
+ task.libs << 'lib' if defined?(JRUBY_VERSION)
79
+ task.libs << 'test'
80
+ set_compat_version(task)
81
+ end
82
+ end
83
+
64
84
  Rake::TestTask.new(:test_jdbc) do |t|
65
85
  t.test_files = FileList['test/generic_jdbc_connection_test.rb']
66
86
  t.libs << 'test' << 'jdbc-mysql/lib' << 'jdbc-derby/lib'
@@ -73,37 +93,23 @@ Rake::TestTask.new(:test_jndi => 'tomcat-jndi:check') do |t|
73
93
  set_compat_version(t)
74
94
  end
75
95
 
76
- task :test_postgresql => [:test_postgres]
77
- task :test_pgsql => [:test_postgres]
78
-
79
- # Ensure driver for these DBs is on your classpath
80
- %w(oracle db2 cachedb informix).each do |d|
81
- Rake::TestTask.new("test_#{d}") do |t|
82
- t.test_files = FileList["test/#{d}*_test.rb"]
83
- t.libs = []
84
- t.libs << 'lib' if defined?(JRUBY_VERSION)
85
- t.libs << 'test'
86
- set_compat_version(t)
87
- end
96
+ # tests for JDBC adapters that don't require a database :
97
+ Rake::TestTask.new(:test_jdbc_adapters) do |task|
98
+ task.test_files = FileList[ 'test/jdbc_adapter/jdbc_sybase_test.rb' ]
99
+ task.libs << 'test'
100
+ set_compat_version(task)
88
101
  end
89
102
 
90
- # Tests for JDBC adapters that don't require a database.
91
- Rake::TestTask.new(:test_jdbc_adapters) do | t |
92
- t.test_files = FileList[ 'test/jdbc_adapter/jdbc_sybase_test.rb' ]
93
- t.libs << 'test'
94
- set_compat_version(t)
103
+ # ensure that the jTDS driver is in your class-path
104
+ Rake::TestTask.new(:test_sybase_jtds) do |task|
105
+ task.test_files = FileList['test/sybase_jtds_simple_test.rb']
106
+ task.libs << 'test'
107
+ set_compat_version(task)
95
108
  end
96
109
 
97
- # Ensure that the jTDS driver is in your classpath before launching rake
98
- Rake::TestTask.new(:test_sybase_jtds) do |t|
99
- t.test_files = FileList['test/sybase_jtds_simple_test.rb']
100
- t.libs << 'test'
101
- set_compat_version(t)
102
- end
103
-
104
- # Ensure that the jConnect driver is in your classpath before launching rake
105
- Rake::TestTask.new(:test_sybase_jconnect) do |t|
106
- t.test_files = FileList['test/sybase_jconnect_simple_test.rb']
107
- t.libs << 'test'
108
- set_compat_version(t)
110
+ # ensure that the jConnect driver is in your class-path
111
+ Rake::TestTask.new(:test_sybase_jconnect) do |task|
112
+ task.test_files = FileList['test/sybase_jconnect_simple_test.rb']
113
+ task.libs << 'test'
114
+ set_compat_version(task)
109
115
  end
data/rakelib/compile.rake CHANGED
@@ -1,14 +1,18 @@
1
1
  jar_file = File.join(*%w(lib arjdbc jdbc adapter_java.jar))
2
2
  begin
3
3
  require 'ant'
4
- directory "pkg/classes"
5
- CLEAN << "pkg"
4
+ directory classes = "pkg/classes"
5
+ CLEAN << classes
6
6
 
7
+ driver_jars = []
8
+ # PostgreSQL driver :
9
+ driver_jars << Dir.glob("jdbc-postgres/lib/*.jar").sort.last
10
+
7
11
  file jar_file => FileList['src/java/**/*.java', 'pkg/classes'] do
8
- rm_rf FileList['pkg/classes/**/*']
12
+ rm_rf FileList["#{classes}/**/*"]
9
13
  ant.javac :srcdir => "src/java", :destdir => "pkg/classes",
10
- :source => "1.5", :target => "1.5", :debug => true,
11
- :classpath => "${java.class.path}:${sun.boot.class.path}",
14
+ :source => "1.6", :target => "1.6", :debug => true, :deprecation => true,
15
+ :classpath => "${java.class.path}:${sun.boot.class.path}:#{driver_jars.join(':')}",
12
16
  :includeantRuntime => false
13
17
 
14
18
  ant.jar :basedir => "pkg/classes", :destfile => jar_file, :includes => "**/*.class"
@@ -16,6 +20,14 @@ begin
16
20
 
17
21
  desc "Compile the native Java code."
18
22
  task :jar => jar_file
23
+
24
+ namespace :jar do
25
+ task :force do
26
+ rm jar_file
27
+ Rake::Task['jar'].invoke
28
+ end
29
+ end
30
+
19
31
  rescue LoadError
20
32
  task :jar do
21
33
  puts "Run 'jar' with JRuby to re-compile the agent extension class"
data/rakelib/rails.rake CHANGED
@@ -1,39 +1,13 @@
1
1
  namespace :rails do
2
- def _adapter(n)
3
- case n
4
- when /postgres/
5
- 'postgresql'
6
- else
7
- n
8
- end
9
- end
10
-
11
- def _driver(n)
12
- case n
13
- when /postgres/
14
- 'postgres'
15
- else
16
- n
17
- end
18
- end
19
-
20
- def _target(n)
21
- case n
22
- when /postgres/
23
- 'test_jdbcpostgresql'
24
- else
25
- "test_jdbc#{n}"
26
- end
27
- end
28
-
29
- task :test => :jar do
30
- raise "need a DRIVER" unless driver = ENV['DRIVER']
31
- raise "need location of RAILS source code" unless rails_dir = ENV['RAILS']
2
+
3
+ task :test do
4
+ raise "need a DRIVER e.g. DRIVER=mysql" unless driver = ENV['DRIVER'] || ENV['ADAPTER']
5
+ raise "need location of RAILS source code e.g. RAILS=../rails" unless rails_dir = ENV['RAILS']
32
6
  rails_dir = File.join(rails_dir, '..') if rails_dir =~ /activerecord$/
33
7
  activerecord_dir = File.join(rails_dir, 'activerecord') # rails/activerecord
34
8
 
35
9
  ar_jdbc_dir = File.expand_path('..', File.dirname(__FILE__))
36
-
10
+
37
11
  rubylib = [
38
12
  "#{ar_jdbc_dir}/lib",
39
13
  "#{ar_jdbc_dir}/jdbc-#{_driver(driver)}/lib",
@@ -46,4 +20,41 @@ namespace :rails do
46
20
 
47
21
  Dir.chdir(activerecord_dir) { rake "RUBYLIB=#{rubylib.join(':')}", "#{_target(driver)}" }
48
22
  end
23
+
24
+ %w(MySQL SQLite3 Postgres).each do |adapter|
25
+ desc "Run Rails' ActiveRecord tests with #{adapter} (JDBC)"
26
+ task "test_#{adapter.downcase}" do
27
+ ENV['ADAPTER'] = adapter; Rake::Task['rails:test'].invoke
28
+ end
29
+ end
30
+
31
+ private
32
+
33
+ def _adapter(name)
34
+ case name
35
+ when /postgres/i
36
+ 'postgresql'
37
+ else
38
+ name.downcase
39
+ end
40
+ end
41
+
42
+ def _driver(name)
43
+ case name
44
+ when /postgres/i
45
+ 'postgres'
46
+ else
47
+ name.downcase
48
+ end
49
+ end
50
+
51
+ def _target(name)
52
+ case name
53
+ when /postgres/i
54
+ 'test_jdbcpostgresql'
55
+ else
56
+ "test_jdbc#{name.downcase}"
57
+ end
58
+ end
59
+
49
60
  end
@@ -25,19 +25,20 @@
25
25
  ***** END LICENSE BLOCK *****/
26
26
  package arjdbc.db2;
27
27
 
28
+ import arjdbc.jdbc.RubyJdbcConnection;
29
+
28
30
  import org.jruby.Ruby;
29
31
  import org.jruby.RubyClass;
30
32
  import org.jruby.runtime.ObjectAllocator;
31
33
  import org.jruby.runtime.builtin.IRubyObject;
32
34
 
33
- import arjdbc.jdbc.RubyJdbcConnection;
34
-
35
35
  /**
36
36
  *
37
37
  * @author mikestone
38
38
  */
39
39
  public class DB2RubyJdbcConnection extends RubyJdbcConnection {
40
- private static final String[] TABLE_TYPES = new String[]{"TABLE", "VIEW", "SYNONYM", "MATERIALIZED QUERY TABLE", "ALIAS"};
40
+
41
+ private static final String[] TABLE_TYPES = new String[]{ "TABLE", "VIEW", "SYNONYM", "MATERIALIZED QUERY TABLE", "ALIAS" };
41
42
 
42
43
  protected DB2RubyJdbcConnection(Ruby runtime, RubyClass metaClass) {
43
44
  super(runtime, metaClass);
@@ -38,6 +38,7 @@ import org.jruby.RubyObjectAdapter;
38
38
  import org.jruby.RubyString;
39
39
  import org.jruby.anno.JRubyMethod;
40
40
  import org.jruby.javasupport.JavaEmbedUtils;
41
+ import org.jruby.runtime.Block;
41
42
  import org.jruby.runtime.ThreadContext;
42
43
  import org.jruby.runtime.builtin.IRubyObject;
43
44
  import org.jruby.util.ByteList;
@@ -105,40 +106,43 @@ public class DerbyModule {
105
106
  }
106
107
 
107
108
  @JRubyMethod(name = "quote", required = 1, optional = 1)
108
- public static IRubyObject quote(ThreadContext context, IRubyObject recv, IRubyObject[] args) {
109
- Ruby runtime = recv.getRuntime();
109
+ public static IRubyObject quote(final ThreadContext context, final IRubyObject self,
110
+ final IRubyObject[] args) {
111
+ final Ruby runtime = self.getRuntime();
110
112
  IRubyObject value = args[0];
111
- if (args.length > 1) {
112
- IRubyObject col = args[1];
113
- String type = col.isNil() ? "" : rubyApi.callMethod(col, "type").toString();
113
+ if ( args.length > 1 ) {
114
+ final IRubyObject column = args[1];
115
+ final String columnType = column.isNil() ? "" : rubyApi.callMethod(column, "type").toString();
114
116
  // intercept and change value, maybe, if the column type is :text or :string
115
- if (type.equals("text") || type.equals("string")) {
116
- value = make_ruby_string_for_text_column(context, recv, runtime, value);
117
+ if ( columnType.equals("text") || columnType.equals("string") ) {
118
+ value = make_ruby_string_for_text_column(context, self, runtime, value);
117
119
  }
118
- String metaClass = value.getMetaClass().getName();
119
-
120
- if (value instanceof RubyString) {
121
- if (type.equals("string")) {
122
- return quote_string_with_surround(runtime, "'", (RubyString)value, "'");
123
- } else if (type.equals("text")) {
124
- return quote_string_with_surround(runtime, "CAST('", (RubyString)value, "' AS CLOB)");
125
- } else if (type.equals("binary")) {
126
- return hexquote_string_with_surround(runtime, "CAST(X'", (RubyString)value, "' AS BLOB)");
127
- } else {
128
- // column type :integer or other numeric or date version
129
- if (only_digits((RubyString)value)) {
130
- return value;
131
- } else {
132
- return super_quote(context, recv, runtime, value, col);
133
- }
120
+ final String metaClass = value.getMetaClass().getName();
121
+
122
+ if ( value instanceof RubyString ) {
123
+ if ( columnType.equals("string") ) {
124
+ return quote_string_with_surround(runtime, "'", (RubyString) value, "'");
125
+ }
126
+ else if ( columnType.equals("text") ) {
127
+ return quote_string_with_surround(runtime, "CAST('", (RubyString) value, "' AS CLOB)");
128
+ }
129
+ else if ( columnType.equals("binary") ) {
130
+ return hexquote_string_with_surround(runtime, "CAST(X'", (RubyString) value, "' AS BLOB)");
134
131
  }
135
- } else if (metaClass.equals("Float") || metaClass.equals("Fixnum") || metaClass.equals("Bignum")) {
136
- if (type.equals("string")) {
132
+ else if ( columnType.equals("xml") ) {
133
+ return quote_string_with_surround(runtime, "XMLPARSE(DOCUMENT '", (RubyString) value, "' PRESERVE WHITESPACE)");
134
+ }
135
+ else { // column type :integer or other numeric or date version
136
+ return only_digits((RubyString) value) ? value : super_quote(context, self, runtime, value, column);
137
+ }
138
+ }
139
+ else if ( metaClass.equals("Float") || metaClass.equals("Fixnum") || metaClass.equals("Bignum") ) {
140
+ if ( columnType.equals("string") ) {
137
141
  return quote_string_with_surround(runtime, "'", RubyString.objAsString(context, value), "'");
138
142
  }
139
143
  }
140
144
  }
141
- return super_quote(context, recv, runtime, value, runtime.getNil());
145
+ return super_quote(context, self, runtime, value, runtime.getNil());
142
146
  }
143
147
 
144
148
  /*
@@ -146,8 +150,7 @@ public class DerbyModule {
146
150
  * This method turns non stringy things into strings.
147
151
  */
148
152
  private static IRubyObject make_ruby_string_for_text_column(ThreadContext context, IRubyObject recv, Ruby runtime, IRubyObject value) {
149
- RubyModule multibyteChars = (RubyModule)
150
- ((RubyModule) ((RubyModule) runtime.getModule("ActiveSupport")).getConstant("Multibyte")).getConstantAt("Chars");
153
+ final RubyModule multibyteChars = getMultibyteChars(runtime);
151
154
  if (value instanceof RubyString || rubyApi.isKindOf(value, multibyteChars) || value.isNil()) {
152
155
  return value;
153
156
  }
@@ -179,8 +182,7 @@ public class DerbyModule {
179
182
  String metaClass = value.getMetaClass().getName();
180
183
 
181
184
  IRubyObject type = (col.isNil()) ? col : rubyApi.callMethod(col, "type");
182
- RubyModule multibyteChars = (RubyModule)
183
- ((RubyModule) ((RubyModule) runtime.getModule("ActiveSupport")).getConstant("Multibyte")).getConstantAt("Chars");
185
+ final RubyModule multibyteChars = getMultibyteChars(runtime);
184
186
  if (value instanceof RubyString || rubyApi.isKindOf(value, multibyteChars)) {
185
187
  RubyString svalue = RubyString.objAsString(context, value);
186
188
  if (type == runtime.newSymbol("binary") && col.getType().respondsTo("string_to_binary")) {
@@ -211,52 +213,57 @@ public class DerbyModule {
211
213
 
212
214
  private final static ByteList TWO_SINGLE = new ByteList(new byte[]{'\'','\''});
213
215
 
214
- private static IRubyObject quote_string_with_surround(Ruby runtime, String before, RubyString string, String after) {
215
- ByteList input = string.getByteList();
216
- ByteList output = new ByteList(before.getBytes(), input.encoding);
217
- for(int i = input.begin; i< input.begin + input.realSize; i++) {
218
- switch(input.bytes[i]) {
219
- case '\'':
220
- output.append(input.bytes[i]);
221
- //FALLTHROUGH
222
- default:
223
- output.append(input.bytes[i]);
216
+ private static IRubyObject quote_string_with_surround(final Ruby runtime,
217
+ final String before, final RubyString string, final String after) {
218
+
219
+ final ByteList input = string.getByteList();
220
+ final ByteList output = new ByteList(before.getBytes(), input.getEncoding());
221
+ final byte[] inputBytes = input.unsafeBytes();
222
+
223
+ for(int i = input.getBegin(); i< input.getBegin() + input.getRealSize(); i++) {
224
+ switch ( inputBytes[i] ) {
225
+ case '\'': output.append(inputBytes[i]); // FALLTHROUGH
226
+ default: output.append(inputBytes[i]);
224
227
  }
225
228
 
226
229
  }
227
230
 
228
231
  output.append(after.getBytes());
229
-
230
232
  return runtime.newString(output);
231
233
  }
232
234
 
233
235
  private final static byte[] HEX = {'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};
234
236
 
235
- private static IRubyObject hexquote_string_with_surround(Ruby runtime, String before, RubyString string, String after) {
236
- ByteList input = string.getByteList();
237
- ByteList output = new ByteList(before.getBytes());
237
+ private static IRubyObject hexquote_string_with_surround(final Ruby runtime,
238
+ final String before, final RubyString string, final String after) {
239
+
240
+ final ByteList input = string.getByteList();
241
+ final ByteList output = new ByteList(before.getBytes());
242
+ final byte[] inputBytes = input.unsafeBytes();
243
+
238
244
  int written = 0;
239
- for(int i = input.begin; i< input.begin + input.realSize; i++) {
240
- byte b1 = input.bytes[i];
245
+ for(int i = input.getBegin(); i< input.getBegin() + input.getRealSize(); i++) {
246
+ byte b1 = inputBytes[i];
241
247
  byte higher = HEX[(((char)b1)>>4)%16];
242
248
  byte lower = HEX[((char)b1)%16];
243
249
  output.append(higher);
244
250
  output.append(lower);
245
251
  written += 2;
246
- if(written >= 16334) { // max hex length = 16334
252
+ if (written >= 16334) { // max hex length = 16334
247
253
  output.append("'||X'".getBytes());
248
254
  written = 0;
249
255
  }
250
256
  }
251
257
 
252
258
  output.append(after.getBytes());
253
- return runtime.newStringShared(output);
259
+ return RubyString.newStringShared(runtime, output);
254
260
  }
255
261
 
256
- private static boolean only_digits(RubyString inp) {
257
- ByteList input = inp.getByteList();
258
- for(int i = input.begin; i< input.begin + input.realSize; i++) {
259
- if(input.bytes[i] < '0' || input.bytes[i] > '9') {
262
+ private static boolean only_digits(final RubyString string) {
263
+ final ByteList input = string.getByteList();
264
+ final byte[] inputBytes = input.unsafeBytes();
265
+ for ( int i = input.getBegin(); i< input.getBegin() + input.getRealSize(); i++ ) {
266
+ if ( inputBytes[i] < '0' || inputBytes[i] > '9' ) {
260
267
  return false;
261
268
  }
262
269
  }
@@ -264,31 +271,26 @@ public class DerbyModule {
264
271
  }
265
272
 
266
273
  @JRubyMethod(name = "quote_string", required = 1)
267
- public static IRubyObject quote_string(IRubyObject recv, IRubyObject string) {
268
- boolean replacementFound = false;
269
- ByteList bl = ((RubyString) string).getByteList();
270
-
271
- for(int i = bl.begin; i < bl.begin + bl.realSize; i++) {
272
- switch (bl.bytes[i]) {
273
- case '\'': break;
274
- default: continue;
274
+ public static IRubyObject quote_string(final IRubyObject self, IRubyObject string) {
275
+ ByteList bytes = ((RubyString) string).getByteList();
276
+
277
+ boolean replacement = false;
278
+ for ( int i = 0; i < bytes.length(); i++ ) {
279
+ switch ( bytes.get(i) ) {
280
+ case '\'': break;
281
+ default: continue;
275
282
  }
276
-
277
- // On first replacement allocate a different bytelist so we don't manip original
278
- if(!replacementFound) {
279
- i-= bl.begin;
280
- bl = new ByteList(bl);
281
- replacementFound = true;
283
+ // on first replacement allocate so we don't manip original
284
+ if ( ! replacement ) {
285
+ bytes = new ByteList(bytes);
286
+ replacement = true;
282
287
  }
283
288
 
284
- bl.replace(i, 1, TWO_SINGLE);
285
- i+=1;
286
- }
287
- if(replacementFound) {
288
- return recv.getRuntime().newStringShared(bl);
289
- } else {
290
- return string;
289
+ bytes.replace(i, 1, TWO_SINGLE);
290
+ i += 1;
291
291
  }
292
+
293
+ return replacement ? RubyString.newStringShared(self.getRuntime(), bytes) : string;
292
294
  }
293
295
 
294
296
  @JRubyMethod(name = "quoted_true", required = 0, frame = false)
@@ -325,19 +327,30 @@ public class DerbyModule {
325
327
  }
326
328
 
327
329
  @JRubyMethod(name = "_execute", required = 1, optional = 1)
328
- public static IRubyObject _execute(ThreadContext context, IRubyObject recv, IRubyObject[] args) throws SQLException, java.io.IOException {
329
- Ruby runtime = recv.getRuntime();
330
- RubyJdbcConnection conn = (RubyJdbcConnection) rubyApi.getInstanceVariable(recv, "@connection");
331
- String sql = args[0].toString().trim().toLowerCase();
332
- if (sql.charAt(0) == '(') {
333
- sql = sql.substring(1).trim();
330
+ public static IRubyObject _execute(final ThreadContext context, final IRubyObject self, final IRubyObject[] args)
331
+ throws SQLException, java.io.IOException {
332
+ final IRubyObject sql = args[0];
333
+
334
+ String sqlStr = sql.toString().trim();
335
+ if ( sqlStr.charAt(0) == '(' ) sqlStr = sqlStr.substring(1).trim();
336
+ sqlStr = sqlStr.substring( 0, Math.min(6, sqlStr.length()) ).toLowerCase();
337
+
338
+ final RubyJdbcConnection connection = (RubyJdbcConnection) rubyApi.getInstanceVariable(self, "@connection");
339
+
340
+ if (sqlStr.startsWith("insert")) {
341
+ return connection.execute_insert(context, sql);
334
342
  }
335
- if (sql.startsWith("insert")) {
336
- return conn.execute_insert(context, args[0]);
337
- } else if (sql.startsWith("select") || sql.startsWith("show") || sql.startsWith("values")) {
338
- return conn.execute_query(context, args[0]);
339
- } else {
340
- return conn.execute_update(context, args[0]);
343
+ else if (sqlStr.startsWith("select") || sqlStr.startsWith("show") || sqlStr.startsWith("values")) {
344
+ return connection.execute_query_raw(context, sql, Block.NULL_BLOCK);
341
345
  }
346
+ else {
347
+ return connection.execute_update(context, sql);
348
+ }
349
+ }
350
+
351
+ private static RubyModule getMultibyteChars(final Ruby runtime) {
352
+ return (RubyModule) ((RubyModule) runtime.getModule("ActiveSupport").
353
+ getConstant("Multibyte")).getConstantAt("Chars");
342
354
  }
355
+
343
356
  }