Dictionary <string, JsonMemberSetter> LoadMemberDeserializationSettings(JsonMemberSetter d, IReflectionController controller) { var member = d.Member.MemberInfo; var sd = new Dictionary <string, JsonMemberSetter> (); d.Converter = controller.GetMemberConverter(member); d.ItemConverter = controller.GetMemberItemConverter(member); var tn = controller.GetSerializedNames(member); if (tn == null) { sd.Add(d.MemberName, d); return(sd); } sd.Add(String.IsNullOrEmpty(tn.DefaultName) ? d.MemberName : tn.DefaultName, d); // polymorphic deserialization foreach (var item in tn) { var st = item.Key; var sn = item.Value; var dt = new JsonMemberSetter(d.OwnerTypeInfo, new MemberCache(st, d.MemberName, d.Member), this) { Converter = d.Converter, ItemConverter = d.ItemConverter }; AddSetter(sd, sn, dt); } return(sd); }
static void AddSetter(Dictionary <string, JsonMemberSetter> sd, string name, JsonMemberSetter item) { if (String.IsNullOrEmpty(name)) { throw new JsonSerializationException(item.MemberName + " should not be serialized to an empty name"); } JsonMemberSetter s; if (sd.TryGetValue(name, out s)) { var mt = s.Member.MemberType; var nt = item.Member.MemberType; if (nt.Equals(mt) || nt.IsSubclassOf(mt)) { throw new JsonSerializationException(String.Concat(name, " has been used by member ", s.Member.MemberName, " in type ", s.Member.MemberInfo.ReflectedType.FullName)); } if (item.Member.MemberInfo.DeclaringType == item.Member.MemberInfo.ReflectedType) { sd[name] = item; } // ignores the member overridden by "new" operator return; } sd.Add(name, item); }
/// <summary> /// Overrides reflection result with <see cref="TypeOverride"/> for the specific type and optionally purge existing overrides. /// </summary> /// <param name="type">The type to be overridden.</param> /// <param name="overrideInfo">The override info of the type.</param> /// <param name="purgeExisting">If this value is true, the reflection engine will reflect the type again and apply the <paramref name="overrideInfo"/>, otherwise, <paramref name="overrideInfo"/> is merged into the existing reflection cache.</param> /// <remarks> /// <para>At this moment, the override only affects the registered type.</para> /// <para>If a class has its subclasses, the override will not be applied to its subclasses.</para> /// </remarks> /// <exception cref="ArgumentNullException">The parameter <paramref name="type"/> or <paramref name="overrideInfo"/> is null.</exception> /// <exception cref="MissingMemberException">No member is found for a <see cref="MemberOverride"/> in <paramref name="overrideInfo"/>.</exception> public void Override(Type type, TypeOverride overrideInfo, bool purgeExisting) { if (type == null) { throw new ArgumentNullException("type"); } if (overrideInfo == null) { throw new ArgumentNullException("overrideInfo"); } lock (_syncRoot) { var s = GetSerializationInfo(type); if (purgeExisting) { LoadSerializationInfo(s); } OverrideSerializationInfo(s, overrideInfo); if (overrideInfo._MemberOverrides == null || overrideInfo._MemberOverrides.Count == 0) { return; } // add properties ignored by _controller in GetProperties method foreach (var ov in overrideInfo._MemberOverrides) { //if (ov.Deserializable != true) { // continue; //} var p = s.FindProperties(ov.MemberName); if (p.Count == 0) { var m = s.Reflection.FindMemberCache(ov.MemberName); if (m == null) { throw new MissingMemberException(s.Reflection.TypeName, ov.MemberName); } var pi = new JsonMemberSetter(s, m, this); // TODO: load serialization control settings var ds = LoadMemberDeserializationSettings(pi, _controller); if (ds != null) { foreach (var item in ds) { AddSetter(s.Setters, item.Key, item.Value); } } } } foreach (var ov in overrideInfo._MemberOverrides) { var g = s.FindGetters(ov.MemberName); if (g == null) { throw new MissingMemberException(type.FullName, ov.MemberName); } OverrideGetter(g, ov); OverrideSetter(s.Setters, ov, g); } } }
Dictionary <string, JsonMemberSetter> GetDeserializingProperties(JsonMemberSetter setter, IReflectionController controller) { var member = setter.Member.MemberInfo; //if (controller == null) { // return new Dictionary<string, JsonMemberSetter> { { setter.MemberName, setter } }; //} setter.CanWrite = controller.IsMemberDeserializable(member, setter.Member); if (setter.CanWrite == false) { if (/*d.TypeInfo.Reflection.AppendItem == null || */ member is PropertyInfo == false) { return(null); } } return(LoadMemberDeserializationSettings(setter, controller)); }
void ConvertProperty(object o, JsonMemberSetter pi, JsonItem ji) { var pc = pi.Converter ?? pi.TypeInfo.Converter; var rt = pc.GetReversiveType(ji); var xv = ji._Value; if (xv != null && rt != null && pi.Member.MemberType.Equals(xv.GetType()) == false) { var c = _manager.GetSerializationInfo(rt); var jt = Reflection.GetJsonDataType(rt); if (jt != JsonDataType.Undefined) { xv = c.DeserializeMethod(this, xv, c); } else if (xv is JsonDict) { xv = CreateObject((JsonDict)xv, c, pi.Member.Getter(o)); } } ji._Value = pc.DeserializationConvert(xv); }
static object ConvertItems(JsonMemberSetter pi, IList vl) { var l = vl.Count; var converted = false; object xv; for (int i = 0; i < l; i++) { var vi = vl[i]; xv = pi.ItemConverter.DeserializationConvert(vi); if (ReferenceEquals(vi, xv) == false) { vl[i] = xv; converted = true; } } if (converted) { if (pi.Member.JsonDataType == JsonDataType.Array) { var a = Array.CreateInstance(pi.Member.ElementType, l); vl.CopyTo((Array)a, 0); return(a); } else if (pi.Member.JsonDataType == JsonDataType.List) { var a = pi.TypeInfo.Instantiate() as IList; for (int i = 0; i < l; i++) { a.Add(vl[i]); } return(a); } } return(vl); }
Dictionary <string, JsonMemberSetter> GetSetters(SerializationInfo typeInfo, MemberCache[] members, IReflectionController controller) { var sd = new Dictionary <string, JsonMemberSetter> (StringComparer.OrdinalIgnoreCase); foreach (var p in members) { var s = new JsonMemberSetter(typeInfo, p, this); if (s.Member.IsReadOnly && s.OwnerTypeInfo.Reflection.AppendItem != null && CanSerializePrivateMembers == false) { continue; } var dp = GetDeserializingProperties(s, controller); if (dp == null) { continue; } foreach (var item in dp) { AddSetter(sd, item.Key, item.Value); } } return(sd); }
void OverrideSetter(Dictionary <string, JsonMemberSetter> s, MemberOverride mo, JsonMemberGetter g) { JsonMemberSetter mp = null; if (mo.OverrideTypedNames) { // remove previous polymorphic deserialization info var rt = new List <string> (); foreach (var item in s) { if (item.Value.MemberName == mo.MemberName) { if (Equals(item.Value.Member.MemberType, g.Member.MemberType) == false) { rt.Add(item.Key); } // find an item with the same member name mp = item.Value; } } if (mp == null) { throw new MissingMemberException(g.Member.MemberType.FullName, mo.MemberName); } foreach (var item in rt) { s.Remove(item); } // add new polymorphic deserialization info if (mo.TypedNames.Count > 0) { foreach (var item in mo.TypedNames) { var t = item.Key; if (g.Member.MemberType.IsAssignableFrom(t) == false) { throw new InvalidCastException("The type (" + t.FullName + ") does not derive from the member type (" + g.Member.MemberType.FullName + ")"); } var n = item.Value; var p = new JsonMemberSetter(g.OwnerTypeInfo, new MemberCache(t, g.MemberName, mp.Member), this); JsonMemberSetter tp; if (s.TryGetValue(n, out tp) && Equals(tp.Member.MemberType, g.Member.MemberType)) { s[n] = p; } else { s.Add(n, p); } } } } else if (mo.OverrideSerializedName && g.SerializedName != mo.SerializedName) { if (s.TryGetValue(g.SerializedName, out mp)) { s.Remove(g.SerializedName); s.Add(mo.SerializedName, mp); } } OverrideJsonSetter(s, mo); if (mo.OverrideSerializedName) { g.SerializedName = mo.SerializedName; } }