Skip to content

Commit 7dc8122

Browse files
committed
Merge pull request #169 from jimflood/sqlite3_result_blob
BLOB function result when ASCII-8BIT encoding
2 parents 99aa5aa + 220c194 commit 7dc8122

File tree

2 files changed

+34
-7
lines changed

2 files changed

+34
-7
lines changed

ext/sqlite3/database.c

Lines changed: 26 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -288,7 +288,14 @@ static VALUE sqlite3val2rb(sqlite3_value * val)
288288
which is what we want, as blobs are binary
289289
*/
290290
int len = sqlite3_value_bytes(val);
291+
#ifdef HAVE_RUBY_ENCODING_H
291292
return rb_tainted_str_new((const char *)sqlite3_value_blob(val), len);
293+
#else
294+
/* When encoding is not available, make it class SQLite3::Blob. */
295+
VALUE strargv[1];
296+
strargv[0] = rb_tainted_str_new((const char *)sqlite3_value_blob(val), len);
297+
return rb_class_new_instance(1, strargv, cSqlite3Blob);
298+
#endif
292299
break;
293300
}
294301
case SQLITE_NULL:
@@ -322,12 +329,25 @@ static void set_sqlite3_func_result(sqlite3_context * ctx, VALUE result)
322329
sqlite3_result_double(ctx, NUM2DBL(result));
323330
break;
324331
case T_STRING:
325-
sqlite3_result_text(
326-
ctx,
327-
(const char *)StringValuePtr(result),
328-
(int)RSTRING_LEN(result),
329-
SQLITE_TRANSIENT
330-
);
332+
if(CLASS_OF(result) == cSqlite3Blob
333+
#ifdef HAVE_RUBY_ENCODING_H
334+
|| rb_enc_get_index(result) == rb_ascii8bit_encindex()
335+
#endif
336+
) {
337+
sqlite3_result_blob(
338+
ctx,
339+
(const void *)StringValuePtr(result),
340+
(int)RSTRING_LEN(result),
341+
SQLITE_TRANSIENT
342+
);
343+
} else {
344+
sqlite3_result_text(
345+
ctx,
346+
(const char *)StringValuePtr(result),
347+
(int)RSTRING_LEN(result),
348+
SQLITE_TRANSIENT
349+
);
350+
}
331351
break;
332352
default:
333353
rb_raise(rb_eRuntimeError, "can't return %s",

test/test_database.rb

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -261,12 +261,19 @@ def test_function_return
261261
end
262262

263263
def test_function_return_types
264-
[10, 2.2, nil, "foo"].each do |thing|
264+
[10, 2.2, nil, "foo", Blob.new("foo\0bar")].each do |thing|
265265
@db.define_function("hello") { |a| thing }
266266
assert_equal [thing], @db.execute("select hello('world')").first
267267
end
268268
end
269269

270+
def test_function_return_type_round_trip
271+
[10, 2.2, nil, "foo", Blob.new("foo\0bar")].each do |thing|
272+
@db.define_function("hello") { |a| a }
273+
assert_equal [thing], @db.execute("select hello(hello(?))", [thing]).first
274+
end
275+
end
276+
270277
def test_define_function_closed
271278
@db.close
272279
assert_raise(SQLite3::Exception) do

0 commit comments

Comments
 (0)