Hi! First of all amazing work with Hive, people love it on my team.
We've noticed a casting error when we reopen a box of type Map<String, dynamic>, values returns an _InternalLinkedHashMap<dynamic, dynamic> which is a map so that's fine, but the actual key, value types are missing. To be clear this only happens when the box gets closed and reopened. The actual exception is:
_CastError (type '_InternalLinkedHashMap<dynamic, dynamic>' is not a subtype of type 'Map<String, dynamic>' in type cast)
Steps to Reproduce
You can reproduce using the code below.
Code sample
Box<Map<String, dynamic>> _getsBox;
void main() async {
WidgetsFlutterBinding.ensureInitialized();
await Hive.initFlutter();
_getsBox = await Hive.openBox<Map<String, dynamic>>('boxName');
await _getsBox.put('key', {'itemKey': 'itemValue'});
print('first call: ${_getsBox.values}');
// success prints values
await Hive.close();
_getsBox = await Hive.openBox<Map<String, dynamic>>('boxName');
print('second call: ${_getsBox.values}');
// casting error
runApp(MyApp());
}
Version
P.D.: Might be related to https://github.com/hivedb/hive/issues/260
I have the same problem.
Found a work around:
You can get all the keys from the box and then iterate over it to get individual values like this:
Map<String, dynamic> obj = Map<String, dynamic>.from(box.get(key));
This works for me.
Unfortunately this is a limitation of the dart language. You can use
var box = await Hive.openBox<Map>('boxName');
var map = box.get("myMap").cast<String, dynamic>();
or you create an object which contains your box and generate a Hive adapter. The adapter will handle the casting.
@leisim What to do, if my map has nested maps? Is there a way to automatically cast all maps to Map
I don't want to use adapters, because I already use JsonSerializable
Most helpful comment
Unfortunately this is a limitation of the dart language. You can use
or you create an object which contains your box and generate a Hive adapter. The adapter will handle the casting.