extralite 0.2.1 → 0.3

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: edc158d606131bab091a3a9053a00a540728e53b12aa6165ec69f3611d5c449a
4
- data.tar.gz: 826223da4bcd18ff70bc5d6f81c08c2ae8aa486387cd2277d0275268a1917853
3
+ metadata.gz: 8063960fd539fc0384882cf017572baefe79b9e29591d03c790951c6fad4fac0
4
+ data.tar.gz: 9f1c5be233721502dd0b97ffef2d195912ec029eccee977b16ca67b567299f04
5
5
  SHA512:
6
- metadata.gz: c5fa113e40bf4ed2f4b2d89267386cd901e7346462ae080a8ba9771c0b8da2d95ce0473e584031210c02b4b3e9785d607afb8886da1c8d75fcadb9bb5022181d
7
- data.tar.gz: df5a8b1025cd8278b5a929415bd62581d79b9769cd57f0353b3163fdb5d3f81a2c9ccd23901a4dade805e58add9436671e728aaead945ffed8239cb4dc619e17
6
+ metadata.gz: b674b89217ff2231d7c48f7d93917c29e84bbcb8b240216854a87b85d0c4ca5588fe821d0e6db406df04adc5c0b29aca4e24335349084e45a7d98449119a981f
7
+ data.tar.gz: 3f33b7ef708052e51033e2ca38f2323c8b78f95eecda2c328fba506762831e260ae03a66ff5944e4b961b22906aa42740ebdeaad1ff233f1141daded682a6d47
data/CHANGELOG.md CHANGED
@@ -1,4 +1,8 @@
1
- ## 0.2 2021-05-24
1
+ ## 0.3 2021-05-24
2
+
3
+ - Add support for running multiple statements
4
+
5
+ ## 0.2 2021-05-23
2
6
 
3
7
  - Implement `Database#transaction_active?`
4
8
  - Add tests
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- extralite (0.2.1)
4
+ extralite (0.3)
5
5
 
6
6
  GEM
7
7
  remote: https://rubygems.org/
@@ -123,6 +123,32 @@ static inline VALUE row_to_hash(sqlite3_stmt *stmt, int column_count, VALUE colu
123
123
  return row;
124
124
  }
125
125
 
