sqlite3 1.3.11-x64-mingw32 → 1.5.0.rc1-x64-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 +5 -5
- data/.gemtest +0 -0
- data/{API_CHANGES.rdoc → API_CHANGES.md} +3 -4
- data/CHANGELOG.md +419 -0
- data/CONTRIBUTING.md +24 -0
- data/Gemfile +2 -15
- data/LICENSE-DEPENDENCIES +20 -0
- data/README.md +233 -0
- data/ext/sqlite3/aggregator.c +273 -0
- data/ext/sqlite3/aggregator.h +12 -0
- data/ext/sqlite3/database.c +210 -182
- data/ext/sqlite3/database.h +2 -0
- data/ext/sqlite3/exception.c +6 -2
- data/ext/sqlite3/extconf.rb +148 -39
- data/ext/sqlite3/sqlite3.c +67 -1
- data/ext/sqlite3/sqlite3_ruby.h +0 -7
- data/ext/sqlite3/statement.c +15 -20
- data/faq/faq.md +431 -0
- data/faq/faq.yml +1 -1
- data/lib/sqlite3/2.6/sqlite3_native.so +0 -0
- data/lib/sqlite3/2.7/sqlite3_native.so +0 -0
- data/lib/sqlite3/3.0/sqlite3_native.so +0 -0
- data/lib/sqlite3/constants.rb +2 -1
- data/lib/sqlite3/database.rb +209 -58
- data/lib/sqlite3/errors.rb +1 -10
- data/lib/sqlite3/pragmas.rb +372 -57
- data/lib/sqlite3/resultset.rb +2 -10
- data/lib/sqlite3/statement.rb +2 -1
- data/lib/sqlite3/translator.rb +1 -1
- data/lib/sqlite3/version.rb +4 -4
- data/lib/sqlite3.rb +5 -0
- data/test/helper.rb +9 -0
- data/test/test_database.rb +180 -9
- data/test/test_database_flags.rb +95 -0
- data/test/test_database_readonly.rb +9 -2
- data/test/test_database_readwrite.rb +41 -0
- data/test/test_integration.rb +12 -77
- data/test/test_integration_aggregate.rb +336 -0
- data/test/test_integration_resultset.rb +0 -17
- data/test/test_sqlite3.rb +16 -0
- data/test/test_statement.rb +12 -9
- metadata +55 -84
- data/CHANGELOG.rdoc +0 -287
- data/Manifest.txt +0 -52
- data/README.rdoc +0 -101
- data/Rakefile +0 -10
- data/lib/sqlite3/2.0/sqlite3_native.so +0 -0
- data/lib/sqlite3/2.1/sqlite3_native.so +0 -0
- data/lib/sqlite3/2.2/sqlite3_native.so +0 -0
- data/setup.rb +0 -1333
- data/tasks/faq.rake +0 -9
- data/tasks/gem.rake +0 -38
- data/tasks/native.rake +0 -52
- data/tasks/vendor_sqlite3.rake +0 -97
data/lib/sqlite3/database.rb
CHANGED
@@ -54,12 +54,73 @@ module SQLite3
|
|
54
54
|
# as hashes or not. By default, rows are returned as arrays.
|
55
55
|
attr_accessor :results_as_hash
|
56
56
|
|
57
|
+
# call-seq: SQLite3::Database.new(file, options = {})
|
58
|
+
#
|
59
|
+
# Create a new Database object that opens the given file. If utf16
|
60
|
+
# is +true+, the filename is interpreted as a UTF-16 encoded string.
|
61
|
+
#
|
62
|
+
# By default, the new database will return result rows as arrays
|
63
|
+
# (#results_as_hash) and has type translation disabled (#type_translation=).
|
64
|
+
|
65
|
+
def initialize file, options = {}, zvfs = nil
|
66
|
+
mode = Constants::Open::READWRITE | Constants::Open::CREATE
|
67
|
+
|
68
|
+
file = file.to_path if file.respond_to? :to_path
|
69
|
+
if file.encoding == ::Encoding::UTF_16LE || file.encoding == ::Encoding::UTF_16BE || options[:utf16]
|
70
|
+
open16 file
|
71
|
+
else
|
72
|
+
# The three primary flag values for sqlite3_open_v2 are:
|
73
|
+
# SQLITE_OPEN_READONLY
|
74
|
+
# SQLITE_OPEN_READWRITE
|
75
|
+
# SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE -- always used for sqlite3_open and sqlite3_open16
|
76
|
+
mode = Constants::Open::READONLY if options[:readonly]
|
77
|
+
|
78
|
+
if options[:readwrite]
|
79
|
+
raise "conflicting options: readonly and readwrite" if options[:readonly]
|
80
|
+
mode = Constants::Open::READWRITE
|
81
|
+
end
|
82
|
+
|
83
|
+
if options[:flags]
|
84
|
+
if options[:readonly] || options[:readwrite]
|
85
|
+
raise "conflicting options: flags with readonly and/or readwrite"
|
86
|
+
end
|
87
|
+
mode = options[:flags]
|
88
|
+
end
|
89
|
+
|
90
|
+
open_v2 file.encode("utf-8"), mode, zvfs
|
91
|
+
|
92
|
+
if options[:strict]
|
93
|
+
disable_quirk_mode
|
94
|
+
end
|
95
|
+
end
|
96
|
+
|
97
|
+
@tracefunc = nil
|
98
|
+
@authorizer = nil
|
99
|
+
@encoding = nil
|
100
|
+
@busy_handler = nil
|
101
|
+
@collations = {}
|
102
|
+
@functions = {}
|
103
|
+
@results_as_hash = options[:results_as_hash]
|
104
|
+
@type_translation = options[:type_translation]
|
105
|
+
@type_translator = make_type_translator @type_translation
|
106
|
+
@readonly = mode & Constants::Open::READONLY != 0
|
107
|
+
|
108
|
+
if block_given?
|
109
|
+
begin
|
110
|
+
yield self
|
111
|
+
ensure
|
112
|
+
close
|
113
|
+
end
|
114
|
+
end
|
115
|
+
end
|
116
|
+
|
57
117
|
def type_translation= value # :nodoc:
|
58
118
|
warn(<<-eowarn) if $VERBOSE
|
59
119
|
#{caller[0]} is calling SQLite3::Database#type_translation=
|
60
120
|
SQLite3::Database#type_translation= is deprecated and will be removed
|
61
121
|
in version 2.0.0.
|
62
122
|
eowarn
|
123
|
+
@type_translator = make_type_translator value
|
63
124
|
@type_translation = value
|
64
125
|
end
|
65
126
|
attr_reader :type_translation # :nodoc:
|
@@ -98,6 +159,13 @@ in version 2.0.0.
|
|
98
159
|
end
|
99
160
|
end
|
100
161
|
|
162
|
+
# Returns the filename for the database named +db_name+. +db_name+ defaults
|
163
|
+
# to "main". Main return `nil` or an empty string if the database is
|
164
|
+
# temporary or in-memory.
|
165
|
+
def filename db_name = 'main'
|
166
|
+
db_filename db_name
|
167
|
+
end
|
168
|
+
|
101
169
|
# Executes the given SQL statement. If additional parameters are given,
|
102
170
|
# they are treated as bind variables, and are bound to the placeholders in
|
103
171
|
# the query.
|
@@ -113,10 +181,6 @@ in version 2.0.0.
|
|
113
181
|
# See also #execute2, #query, and #execute_batch for additional ways of
|
114
182
|
# executing statements.
|
115
183
|
def execute sql, bind_vars = [], *args, &block
|
116
|
-
# FIXME: This is a terrible hack and should be removed but is required
|
117
|
-
# for older versions of rails
|
118
|
-
hack = Object.const_defined?(:ActiveRecord) && sql =~ /^PRAGMA index_list/
|
119
|
-
|
120
184
|
if bind_vars.nil? || !args.empty?
|
121
185
|
if args.empty?
|
122
186
|
bind_vars = []
|
@@ -133,30 +197,14 @@ Support for bind parameters as *args will be removed in 2.0.0.
|
|
133
197
|
|
134
198
|
prepare( sql ) do |stmt|
|
135
199
|
stmt.bind_params(bind_vars)
|
136
|
-
|
137
|
-
stmt = ResultSet.new(self, stmt).to_a if type_translation
|
200
|
+
stmt = ResultSet.new self, stmt
|
138
201
|
|
139
202
|
if block_given?
|
140
203
|
stmt.each do |row|
|
141
|
-
|
142
|
-
yield type_translation ? row : ordered_map_for(columns, row)
|
143
|
-
else
|
144
|
-
yield row
|
145
|
-
end
|
204
|
+
yield row
|
146
205
|
end
|
147
206
|
else
|
148
|
-
|
149
|
-
stmt.map { |row|
|
150
|
-
h = type_translation ? row : ordered_map_for(columns, row)
|
151
|
-
|
152
|
-
# FIXME UGH TERRIBLE HACK!
|
153
|
-
h['unique'] = h['unique'].to_s if hack
|
154
|
-
|
155
|
-
h
|
156
|
-
}
|
157
|
-
else
|
158
|
-
stmt.to_a
|
159
|
-
end
|
207
|
+
stmt.to_a
|
160
208
|
end
|
161
209
|
end
|
162
210
|
end
|
@@ -192,6 +240,9 @@ Support for bind parameters as *args will be removed in 2.0.0.
|
|
192
240
|
#
|
193
241
|
# This always returns +nil+, making it unsuitable for queries that return
|
194
242
|
# rows.
|
243
|
+
#
|
244
|
+
# See also #execute_batch2 for additional ways of
|
245
|
+
# executing statements.
|
195
246
|
def execute_batch( sql, bind_vars = [], *args )
|
196
247
|
# FIXME: remove this stuff later
|
197
248
|
unless [Array, Hash].include?(bind_vars.class)
|
@@ -236,8 +287,32 @@ Support for this behavior will be removed in version 2.0.0.
|
|
236
287
|
nil
|
237
288
|
end
|
238
289
|
|
290
|
+
# Executes all SQL statements in the given string. By contrast, the other
|
291
|
+
# means of executing queries will only execute the first statement in the
|
292
|
+
# string, ignoring all subsequent statements. This will execute each one
|
293
|
+
# in turn. Bind parameters cannot be passed to #execute_batch2.
|
294
|
+
#
|
295
|
+
# If a query is made, all values will be returned as strings.
|
296
|
+
# If no query is made, an empty array will be returned.
|
297
|
+
#
|
298
|
+
# Because all values except for 'NULL' are returned as strings,
|
299
|
+
# a block can be passed to parse the values accordingly.
|
300
|
+
#
|
301
|
+
# See also #execute_batch for additional ways of
|
302
|
+
# executing statements.
|
303
|
+
def execute_batch2(sql, &block)
|
304
|
+
if block_given?
|
305
|
+
result = exec_batch(sql, @results_as_hash)
|
306
|
+
result.map do |val|
|
307
|
+
yield val
|
308
|
+
end
|
309
|
+
else
|
310
|
+
exec_batch(sql, @results_as_hash)
|
311
|
+
end
|
312
|
+
end
|
313
|
+
|
239
314
|
# This is a convenience method for creating a statement, binding
|
240
|
-
#
|
315
|
+
# parameters to it, and calling execute:
|
241
316
|
#
|
242
317
|
# result = db.query( "select * from foo where a=?", [5])
|
243
318
|
# # is the same as
|
@@ -289,7 +364,11 @@ Support for this will be removed in version 2.0.0.
|
|
289
364
|
#
|
290
365
|
# See also #get_first_row.
|
291
366
|
def get_first_value( sql, *bind_vars )
|
292
|
-
|
367
|
+
query( sql, bind_vars ) do |rs|
|
368
|
+
if (row = rs.next)
|
369
|
+
return @results_as_hash ? row[rs.columns[0]] : row[0]
|
370
|
+
end
|
371
|
+
end
|
293
372
|
nil
|
294
373
|
end
|
295
374
|
|
@@ -318,8 +397,8 @@ Support for this will be removed in version 2.0.0.
|
|
318
397
|
# end
|
319
398
|
#
|
320
399
|
# puts db.get_first_value( "select maim(name) from table" )
|
321
|
-
def create_function name, arity, text_rep=Constants::TextRep::
|
322
|
-
|
400
|
+
def create_function name, arity, text_rep=Constants::TextRep::UTF8, &block
|
401
|
+
define_function_with_flags(name, text_rep) do |*args|
|
323
402
|
fp = FunctionProxy.new
|
324
403
|
block.call(fp, *args)
|
325
404
|
fp.result
|
@@ -366,39 +445,52 @@ Support for this will be removed in version 2.0.0.
|
|
366
445
|
def create_aggregate( name, arity, step=nil, finalize=nil,
|
367
446
|
text_rep=Constants::TextRep::ANY, &block )
|
368
447
|
|
369
|
-
|
448
|
+
proxy = Class.new do
|
370
449
|
def self.step( &block )
|
371
|
-
define_method(:
|
450
|
+
define_method(:step_with_ctx, &block)
|
372
451
|
end
|
373
452
|
|
374
453
|
def self.finalize( &block )
|
375
|
-
define_method(:
|
454
|
+
define_method(:finalize_with_ctx, &block)
|
376
455
|
end
|
377
456
|
end
|
378
457
|
|
379
458
|
if block_given?
|
380
|
-
|
459
|
+
proxy.instance_eval(&block)
|
381
460
|
else
|
382
|
-
|
383
|
-
define_method(:
|
384
|
-
define_method(:
|
461
|
+
proxy.class_eval do
|
462
|
+
define_method(:step_with_ctx, step)
|
463
|
+
define_method(:finalize_with_ctx, finalize)
|
385
464
|
end
|
386
465
|
end
|
387
466
|
|
388
|
-
proxy
|
389
|
-
|
390
|
-
|
467
|
+
proxy.class_eval do
|
468
|
+
# class instance variables
|
469
|
+
@name = name
|
470
|
+
@arity = arity
|
471
|
+
|
472
|
+
def self.name
|
473
|
+
@name
|
474
|
+
end
|
475
|
+
|
476
|
+
def self.arity
|
477
|
+
@arity
|
478
|
+
end
|
479
|
+
|
480
|
+
def initialize
|
481
|
+
@ctx = FunctionProxy.new
|
482
|
+
end
|
391
483
|
|
392
484
|
def step( *args )
|
393
|
-
|
485
|
+
step_with_ctx(@ctx, *args)
|
394
486
|
end
|
395
487
|
|
396
488
|
def finalize
|
397
|
-
|
489
|
+
finalize_with_ctx(@ctx)
|
490
|
+
@ctx.result
|
398
491
|
end
|
399
|
-
|
400
|
-
proxy
|
401
|
-
define_aggregator(name, proxy)
|
492
|
+
end
|
493
|
+
define_aggregator2(proxy, name)
|
402
494
|
end
|
403
495
|
|
404
496
|
# This is another approach to creating an aggregate function (see
|
@@ -449,29 +541,75 @@ Support for this will be removed in version 2.0.0.
|
|
449
541
|
# db.create_aggregate_handler( LengthsAggregateHandler )
|
450
542
|
# puts db.get_first_value( "select lengths(name) from A" )
|
451
543
|
def create_aggregate_handler( handler )
|
452
|
-
|
453
|
-
|
454
|
-
|
455
|
-
|
544
|
+
# This is a compatibility shim so the (basically pointless) FunctionProxy
|
545
|
+
# "ctx" object is passed as first argument to both step() and finalize().
|
546
|
+
# Now its up to the library user whether he prefers to store his
|
547
|
+
# temporaries as instance variables or fields in the FunctionProxy.
|
548
|
+
# The library user still must set the result value with
|
549
|
+
# FunctionProxy.result= as there is no backwards compatible way to
|
550
|
+
# change this.
|
551
|
+
proxy = Class.new(handler) do
|
552
|
+
def initialize
|
553
|
+
super
|
554
|
+
@fp = FunctionProxy.new
|
456
555
|
end
|
457
556
|
|
458
557
|
def step( *args )
|
459
|
-
|
558
|
+
super(@fp, *args)
|
460
559
|
end
|
461
560
|
|
462
561
|
def finalize
|
463
|
-
|
464
|
-
@instance = nil
|
562
|
+
super(@fp)
|
465
563
|
@fp.result
|
466
564
|
end
|
565
|
+
end
|
566
|
+
define_aggregator2(proxy, proxy.name)
|
567
|
+
self
|
568
|
+
end
|
569
|
+
|
570
|
+
# Define an aggregate function named +name+ using a object template
|
571
|
+
# object +aggregator+. +aggregator+ must respond to +step+ and +finalize+.
|
572
|
+
# +step+ will be called with row information and +finalize+ must return the
|
573
|
+
# return value for the aggregator function.
|
574
|
+
#
|
575
|
+
# _API Change:_ +aggregator+ must also implement +clone+. The provided
|
576
|
+
# +aggregator+ object will serve as template that is cloned to provide the
|
577
|
+
# individual instances of the aggregate function. Regular ruby objects
|
578
|
+
# already provide a suitable +clone+.
|
579
|
+
# The functions arity is the arity of the +step+ method.
|
580
|
+
def define_aggregator( name, aggregator )
|
581
|
+
# Previously, this has been implemented in C. Now this is just yet
|
582
|
+
# another compatibility shim
|
583
|
+
proxy = Class.new do
|
584
|
+
@template = aggregator
|
585
|
+
@name = name
|
586
|
+
|
587
|
+
def self.template
|
588
|
+
@template
|
589
|
+
end
|
467
590
|
|
468
|
-
|
591
|
+
def self.name
|
592
|
+
@name
|
593
|
+
end
|
594
|
+
|
595
|
+
def self.arity
|
596
|
+
# this is what sqlite3_obj_method_arity did before
|
597
|
+
@template.method(:step).arity
|
598
|
+
end
|
599
|
+
|
600
|
+
def initialize
|
601
|
+
@klass = self.class.template.clone
|
602
|
+
end
|
469
603
|
|
470
|
-
def
|
471
|
-
@
|
604
|
+
def step(*args)
|
605
|
+
@klass.step(*args)
|
606
|
+
end
|
607
|
+
|
608
|
+
def finalize
|
609
|
+
@klass.finalize
|
472
610
|
end
|
473
611
|
end
|
474
|
-
|
612
|
+
define_aggregator2(proxy, name)
|
475
613
|
self
|
476
614
|
end
|
477
615
|
|
@@ -498,7 +636,7 @@ Support for this will be removed in version 2.0.0.
|
|
498
636
|
abort = false
|
499
637
|
begin
|
500
638
|
yield self
|
501
|
-
rescue
|
639
|
+
rescue
|
502
640
|
abort = true
|
503
641
|
raise
|
504
642
|
ensure
|
@@ -579,12 +717,25 @@ Support for this will be removed in version 2.0.0.
|
|
579
717
|
end
|
580
718
|
end
|
581
719
|
|
720
|
+
# Translates a +row+ of data from the database with the given +types+
|
721
|
+
def translate_from_db types, row
|
722
|
+
@type_translator.call types, row
|
723
|
+
end
|
724
|
+
|
582
725
|
private
|
583
726
|
|
584
|
-
|
585
|
-
|
586
|
-
|
587
|
-
|
727
|
+
NULL_TRANSLATOR = lambda { |_, row| row }
|
728
|
+
|
729
|
+
def make_type_translator should_translate
|
730
|
+
if should_translate
|
731
|
+
lambda { |types, row|
|
732
|
+
types.zip(row).map do |type, value|
|
733
|
+
translator.translate( type, value )
|
734
|
+
end
|
735
|
+
}
|
736
|
+
else
|
737
|
+
NULL_TRANSLATOR
|
738
|
+
end
|
588
739
|
end
|
589
740
|
end
|
590
741
|
end
|
data/lib/sqlite3/errors.rb
CHANGED
@@ -2,17 +2,8 @@ require 'sqlite3/constants'
|
|
2
2
|
|
3
3
|
module SQLite3
|
4
4
|
class Exception < ::StandardError
|
5
|
-
@code = 0
|
6
|
-
|
7
|
-
# The numeric error code that this exception represents.
|
8
|
-
def self.code
|
9
|
-
@code
|
10
|
-
end
|
11
|
-
|
12
5
|
# A convenience for accessing the error code for this exception.
|
13
|
-
|
14
|
-
self.class.code
|
15
|
-
end
|
6
|
+
attr_reader :code
|
16
7
|
end
|
17
8
|
|
18
9
|
class SQLException < Exception; end
|