Chromium Code Reviews| Index: pkg/serialization/lib/serialization.dart |
| diff --git a/pkg/serialization/lib/serialization.dart b/pkg/serialization/lib/serialization.dart |
| index 1c5f07060085b3410e915c23052ab96b85c88082..b6ba64cc075221d2a55dbb9f52b663c921134dba 100644 |
| --- a/pkg/serialization/lib/serialization.dart |
| +++ b/pkg/serialization/lib/serialization.dart |
| @@ -177,13 +177,35 @@ class Serialization { |
| * the account. Instead we should just connect the de-serialized message |
| * object to the account object that already exists there. |
| */ |
| - Map<String, dynamic> externalObjects = {}; |
| + Map<String, dynamic> namedObjects = {}; |
| /** |
| * When we write out data using this serialization, should we also write |
| - * out a description of the rules. |
| + * out a description of the rules. This is on by default unless using |
| + * CustomRule subclasses, in which case it requires additional setup and |
| + * is off by default. |
| */ |
| - bool selfDescribing = true; |
| + bool _selfDescribing; |
| + |
| + /** |
| + * When we write out data using this serialization, should we also write |
| + * out a description of the rules. This is on by default unless using |
| + * CustomRule subclasses, in which case it requires additional setup and |
| + * is off by default. |
| + */ |
| + bool get selfDescribing { |
| + if (_selfDescribing != null) return _selfDescribing; |
| + _selfDescribing = !rules.some((x) => x is CustomRule); |
|
Jennifer Messerly
2012/12/12 20:38:28
Do we know that the set of "rules" is fixed at thi
Alan Knight
2012/12/12 21:19:33
Yes, this was a cheesy attempt to make it default
|
| + return _selfDescribing; |
| + } |
| + |
| + /** |
| + * When we write out data using this serialization, should we also write |
| + * out a description of the rules. This is on by default unless using |
| + * CustomRule subclasses, in which case it requires additional setup and |
| + * is off by default. |
| + */ |
| + set selfDescribing(x) => _selfDescribing = x; |
| /** |
| * Creates a new serialization with a default set of rules for primitives |
| @@ -286,29 +308,19 @@ class Serialization { |
| } |
| /** |
| - * Read the serialized data from [input] and return a List of the root |
| - * objects from the result. If there are objects that need to be resolved |
| + * Read the serialized data from [input] and return the root object |
| + * from the result. If there are objects that need to be resolved |
| * in the current context, they should be provided in [externals] as a |
| * Map from names to values. In particular, in the current implementation |
| * any class mirrors needed should be provided in [externals] using the |
| * class name as a key. In addition to the [externals] map provided here, |
| * values will be looked up in the [externalObjects] map. |
| */ |
| - List read(String input, [Map externals = const {}]) { |
| + read(String input, [Map externals = const {}]) { |
| return newReader().read(input, externals); |
| } |
| /** |
| - * In the most common case there is only a single root object to be read, |
| - * and this method can be used to return just one object rather than |
| - * a List. The [input] and [externals] parameters are the same as for the |
| - * general [read] method. |
| - */ |
| - Object readOne(String input, [Map externals = const {}]) { |
| - return newReader().readOne(input, externals); |
| - } |
| - |
| - /** |
| * Return a new [Reader] object for this serialization. This is useful if |
| * you want to do something more complex with the reader than just returning |
| * the final result. |
| @@ -319,7 +331,7 @@ class Serialization { |
| * Return the list of SerializationRule that apply to [object]. For |
| * internal use, but public because it's used in testing. |
| */ |
| - List<SerializationRule> rulesFor(object) { |
| + List<SerializationRule> rulesFor(object, Writer w) { |
| // This has a couple of edge cases. |
| // 1) The owning object may have indicated we should use a different |
| // rule than the default. |
| @@ -343,7 +355,8 @@ class Serialization { |
| target = object; |
| candidateRules = rules; |
| } |
| - List applicable = candidateRules.filter((each) => each.appliesTo(target)); |
| + List applicable = candidateRules.filter( |
| + (each) => each.appliesTo(target, w)); |
| if (applicable.isEmpty) { |
| return [addRuleFor(target)]; |
| @@ -374,8 +387,7 @@ class Serialization { |
| // Make some bogus rule instances so we have something to feed rule creation |
| // and get their types. If only we had class literals implemented... |
| - var closureRule = new ClosureToMapRule.stub([].runtimeType); |
| - var basicRule = new BasicRule(reflect(null).type, '', [], [], []); |
| + var basicRule = new BasicRule(reflect(null).type, '', [], [], []); |
| var meta = new Serialization() |
| ..selfDescribing = false |
| @@ -387,10 +399,28 @@ class Serialization { |
| 'constructorName', |
| 'constructorFields', 'regularFields', []], |
| fields: []) |
| - ..addRule(new ClassMirrorRule()); |
| - meta.externalObjects = externalObjects; |
| + ..addRule(new NamedObjectRule()) |
| + ..addRule(new MirrorRule()); |
| + meta.namedObjects = namedObjects; |
| return meta; |
| } |
| + |
| + /** Return true if our [namedObjects] collection has an entry for [object].*/ |
| + bool _hasNameFor(object) { |
| + var sentinel = const _Sentinel(); |
| + return _nameFor(object, () => sentinel) != sentinel; |
| + } |
| + |
| + /** |
| + * Return the name we have for [object] in our [namedObjects] collection or |
| + * the result of evaluating [ifAbsent] if there is no entry. |
| + */ |
| + _nameFor(object, [ifAbsent]) { |
| + for (var key in namedObjects.keys) { |
| + if (identical(namedObjects[key], object)) return key; |
| + } |
| + return ifAbsent == null ? null : ifAbsent(); |
| + } |
| } |
| /** |