sqlite3 0.1.1 → 1.3.3.beta.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (55) hide show
  1. data/API_CHANGES.rdoc +50 -0
  2. data/CHANGELOG.rdoc +177 -0
  3. data/ChangeLog.cvs +88 -0
  4. data/LICENSE +24 -17
  5. data/Manifest.txt +50 -0
  6. data/README.rdoc +100 -4
  7. data/Rakefile +10 -0
  8. data/ext/sqlite3/backup.c +164 -0
  9. data/ext/sqlite3/backup.h +15 -0
  10. data/ext/sqlite3/database.c +762 -0
  11. data/ext/sqlite3/database.h +15 -0
  12. data/ext/sqlite3/exception.c +94 -0
  13. data/ext/sqlite3/exception.h +8 -0
  14. data/ext/sqlite3/extconf.rb +47 -0
  15. data/ext/sqlite3/sqlite3.c +36 -0
  16. data/ext/sqlite3/sqlite3_ruby.h +44 -0
  17. data/ext/sqlite3/statement.c +419 -0
  18. data/ext/sqlite3/statement.h +16 -0
  19. data/faq/faq.rb +145 -0
  20. data/faq/faq.yml +426 -0
  21. data/lib/sqlite3.rb +9 -12
  22. data/lib/sqlite3/constants.rb +46 -72
  23. data/lib/sqlite3/database.rb +415 -140
  24. data/lib/sqlite3/errors.rb +1 -56
  25. data/lib/sqlite3/pragmas.rb +246 -63
  26. data/lib/sqlite3/resultset.rb +30 -112
  27. data/lib/sqlite3/statement.rb +42 -108
  28. data/lib/sqlite3/translator.rb +118 -0
  29. data/lib/sqlite3/value.rb +57 -0
  30. data/lib/sqlite3/version.rb +23 -1
  31. data/setup.rb +1333 -0
  32. data/tasks/faq.rake +9 -0
  33. data/tasks/gem.rake +31 -0
  34. data/tasks/native.rake +61 -0
  35. data/tasks/vendor_sqlite3.rake +104 -0
  36. data/test/helper.rb +3 -0
  37. data/test/test_backup.rb +33 -0
  38. data/test/test_collation.rb +82 -0
  39. data/test/test_database.rb +312 -0
  40. data/test/test_database_readonly.rb +29 -0
  41. data/test/test_deprecated.rb +37 -0
  42. data/test/test_encoding.rb +119 -0
  43. data/test/test_integration.rb +544 -0
  44. data/test/test_integration_open_close.rb +30 -0
  45. data/test/test_integration_pending.rb +115 -0
  46. data/test/test_integration_resultset.rb +156 -0
  47. data/test/test_integration_statement.rb +194 -0
  48. data/test/test_sqlite3.rb +9 -0
  49. data/test/test_statement.rb +207 -0
  50. data/test/test_statement_execute.rb +35 -0
  51. metadata +124 -67
  52. data/lib/sqlite3/api.rb +0 -52
  53. data/lib/sqlite3/driver.rb +0 -138
  54. data/lib/sqlite3/encoding.rb +0 -43
  55. data/lib/sqlite3/extensions.rb +0 -27
@@ -1,37 +1,6 @@
1
- # Copyright (c) 2004, Jamis Buck (jamis@jamisbuck.org)
2
- # All rights reserved.
3
-
4
- # Redistribution and use in source and binary forms, with or without
5
- # modification, are permitted provided that the following conditions
6
- # are met:
7
-
8
- # * Redistributions of source code must retain the above copyright
9
- # notice, this list of conditions and the following disclaimer.
10
-
11
- # * Redistributions in binary form must reproduce the above copyright
12
- # notice, this list of conditions and the following disclaimer in
13
- # the documentation and/or other materials provided with the
14
- # distribution.
15
-
16
- # * The names of its contributors may not be used to endorse or
17
- # promote products derived from this software without specific prior
18
- # written permission.
19
-
20
- # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21
- # "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22
- # LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
23
- # FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
24
- # COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
25
- # INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
26
- # BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
27
- # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
28
- # CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29
- # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
30
- # ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31
- # POSSIBILITY OF SUCH DAMAGE.
1
+ require 'sqlite3/constants'
32
2
 
