Closed timshadel closed 1 year ago
Supporting async Codec could be possible but would require a lot of changes and complexity in supporting both models (synchronous and asynchronous). Using encryption could have huge performance penalty (especially on startup as everything is decrypted during open). I understand the encryption support might sound too good compared to what it really is.
I just wonder if its worth the support though, sembast is a small all in memory database. Any serious database needs should rely on more complete packages such as isar, objectbox, hive, realm, sqflite
If not all your information is sensitive, you could also consider using a regular database and only encrypt the data your need.
(I'm assuming you're looking at other alternatives. If indeed you think you don't have other solutions than sembast - and you seem to have to lot of knowledge - I could consider adding a new asynchronous codec interface)
Following your request async codec support has been added in sembast 3.4.2 just published.
The codec must be able to handle the conversion of a json encodable data to a single line string. (i.e. json being one).
If your codec requires calling a plugin or an asynchronous operation you have to create an
asynchronous codec. One solution is to subclass AsyncContentCodecBase
(which is a Codec<Object?, String>
but with
the synchronous encoding/decoding disabled) where you just have to implement:
decodeAsync
encodeAsync
/// My simple asynchronous codec.
class MyAsyncCodec extends AsyncContentCodecBase {
String _reverseString(String text) => text.split('').reversed.join();
@override
Future<Object?> decodeAsync(String encoded) async {
// Simple demo, just reverse the json asynchronously.
return jsonDecode(_reverseString(encoded));
}
@override
Future<String> encodeAsync(Object? input) async {
// Simple demo, just reverse the json asynchronously.
return _reverseString(jsonEncode(input));
}
}
Many Flutter encryption libraries use native platform methods for encryption. Because these must use MethodChannel calls, they must be
async
. TheCodec
is a wonderful, common interface for synchronous change steps which can be fused together. It doesn't have any asynchronous option.Sadly, most synchronous encryption available in Dart is inadequate for production use. Either their algorithms are weak, or they implement only some of the algorithms required to construct production-grade encryption, or they cannot secure their memory properly. Sodium is great, and it's synchronous because it uses C APIs called via FFI to an underlying layer which manages secure memory. (See also #340) But it's not for everyone. Anyone requiring FIPS-140 compliance needs to use only approved encryption providers, like OpenSSL or native Apple Crypto or Google's BoringCrypto. These will require
async
method calls.I don't know enough about the internals of Sembast to know if using
async
would drastically affect the rest of the API (often a low-levelasync
call means changing all calling paths toasync
, and that may be disastrously complex.All Store operations are already
async
, as is theopenDatabase
call. But it's the internals that must be reviewed before taking this idea seriously.