126
+ inline void prepare_multi_stmt(sqlite3 *db, sqlite3_stmt **stmt, VALUE sql) {
127
+ const char *rest = 0;
128
+ const char *ptr = RSTRING_PTR(sql);
129
+ const char *end = ptr + RSTRING_LEN(sql);
130
+ while (1) {
131
+ int rc = sqlite3_prepare(db, ptr, end - ptr, stmt, &rest);
132
+ if (rc) {
133
+ sqlite3_finalize(*stmt);
134
+ rb_raise(cError, "%s", sqlite3_errmsg(db));
135
+ }
136
+
137
+ if (rest == end) return;
138
+
139
+ // perform current query, but discard its results
140
+ rc = sqlite3_step(*stmt);
141
+ sqlite3_finalize(*stmt);
142
+ switch (rc) {
143
+ case SQLITE_BUSY:
144
+ rb_raise(cError, "Database is busy");
145
+ case SQLITE_ERROR:
146
+ rb_raise(cError, "%s", sqlite3_errmsg(db));
147
+ }
148
+ ptr = rest;
149
+ }
150
+ }
151
+
126
152
  VALUE Database_query_hash(int argc, VALUE *argv, VALUE self) {
127
153
  int rc;
128
154
  sqlite3_stmt* stmt;
@@ -138,13 +164,7 @@ VALUE Database_query_hash(int argc, VALUE *argv, VALUE self) {
138
164
  sql = argv[0];
139
165
  GetDatabase(self, db);
140
166
 
141
- rc = sqlite3_prepare(db->sqlite3_db, RSTRING_PTR(sql), RSTRING_LEN(sql), &stmt, 0);
142
- if (rc) {
143
- sqlite3_finalize(stmt);
144
- rb_raise(cError, "%s", sqlite3_errmsg(db->sqlite3_db));
145
- return Qnil;
146
- }
147
-
167
+ prepare_multi_stmt(db->sqlite3_db, &stmt, sql);
148
168
  bind_all_parameters(stmt, argc, argv);
149
169
  column_count = sqlite3_column_count(stmt);
150
170
  column_names = get_column_names(stmt, column_count);
@@ -202,14 +222,7 @@ VALUE Database_query_ary(int argc, VALUE *argv, VALUE self) {
202
222
  sql = argv[0];
203
223
  GetDatabase(self, db);
204
224
 
205
- rc = sqlite3_prepare(db->sqlite3_db, RSTRING_PTR(sql), RSTRING_LEN(sql), &stmt, 0);
206
- if (rc) {
207
- fprintf(stderr, "Failed to prepare statement: %s\n", sqlite3_errmsg(db->sqlite3_db));
208
- sqlite3_finalize(stmt);
209
- // TODO: raise error
210
- return Qfalse;
211
- }
212
-
225
+ prepare_multi_stmt(db->sqlite3_db, &stmt, sql);
213
226
  bind_all_parameters(stmt, argc, argv);
214
227
  column_count = sqlite3_column_count(stmt);
215
228
 
@@ -225,10 +238,13 @@ step:
225
238
  case SQLITE_DONE:
226
239
  break;
227
240
  case SQLITE_BUSY:
241
+ sqlite3_finalize(stmt);
228
242
  rb_raise(cError, "Database is busy");
229
243
  case SQLITE_ERROR:
244
+ sqlite3_finalize(stmt);
230
245
  rb_raise(cError, "%s", sqlite3_errmsg(db->sqlite3_db));
231
246
  default:
247
+ sqlite3_finalize(stmt);
232
248
  rb_raise(cError, "Invalid return code for sqlite3_step: %d", rc);
233
249
  }
234
250
  sqlite3_finalize(stmt);
@@ -251,14 +267,7 @@ VALUE Database_query_single_column(int argc, VALUE *argv, VALUE self) {
251
267
  sql = argv[0];
252
268
  GetDatabase(self, db);
253
269
 
254
- rc = sqlite3_prepare(db->sqlite3_db, RSTRING_PTR(sql), RSTRING_LEN(sql), &stmt, 0);
255
- if (rc) {
256
- fprintf(stderr, "Failed to prepare statement: %s\n", sqlite3_errmsg(db->sqlite3_db));
257
- sqlite3_finalize(stmt);
258
- // TODO: raise error
259
- return Qfalse;
260
- }
261
-
270
+ prepare_multi_stmt(db->sqlite3_db, &stmt, sql);
262
271
  bind_all_parameters(stmt, argc, argv);
263
272
  column_count = sqlite3_column_count(stmt);
264
273
  if (column_count != 1)
@@ -268,6 +277,7 @@ VALUE Database_query_single_column(int argc, VALUE *argv, VALUE self) {
268
277
  if (!yield_to_block) result = rb_ary_new();
269
278
  step:
270
279
  rc = sqlite3_step(stmt);
280
+ printf("rc=%d\n", rc);
271
281
  switch (rc) {
272
282
  case SQLITE_ROW:
273
283
  value = get_column_value(stmt, 0, sqlite3_column_type(stmt, 0));
@@ -276,10 +286,13 @@ step:
276
286
  case SQLITE_DONE:
277
287
  break;
278
288
  case SQLITE_BUSY:
289
+ sqlite3_finalize(stmt);
279
290
  rb_raise(cError, "Database is busy");
280
291
  case SQLITE_ERROR:
292
+ sqlite3_finalize(stmt);
281
293
  rb_raise(cError, "%s", sqlite3_errmsg(db->sqlite3_db));
282
294
  default:
295
+ sqlite3_finalize(stmt);
283
296
  rb_raise(cError, "Invalid return code for sqlite3_step: %d", rc);
284
297
  }
285
298
 
@@ -301,14 +314,7 @@ VALUE Database_query_single_value(int argc, VALUE *argv, VALUE self) {
301
314
  sql = argv[0];
302
315
  GetDatabase(self, db);
303
316
 
304
- rc = sqlite3_prepare(db->sqlite3_db, RSTRING_PTR(sql), RSTRING_LEN(sql), &stmt, 0);
305
- if (rc) {
306
- fprintf(stderr, "Failed to prepare statement: %s\n", sqlite3_errmsg(db->sqlite3_db));
307
- sqlite3_finalize(stmt);
308
- // TODO: raise error
309
- return Qfalse;
310
- }
311
-
317
+ prepare_multi_stmt(db->sqlite3_db, &stmt, sql);
312
318
  bind_all_parameters(stmt, argc, argv);
313
319
  column_count = sqlite3_column_count(stmt);
314
320
  if (column_count != 1)
@@ -1,3 +1,3 @@
1
1
  module Extralite
2
- VERSION = '0.2.1'
2
+ VERSION = '0.3'
3
3
  end
@@ -48,4 +48,10 @@ class DatabaseTest < MiniTest::Test
48
48
  @db.query('rollback')
49
49
  assert_equal false, @db.transaction_active?
50
50
  end
51
+
52
+ def test_multiple_statements
53
+ @db.query("insert into t values ('a', 'b', 'c'); insert into t values ('d', 'e', 'f');")
54
+
55
+ assert_equal [1, 4, 'a', 'd'], @db.query_single_column('select x from t order by x')
56
+ end
51
57
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: extralite
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.1
4
+ version: '0.3'
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sharon Rosner
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2021-05-23 00:00:00.000000000 Z
11
+ date: 2021-05-24 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rake-compiler