33
3
  module SQLite3
34
-
35
4
  class Exception < ::StandardError
36
5
  @code = 0
37
6
 
@@ -72,28 +41,4 @@ module SQLite3
72
41
  class FormatException < Exception; end
73
42
  class RangeException < Exception; end
74
43
  class NotADatabaseException < Exception; end
75
-
76
- EXCEPTIONS =
77
- [
78
- nil, SQLException, InternalException,
79
- PermissionException, AbortException, BusyException,
80
- LockedException, MemoryException, ReadOnlyException,
81
- InterruptException, IOException, CorruptException,
82
- NotFoundException, FullException, CantOpenException,
83
- ProtocolException, EmptyException, SchemaChangedException,
84
- TooBigException, ConstraintException, MismatchException,
85
- MisuseException, UnsupportedException, AuthorizationException,
86
- FormatException, RangeException, NotADatabaseException
87
- ].each_with_index { |e,i| e.instance_variable_set(:@code, i ) if e }
88
-
89
- module Error
90
- def check( result, db=nil, msg=nil )
91
- unless result == Constants::ErrorCode::OK
92
- msg = ( msg ? msg + ": " : "" ) + db.errmsg if db
93
- raise(( EXCEPTIONS[result] || SQLite3::Exception ), msg)
94
- end
95
- end
96
- module_function :check
97
- end
98
-
99
44
  end
@@ -1,34 +1,4 @@
1
- # Copyright (c) 2004, Jamis Buck (jamis@jamisbuck.org)
2
- # All rights reserved.
3
-
4
- # Redistribution and use in source and binary forms, with or without
5
- # modification, are permitted provided that the following conditions
6
- # are met:
7
-
8
- # * Redistributions of source code must retain the above copyright
9
- # notice, this list of conditions and the following disclaimer.
10
-
11
- # * Redistributions in binary form must reproduce the above copyright
12
- # notice, this list of conditions and the following disclaimer in
13
- # the documentation and/or other materials provided with the
14
- # distribution.
15
-
16
- # * The names of its contributors may not be used to endorse or
17
- # promote products derived from this software without specific prior
18
- # written permission.
19
-
20
- # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21
- # "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22
- # LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
23
- # FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
24
- # COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
25
- # INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
26
- # BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
27
- # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
28
- # CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29
- # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
30
- # ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31
- # POSSIBILITY OF SUCH DAMAGE.
1
+ require 'sqlite3/errors'
32
2
 
33
3
  module SQLite3
34
4
 
@@ -39,16 +9,228 @@ module SQLite3
39
9
  # at http://sqlite.org/pragma.html.
40
10
  module Pragmas
41
11
 
42
- def table_info(table, &block) # :yields: row
43
- columns, *rows = execute2("PRAGMA table_info(#{table})")
12
+ # Returns +true+ or +false+ depending on the value of the named pragma.
13
+ def get_boolean_pragma( name )
14
+ get_first_value( "PRAGMA #{name}" ) != "0"
15
+ end
16
+ private :get_boolean_pragma
17
+
18
+ # Sets the given pragma to the given boolean value. The value itself
19
+ # may be +true+ or +false+, or any other commonly used string or
20
+ # integer that represents truth.
21
+ def set_boolean_pragma( name, mode )
22
+ case mode
23
+ when String
24
+ case mode.downcase
25
+ when "on", "yes", "true", "y", "t"; mode = "'ON'"
26
+ when "off", "no", "false", "n", "f"; mode = "'OFF'"
27
+ else
28
+ raise Exception,
29
+ "unrecognized pragma parameter #{mode.inspect}"
30
+ end
31
+ when true, 1
32
+ mode = "ON"
33
+ when false, 0, nil
34
+ mode = "OFF"
35
+ else
36
+ raise Exception,
37
+ "unrecognized pragma parameter #{mode.inspect}"
38
+ end
39
+
40
+ execute( "PRAGMA #{name}=#{mode}" )
41
+ end
42
+ private :set_boolean_pragma
43
+
44
+ # Requests the given pragma (and parameters), and if the block is given,
45
+ # each row of the result set will be yielded to it. Otherwise, the results
46
+ # are returned as an array.
47
+ def get_query_pragma( name, *parms, &block ) # :yields: row
48
+ if parms.empty?
49
+ execute( "PRAGMA #{name}", &block )
50
+ else
51
+ args = "'" + parms.join("','") + "'"
52
+ execute( "PRAGMA #{name}( #{args} )", &block )
53
+ end
54
+ end
55
+ private :get_query_pragma
56
+
57
+ # Return the value of the given pragma.
58
+ def get_enum_pragma( name )
59
+ get_first_value( "PRAGMA #{name}" )
60
+ end
61
+ private :get_enum_pragma
44
62
 
