internal static void WriteDictionary <TProperty>( JsonValueConverter <TProperty> converter, JsonSerializerOptions options, ref WriteStackFrame current, Utf8JsonWriter writer) { if (converter == null) { return; } Debug.Assert(current.Enumerator != null); string key; TProperty value; if (current.Enumerator is IEnumerator <KeyValuePair <string, TProperty> > enumerator) { // Avoid boxing for strongly-typed enumerators such as returned from IDictionary<string, TRuntimeProperty> value = enumerator.Current.Value; key = enumerator.Current.Key; } else { // Todo: support non-generic Dictionary here (IDictionaryEnumerator) throw new NotSupportedException(); } if (value == null) { writer.WriteNull(key); } else { #if true // temporary behavior until the writer can accept escaped string. byte[] utf8Key = Encoding.UTF8.GetBytes(key); converter.Write(utf8Key, value, writer); #else byte[] pooledKey = null; byte[] utf8Key = Encoding.UTF8.GetBytes(key); int length = JsonWriterHelper.GetMaxEscapedLength(utf8Key.Length, 0); Span <byte> escapedKey = length <= JsonConstants.StackallocThreshold ? stackalloc byte[length] : (pooledKey = ArrayPool <byte> .Shared.Rent(length)); JsonWriterHelper.EscapeString(utf8Key, escapedKey, 0, out int written); converter.Write(escapedKey.Slice(0, written), value, writer); if (pooledKey != null) { // We clear the array because it is "user data" (although a property name). new Span <byte>(pooledKey, 0, written).Clear(); ArrayPool <byte> .Shared.Return(pooledKey); } #endif } }
internal static void WriteDictionary <TProperty>( JsonValueConverter <TProperty> converter, JsonSerializerOptions options, ref WriteStackFrame current, Utf8JsonWriter writer) { if (converter == null) { return; } Debug.Assert(current.Enumerator != null); string key; TProperty value; if (current.Enumerator is IEnumerator <KeyValuePair <string, TProperty> > enumerator) { // Avoid boxing for strongly-typed enumerators such as returned from IDictionary<string, TRuntimeProperty> value = enumerator.Current.Value; key = enumerator.Current.Key; } else if (current.Enumerator is IEnumerator <KeyValuePair <string, object> > polymorphicEnumerator) { value = (TProperty)polymorphicEnumerator.Current.Value; key = polymorphicEnumerator.Current.Key; } else if (current.IsImmutableDictionary || current.IsImmutableDictionaryProperty) { value = (TProperty)((DictionaryEntry)current.Enumerator.Current).Value; key = (string)((DictionaryEntry)current.Enumerator.Current).Key; } else { // Todo: support non-generic Dictionary here (IDictionaryEnumerator) throw new NotSupportedException(); } if (value == null) { writer.WriteNull(key); } else { JsonEncodedText escapedKey = JsonEncodedText.Encode(key); converter.Write(escapedKey, value, writer); } }