type '_InternalLinkedHashMap<String, dynamic>' is not a subtype of type 'Map<String, String>' in type cast

Viewed 378

I'm failing to cast a Map<String, dynamic> into a Map<String, Map<String, String>. What is the best way to do this?

Note that I'm using the advanced analysis options in my analysis_options.yaml:

analyzer:
  enable-experiment:
    - extension-methods
  strong-mode:
    implicit-casts: false
    implicit-dynamic: false

I tried

var de = Map<String, Map<String, String>>.from((json.decode(await rootBundle.loadString('lang/de.json'))) as Map<String, dynamic>);

and

var de = (json.decode(await rootBundle.loadString('lang/de.json')) as Map<String, dynamic>).cast<String, Map<String, String>>();

and

var de = Map.castFrom<String, dynamic, String, Map<String, String>>((json.decode(await rootBundle.loadString('lang/de.json'))) as Map<String, dynamic>);

All attempts raised the following runtime error: type '_InternalLinkedHashMap<String, dynamic>' is not a subtype of type 'Map<String, String>' in type cast

What is the best way to this? I think this can be done by iterating through the map but if these are very large, this is an expensive operation. Is there any way to cast them without iterating?

1 Answers

I don't believe there is a way to cast to the appropriate type when dealing with nested data like this.

There was a similar discussion here about casting nested lists: https://github.com/dart-lang/language/issues/1574

I think iterating over the data in some fashion is the only thing you can do in this situation.

One possible solution:

final data = await rootBundle.loadString('lang/de.json');
final Map<String, Map<String, String>> de = {
  for (final entry in (json.decode(data) as Map).entries)
    entry.key as String: {
      for (final e in (entry.value as Map).entries)
        e.key as String: e.value as String,
    },
};
Related