45
- needs_tweak_default = version_compare(driver.libversion, "3.3.7") > 0
63
+ # Set the value of the given pragma to +mode+. The +mode+ parameter must
64
+ # conform to one of the values in the given +enum+ array. Each entry in
65
+ # the array is another array comprised of elements in the enumeration that
66
+ # have duplicate values. See #synchronous, #default_synchronous,
67
+ # #temp_store, and #default_temp_store for usage examples.
68
+ def set_enum_pragma( name, mode, enums )
69
+ match = enums.find { |p| p.find { |i| i.to_s.downcase == mode.to_s.downcase } }
70
+ raise Exception,
71
+ "unrecognized #{name} #{mode.inspect}" unless match
72
+ execute( "PRAGMA #{name}='#{match.first.upcase}'" )
73
+ end
74
+ private :set_enum_pragma
75
+
76
+ # Returns the value of the given pragma as an integer.
77
+ def get_int_pragma( name )
78
+ get_first_value( "PRAGMA #{name}" ).to_i
79
+ end
80
+ private :get_int_pragma
81
+
82
+ # Set the value of the given pragma to the integer value of the +value+
83
+ # parameter.
84
+ def set_int_pragma( name, value )
85
+ execute( "PRAGMA #{name}=#{value.to_i}" )
86
+ end
87
+ private :set_int_pragma
88
+
89
+ # The enumeration of valid synchronous modes.
90
+ SYNCHRONOUS_MODES = [ [ 'full', 2 ], [ 'normal', 1 ], [ 'off', 0 ] ]
91
+
92
+ # The enumeration of valid temp store modes.
93
+ TEMP_STORE_MODES = [ [ 'default', 0 ], [ 'file', 1 ], [ 'memory', 2 ] ]
94
+
95
+ # Does an integrity check on the database. If the check fails, a
96
+ # SQLite3::Exception will be raised. Otherwise it
97
+ # returns silently.
98
+ def integrity_check
99
+ execute( "PRAGMA integrity_check" ) do |row|
100
+ raise Exception, row[0] if row[0] != "ok"
101
+ end
102
+ end
103
+
104
+ def auto_vacuum
105
+ get_boolean_pragma "auto_vacuum"
106
+ end
107
+
108
+ def auto_vacuum=( mode )
109
+ set_boolean_pragma "auto_vacuum", mode
110
+ end
111
+
112
+ def schema_cookie
113
+ get_int_pragma "schema_cookie"
114
+ end
115
+
116
+ def schema_cookie=( cookie )
117
+ set_int_pragma "schema_cookie", cookie
118
+ end
119
+
120
+ def user_cookie
121
+ get_int_pragma "user_cookie"
122
+ end
123
+
124
+ def user_cookie=( cookie )
125
+ set_int_pragma "user_cookie", cookie
126
+ end
127
+
128
+ def cache_size
129
+ get_int_pragma "cache_size"
130
+ end
131
+
132
+ def cache_size=( size )
133
+ set_int_pragma "cache_size", size
134
+ end
135
+
136
+ def default_cache_size
137
+ get_int_pragma "default_cache_size"
138
+ end
139
+
140
+ def default_cache_size=( size )
141
+ set_int_pragma "default_cache_size", size
142
+ end
143
+
144
+ def default_synchronous
145
+ get_enum_pragma "default_synchronous"
146
+ end
147
+
148
+ def default_synchronous=( mode )
149
+ set_enum_pragma "default_synchronous", mode, SYNCHRONOUS_MODES
150
+ end
151
+
152
+ def synchronous
153
+ get_enum_pragma "synchronous"
154
+ end
155
+
156
+ def synchronous=( mode )
157
+ set_enum_pragma "synchronous", mode, SYNCHRONOUS_MODES
158
+ end
159
+
160
+ def default_temp_store
161
+ get_enum_pragma "default_temp_store"
162
+ end
163
+
164
+ def default_temp_store=( mode )
165
+ set_enum_pragma "default_temp_store", mode, TEMP_STORE_MODES
166
+ end
167
+
168
+ def temp_store
169
+ get_enum_pragma "temp_store"
170
+ end
171
+
172
+ def temp_store=( mode )
173
+ set_enum_pragma "temp_store", mode, TEMP_STORE_MODES
174
+ end
175
+
176
+ def full_column_names
177
+ get_boolean_pragma "full_column_names"
178
+ end
179
+
180
+ def full_column_names=( mode )
181
+ set_boolean_pragma "full_column_names", mode
182
+ end
183
+
184
+ def parser_trace
185
+ get_boolean_pragma "parser_trace"
186
+ end
187
+
188
+ def parser_trace=( mode )
189
+ set_boolean_pragma "parser_trace", mode
190
+ end
191
+
192
+ def vdbe_trace
193
+ get_boolean_pragma "vdbe_trace"
194
+ end
195
+
196
+ def vdbe_trace=( mode )
197
+ set_boolean_pragma "vdbe_trace", mode
198
+ end
199
+
200
+ def database_list( &block ) # :yields: row
201
+ get_query_pragma "database_list", &block
202
+ end
203
+
204
+ def foreign_key_list( table, &block ) # :yields: row
205
+ get_query_pragma "foreign_key_list", table, &block
206
+ end
207
+
208
+ def index_info( index, &block ) # :yields: row
209
+ get_query_pragma "index_info", index, &block
210
+ end
211
+
212
+ def index_list( table, &block ) # :yields: row
213
+ get_query_pragma "index_list", table, &block
214
+ end
215
+
216
+ ###
217
+ # Returns information about +table+. Yields each row of table information
218
+ # if a block is provided.
219
+ def table_info table
220
+ stmt = prepare "PRAGMA table_info(#{table})"
221
+ columns = stmt.columns
222
+
223
+ needs_tweak_default =
224
+ version_compare(SQLite3.libversion.to_s, "3.3.7") > 0
46
225
 
