public void Add(InnerObjectInfo obj)
 {
     if (InnerObjects == null)
         InnerObjects = new List<InnerObjectInfo>();
     obj.Id = InnerObjects.Count;
     InnerObjects.Add(obj);
 }
 private void OnObjectDeserializationFinished(long streamPos)
 {
     var info = _activeEntries.Pop();
     info.EndInit(streamPos);
     if (_activeEntries.Count > 0)
     {
         // add this object info as inner one for the previous object
         var parent = _activeEntries.Peek();
         parent.Add(info);
     }
     else
     {
         // this is a top-level object
         _rootInfo = info;
     }
 }
 public RootObjectInfo(Type refType, long streamPos, uint totalSize, string error)
 {
     Data = new InnerObjectInfo(refType, streamPos, totalSize);
     Error = error;
 }
 public RootObjectInfo(InnerObjectInfo data, int id)
 {
     Data = data;
     Data.Id = id;
 }
 private void OnObjectDeserializationStarted(Type refType, SerializationTypeInfo typeInfo, long streamPos, uint metaInfoLen, int version)
 {
     var lastVersion = typeInfo.IsValid ? _container.SerializerStorage.GetSerializer(typeInfo).Version : -1;
     var info = new InnerObjectInfo(refType, typeInfo, streamPos, metaInfoLen, version, lastVersion);
     _activeEntries.Push(info);
 }
        public void UpdateJsonData(InnerObjectInfo info)
        {
            if (_jsonSerializer == null)
            {
                _jsonSerializer = new JsonSerializer()
                {
                    Culture = System.Globalization.CultureInfo.InvariantCulture,
                    Formatting = Formatting.Indented,
                    DefaultValueHandling = DefaultValueHandling.Include,
                    NullValueHandling = NullValueHandling.Include,
                    MissingMemberHandling = MissingMemberHandling.Ignore,
                    ReferenceLoopHandling = ReferenceLoopHandling.Ignore,
                    TypeNameAssemblyFormatHandling = TypeNameAssemblyFormatHandling.Simple,
                    SerializationBinder = new SerializationTypeBinder(),
                };
                _jsonSerializer.Error += (sender, args) =>
                {
                    if (args.ErrorContext.Error is JsonSerializationException jErr)
                    {
                        _jsonErrors.Add(jErr.Message);
                        args.ErrorContext.Handled = true;
                    }
                };
            }
            if (info.JsonData == null & !info.JsonHasErrors)
            {
                try
                {
                    const int indentation = 4;
                    const bool showTypes = true;

                    object obj = null;
                    var container = _container as IContainerInternals;
                    container.Deserialize(info.StreamPosition, ref obj, info.TypeInfo, info.Version);

                    var stringWriter = new System.IO.StringWriter();
                    using (var writer = new JsonTextWriter(stringWriter))
                    {
                        writer.QuoteName = false;
                        writer.Formatting = Formatting.Indented;
                        writer.Indentation = indentation;
                        writer.IndentChar = ' ';
                        _jsonSerializer.TypeNameHandling = showTypes ? TypeNameHandling.Objects : TypeNameHandling.None;
                        _jsonSerializer.Serialize(writer, obj, info.TypeInfo.Type);
                    }
                    var json = stringWriter.ToString();

                    var sb = new StringBuilder(json.Length);
                    int i = json.IndexOf('\n') + 1; // skip first line with opening bracket
                    if (i >= 0)
                        i = json.IndexOf('\n', i) + 1 + indentation; // skip second line with $type info
                    if (i > 0)
                        for (int max = json.Length; i < max; i++)
                        {
                            var c = json[i];
                            if (c == '\r')
                                continue;
                            if (c == '\n')
                            {
                                if (sb[sb.Length - 1] == ',')
                                    sb.Length--; // remove trailing comma
                                i += indentation; // remove root object indentation
                                if (i >= max)
                                    break;
                            }
                            sb.Append(c);
                        }

                    if (_jsonErrors.Count > 0)
                    {
                        sb.AppendLine("\n\n");
                        sb.Append("===== ERRORS =====");
                        foreach (var err in _jsonErrors)
                        {
                            sb.AppendLine();
                            sb.AppendLine();
                            sb.Append(err);
                        }
                    }
                    info.JsonData = sb.ToString();
                    info.JsonHasErrors = _jsonErrors.Count > 0;
                    info.JsonCreated = true;
                }
                catch (Exception ex)
                {
                    info.JsonCreated = false;
                    info.JsonHasErrors = true;
                    info.JsonData = ex.PrettyTypeName() + ": " + ex.Message + "\n\n" + ex.StackTrace;
                }
                _jsonErrors.Clear();
            }
        }