Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
53 changes: 53 additions & 0 deletions lib/sqlite3_async.dart
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ import 'package:logging/logging.dart';
import 'package:logging_appenders/logging_appenders.dart';
import 'package:sqlite3/sqlite3.dart';

export 'package:sqlite3/sqlite3.dart' show AllowedArgumentCount;

/// An opened sqlite3 database with async methods.
class AsyncDatabase {
static final Logger _log = Logger((AsyncDatabase).toString());
Expand Down Expand Up @@ -80,6 +82,24 @@ class AsyncDatabase {
body: _StatementParams(sql, parameters));
}

// Register a custom function we can invoke from sql
Future<void> createFunction({
required String functionName,
required ScalarFunction function,
AllowedArgumentCount argumentCount = const AllowedArgumentCount.any(),
bool deterministic = false,
bool directOnly = true,
}) async {
return await _sendCommand("createFunction",
body: _CreateFunctionParams(
functionName: functionName,
function: function,
argumentCount: argumentCount,
deterministic: deterministic,
directOnly: directOnly,
));
}

/// Closes this database and releases associated resources.
Future<void> dispose() async {
await _sendCommand("dispose");
Expand Down Expand Up @@ -115,6 +135,9 @@ class AsyncDatabase {
case "select":
_selectSync(db!, cmd, ourReceivePort);
break;
case "createFunction":
_createFunctionSync(db!, cmd, ourReceivePort);
break;
case "dispose":
_disposeSync(db!, cmd, ourReceivePort);
break;
Expand Down Expand Up @@ -172,6 +195,19 @@ class AsyncDatabase {
body: version));
}

static void _createFunctionSync(
Database db, _AsyncDatabaseCommand cmd, ReceivePort ourReceivePort) {
_CreateFunctionParams params = cmd.body;
db.createFunction(
functionName: params.functionName,
function: params.function,
argumentCount: params.argumentCount,
deterministic: params.deterministic,
directOnly: params.directOnly,
);
cmd.sendPort.send(_AsyncDatabaseCommand(cmd.type, ourReceivePort.sendPort));
}

static Database _openSync(
_AsyncDatabaseCommand cmd, ReceivePort ourReceivePort) {
_OpenDatabaseParams params = cmd.body;
Expand Down Expand Up @@ -226,3 +262,20 @@ class _StatementParams {

const _StatementParams(this.sql, this.parameters);
}

@immutable
class _CreateFunctionParams {
final String functionName;
final ScalarFunction function;
final AllowedArgumentCount argumentCount;
final bool deterministic;
final bool directOnly;

const _CreateFunctionParams({
required this.functionName,
required this.function,
this.argumentCount = const AllowedArgumentCount.any(),
this.deterministic = false,
this.directOnly = true,
});
}
4 changes: 2 additions & 2 deletions pubspec.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -12,10 +12,10 @@ dependencies:
sdk: flutter
logging: ^1.2.0
logging_appenders: ^1.3.1
sqlite3: ^2.4.4
sqlite3: ^2.4.7

dev_dependencies:
flutter_test:
sdk: flutter
flutter_lints: ^4.0.0
sqlite3_flutter_libs: ^0.5.24
sqlite3_flutter_libs: ^0.5.26
26 changes: 26 additions & 0 deletions test/sqlite3_async_test.dart
Original file line number Diff line number Diff line change
Expand Up @@ -82,6 +82,32 @@ void main() {
expect(fullInsertionsTime, greaterThan(triggeredInsertionsTime));
await db.dispose();
});

test('create custom function', () async {
var db = await AsyncDatabase.open(testDbPath);
await _createTable(db);

await db.createFunction(
functionName: 'get_int_from_row_name',
argumentCount: const AllowedArgumentCount(1),
function: (args) {
final [name as String] = args;
return int.parse(name.split('_')[1]);
},
);

for (int i = 0; i < 100; i++) {
await _insertItem("a_$i", db);
}

var rows = await db.select(
"SELECT name, get_int_from_row_name(name) as name_int FROM items");

expect(
rows.every((element) => element['name'] == 'a_${element['name_int']}'),
true);
await db.dispose();
});
}

Future<void> _insertItem(String itemName, AsyncDatabase db) {
Expand Down