47
226
  result = [] unless block_given?
48
- rows.each do |row|
49
- new_row = {}
50
- columns.each_with_index do |name, index|
51
- new_row[name] = row[index]
227
+ stmt.each do |row|
228
+ new_row = Hash[columns.zip(row)]
229
+
230
+ # FIXME: This should be removed but is required for older versions
231
+ # of rails
232
+ if(Object.const_defined?(:ActiveRecord))
233
+ new_row['notnull'] = new_row['notnull'].to_s
52
234
  end
53
235
 
54
236
  tweak_default(new_row) if needs_tweak_default
@@ -59,39 +241,40 @@ module SQLite3
59
241
  result << new_row
60
242
  end
61
243
  end
244
+ stmt.close
62
245
 
63
246
  result
64
247
  end
65
248
 
66
249
  private
67
250
 
68
- # Compares two version strings
69
- def version_compare(v1, v2)
70
- v1 = v1.split(".").map { |i| i.to_i }
71
- v2 = v2.split(".").map { |i| i.to_i }
72
- parts = [v1.length, v2.length].max
73
- v1.push 0 while v1.length < parts
74
- v2.push 0 while v2.length < parts
75
- v1.zip(v2).each do |a,b|
76
- return -1 if a < b
77
- return 1 if a > b
251
+ # Compares two version strings
252
+ def version_compare(v1, v2)
253
+ v1 = v1.split(".").map { |i| i.to_i }
254
+ v2 = v2.split(".").map { |i| i.to_i }
255
+ parts = [v1.length, v2.length].max
256
+ v1.push 0 while v1.length < parts
257
+ v2.push 0 while v2.length < parts
258
+ v1.zip(v2).each do |a,b|
259
+ return -1 if a < b
260
+ return 1 if a > b
261
+ end
262
+ return 0
78
263
  end
