I am looking for some reverse of new JsObject.jsify
. Something, that would convert javascript Object
back to Dart Map
Is there somethi
Will convert recursively any JS object to a Dart map, list or scalar value:
/// js_interop.dart
import 'dart:js';
/// Converts the specified JavaScript [value] to a Dart instance.
dynamic convertToDart(value) {
// Value types.
if (value == null) return null;
if (value is bool || value is num || value is DateTime || value is String) return value;
// JsArray.
if (value is Iterable) return value.map(convertToDart).toList();
// JsObject.
return new Map.fromIterable(getKeysOfObject(value), value: (key) => convertToDart(value[key]));
}
/// Gets the enumerable properties of the specified JavaScript [object].
List getKeysOfObject(JsObject object) => (context['Object'] as JsFunction).callMethod('keys', [object]);
Usage:
/// config.js
window.$environment = 'staging';
window.$config = {
name: 'FooBar',
params: {
assets: ['css', 'js'],
forceSsl: true
}
};
/// main.dart
import 'dart:js' as js;
import 'js_interop.dart';
void main() {
var environment = convertToDart(js.context[r'$environment']);
assert(environment is String);
assert(environment == 'staging');
var config = convertToDart(js.context[r'$config']);
assert(config is Map);
assert(config.length == 2);
assert(config['name'] is String);
assert(config['name'] == 'FooBar');
assert(config['params'] is Map);
assert(config['params'].length == 2);
assert(config['params']['forceSsl'] is bool);
assert(config['params']['forceSsl'] == true);
assert(config['params']['assets'] is List);
assert(config['params']['assets'].length == 2);
assert(config['params']['assets'].first == 'css');
assert(config['params']['assets'].last == 'js');
}
Caveats: the created instance does not reflect the changes from the original JS object. If you need this feature, Alexandre Arduin's answer is the right one.