79
- return 0
80
- end
81
-
82
- # Since SQLite 3.3.8, the table_info pragma has returned the default
83
- # value of the row as a quoted SQL value. This method essentially
84
- # unquotes those values.
85
- def tweak_default(hash)
86
- case hash["dflt_value"]
87
- when /^null$/i
88
- hash["dflt_value"] = nil
89
- when /^'(.*)'$/
90
- hash["dflt_value"] = $1.gsub(/''/, "'")
91
- when /^"(.*)"$/
92
- hash["dflt_value"] = $1.gsub(/""/, '"')
264
+
265
+ # Since SQLite 3.3.8, the table_info pragma has returned the default
266
+ # value of the row as a quoted SQL value. This method essentially
267
+ # unquotes those values.
268
+ def tweak_default(hash)
269
+ case hash["dflt_value"]
270
+ when /^null$/i
271
+ hash["dflt_value"] = nil
272
+ when /^'(.*)'$/
273
+ hash["dflt_value"] = $1.gsub(/''/, "'")
274
+ when /^"(.*)"$/
275
+ hash["dflt_value"] = $1.gsub(/""/, '"')
276
+ end
93
277
  end
94
- end
95
278
  end
96
279
 
97
280
  end
@@ -1,34 +1,5 @@
1
- # Copyright (c) 2004, Jamis Buck (jamis@jamisbuck.org)
2
- # All rights reserved.
3
-
4
- # Redistribution and use in source and binary forms, with or without
5
- # modification, are permitted provided that the following conditions
6
- # are met:
7
-
8
- # * Redistributions of source code must retain the above copyright
9
- # notice, this list of conditions and the following disclaimer.
10
-
11
- # * Redistributions in binary form must reproduce the above copyright
12
- # notice, this list of conditions and the following disclaimer in
13
- # the documentation and/or other materials provided with the
14
- # distribution.
15
-
16
- # * The names of its contributors may not be used to endorse or
17
- # promote products derived from this software without specific prior
18
- # written permission.
19
-
20
- # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21
- # "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22
- # LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
23
- # FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
24
- # COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
25
- # INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
26
- # BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
27
- # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
28
- # CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29
- # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
30
- # ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31
- # POSSIBILITY OF SUCH DAMAGE.
1
+ require 'sqlite3/constants'
2
+ require 'sqlite3/errors'
32
3
 
33
4
  module SQLite3
34
5
 
@@ -60,47 +31,22 @@ module SQLite3
60
31
 
61
32
  # Create a new ResultSet attached to the given database, using the
62
33
  # given sql text.
63
- def initialize(db, stmt, utf_16 = false)
64
- @db = db
65
- @driver = @db.driver
34
+ def initialize db, stmt
35
+ @db = db
66
36
  @stmt = stmt
67
- @utf_16 = utf_16
68
- commence
69
37
  end
70
38
 
71
- # A convenience method for compiling the virtual machine and stepping
72
- # to the first row of the result set.
73
- def commence
74
- result = @driver.step(@stmt.handle)
75
- if result == Constants::ErrorCode::ERROR
76
- @driver.reset(@stmt.handle)
77
- end
78
- check result
79
- @first_row = true
80
- end
81
- private :commence
82
-
83
- def check(result)
84
- @eof = (result == Constants::ErrorCode::DONE)
85
- found = (result == Constants::ErrorCode::ROW)
86
- Error.check(result, @db) unless @eof || found
87
- end
88
- private :check
89
-
90
39
  # Reset the cursor, so that a result set which has reached end-of-file
91
40
  # can be rewound and reiterated.
92
- def reset(*bind_params)
93
- @stmt.must_be_open!
94
- @stmt.reset!(false)
95
- @driver.reset(@stmt.handle)
96
- @stmt.bind_params(*bind_params)
41
+ def reset( *bind_params )
42
+ @stmt.reset!
43
+ @stmt.bind_params( *bind_params )
97
44
  @eof = false
98
- commence
99
45
  end
100
46
 
101
47
  # Query whether the cursor has reached the end of the result set or not.
102
48
  def eof?
103
- @eof
49
+ @stmt.done?
104
50
  end
105
51
 
106
52
  # Obtain the next row from the cursor. If there are no more rows to be
@@ -117,67 +63,39 @@ module SQLite3
117
63
  # For hashes, the column names are the keys of the hash, and the column
118
64
  # types are accessible via the +types+ property.
119
65
  def next
120
- return nil if @eof
121
-
122
- @stmt.must_be_open!
66
+ row = @stmt.step
67
+ return nil if @stmt.done?
123
68
 
124
- unless @first_row
125
- result = @driver.step(@stmt.handle)
126
- check result
127
- end
128
-
129
- @first_row = false
130
-
131
- unless @eof
132
- row = []
133
- @driver.data_count(@stmt.handle).times do |column|
134
- type = @driver.column_type(@stmt.handle, column)
135
-
136
- if type == Constants::ColumnType::NULL
137
- row << nil
138
- elsif type == Constants::ColumnType::BLOB
139
- row << @driver.column_blob(@stmt.handle, column)
140
- elsif type == Constants::ColumnType::INTEGER
141
- row << @driver.column_int64(@stmt.handle, column)
142
- elsif type == Constants::ColumnType::FLOAT
143
- row << @driver.column_double(@stmt.handle, column)
144
- else
145
- row << @driver.column_text(@stmt.handle, column, @utf_16)
146
- end
69
+ if @db.type_translation
70
+ row = @stmt.types.zip(row).map do |type, value|
71
+ @db.translator.translate( type, value )
147
72
  end
73
+ end
148
74
 
149
- # if @db.type_translation
150
- # row = @stmt.types.zip(row).map do |type, value|
151
- # @db.translator.translate(type, value)
152
- # end
153
- # end
154
-
155
- if @db.results_as_hash
156
- new_row = HashWithTypes[ *(@stmt.columns.zip(row).to_a.flatten) ]
157
- row.each_with_index { |value,idx| new_row[idx] = value }
158
- row = new_row
75
+ if @db.results_as_hash
76
+ new_row = HashWithTypes[*@stmt.columns.zip(row).flatten]
77
+ row.each_with_index { |value,idx|
78
+ new_row[idx] = value
79
+ }
80
+ row = new_row
81
+ else
82
+ if row.respond_to?(:fields)
83
+ row = ArrayWithTypes.new(row)
159
84
  else
160
- if row.respond_to?(:fields)
161
- row = ArrayWithTypes.new(row)
162
- else
163
- row = ArrayWithTypesAndFields.new(row)
164
- end
165
- row.fields = @stmt.columns
85
+ row = ArrayWithTypesAndFields.new(row)
166
86
  end
167
-
168
- # row.types = @stmt.types
169
-
170
- return row
87
+ row.fields = @stmt.columns
171
88
  end
172
89
 
173
- nil
90
+ row.types = @stmt.types
91
+ row
174
92
  end
175
93
 
176
94
  # Required by the Enumerable mixin. Provides an internal iterator over the
177
95
  # rows of the result set.
178
- def each
179
- while row=self.next
180
- yield row
96
+ def each( &block )
97
+ while node = self.next
98
+ yield node
181
99
  end
182
100
  end
183
101