LogEventPropertyValue CreatePropertyValue(object value, Destructuring destructuring, int depth) { if (value == null) return new ScalarValue(null); if (destructuring == Destructuring.Stringify) return new ScalarValue(value.ToString()); var valueType = value.GetType(); var limiter = new DepthLimiter(depth, this); foreach (var scalarConversionPolicy in _scalarConversionPolicies) { ScalarValue converted; if (scalarConversionPolicy.TryConvertToScalar(value, limiter, out converted)) return converted; } var enumerable = value as IEnumerable; if (enumerable != null) { // Only dictionaries with 'scalar' keys are permitted, as // more complex keys may not serialize to unique values for // representation in sinks. This check strengthens the expectation // that resulting dictionary is representable in JSON as well // as richer formats (e.g. XML, .NET type-aware...). // Only actual dictionaries are supported, as arbitrary types // can implement multiple IDictionary interfaces and thus introduce // multiple different interpretations. if (valueType.IsConstructedGenericType && valueType.GetGenericTypeDefinition() == typeof(Dictionary<,>) && IsValidDictionaryKeyType(valueType.GenericTypeArguments[0])) { return new DictionaryValue(enumerable.Cast<dynamic>() .Select(kvp => new KeyValuePair<ScalarValue, LogEventPropertyValue>( (ScalarValue)limiter.CreatePropertyValue(kvp.Key, destructuring), limiter.CreatePropertyValue(kvp.Value, destructuring))) .Where(kvp => kvp.Key.Value != null)); // Limiting may kick in } return new SequenceValue( enumerable.Cast<object>().Select(o => limiter.CreatePropertyValue(o, destructuring))); } // Unknown types if (destructuring == Destructuring.Destructure) { foreach (var destructuringPolicy in _destructuringPolicies) { LogEventPropertyValue result; if (destructuringPolicy.TryDestructure(value, limiter, out result)) return result; } var typeTag = value.GetType().Name; if (typeTag.Length <= 0 || !char.IsLetter(typeTag[0])) typeTag = null; return new StructureValue(GetProperties(value, limiter), typeTag); } return new ScalarValue(value.ToString()); }
LogEventPropertyValue CreatePropertyValue(object value, Destructuring destructuring, int depth) { if (value == null) { return(new ScalarValue(null)); } if (destructuring == Destructuring.Stringify) { return(new ScalarValue(value.ToString())); } var valueType = value.GetType(); var limiter = new DepthLimiter(depth, this); foreach (var scalarConversionPolicy in _scalarConversionPolicies) { ScalarValue converted; if (scalarConversionPolicy.TryConvertToScalar(value, limiter, out converted)) { return(converted); } } var enumerable = value as IEnumerable; if (enumerable != null) { // Only dictionaries with 'scalar' keys are permitted, as // more complex keys may not serialize to unique values for // representation in sinks. This check strengthens the expectation // that resulting dictionary is representable in JSON as well // as richer formats (e.g. XML, .NET type-aware...). // Only actual dictionaries are supported, as arbitrary types // can implement multiple IDictionary interfaces and thus introduce // multiple different interpretations. if (valueType.IsGenericType && valueType.GetGenericTypeDefinition() == typeof(Dictionary <,>) && IsValidDictionaryKeyType(valueType.GetGenericArguments()[0])) { return(new DictionaryValue(enumerable.Cast <dynamic>() .Select(kvp => new KeyValuePair <ScalarValue, LogEventPropertyValue>( (ScalarValue)limiter.CreatePropertyValue(kvp.Key, destructuring), limiter.CreatePropertyValue(kvp.Value, destructuring))) .Where(kvp => kvp.Key.Value != null))); } return(new SequenceValue( enumerable.Cast <object>().Select(o => limiter.CreatePropertyValue(o, destructuring)))); } // Unknown types if (destructuring == Destructuring.Destructure) { foreach (var destructuringPolicy in _destructuringPolicies) { LogEventPropertyValue result; if (destructuringPolicy.TryDestructure(value, limiter, out result)) { return(result); } } var typeTag = value.GetType().Name; if (typeTag.Length <= 0 || !char.IsLetter(typeTag[0])) { typeTag = null; } return(new StructureValue(GetProperties(value, limiter), typeTag)); } return(new ScalarValue(value.ToString())); }
LogEventPropertyValue CreatePropertyValue(object value, Destructuring destructuring, int depth) { if (value == null) return new ScalarValue(null); if (destructuring == Destructuring.Stringify) return new ScalarValue(value.ToString()); var valueType = value.GetType(); var limiter = new DepthLimiter(depth, _maximumDestructuringDepth, this); foreach (var scalarConversionPolicy in _scalarConversionPolicies) { ScalarValue converted; if (scalarConversionPolicy.TryConvertToScalar(value, limiter, out converted)) return converted; } if (destructuring == Destructuring.Destructure) { foreach (var destructuringPolicy in _destructuringPolicies) { LogEventPropertyValue result; if (destructuringPolicy.TryDestructure(value, limiter, out result)) return result; } } var enumerable = value as IEnumerable; if (enumerable != null) { // Only dictionaries with 'scalar' keys are permitted, as // more complex keys may not serialize to unique values for // representation in sinks. This check strengthens the expectation // that resulting dictionary is representable in JSON as well // as richer formats (e.g. XML, .NET type-aware...). // Only actual dictionaries are supported, as arbitrary types // can implement multiple IDictionary interfaces and thus introduce // multiple different interpretations. if (IsValueTypeDictionary(valueType)) { var typeInfo = typeof(KeyValuePair<,>).MakeGenericType(valueType.GenericTypeArguments).GetTypeInfo(); var keyProperty = typeInfo.GetDeclaredProperty("Key"); var valueProperty = typeInfo.GetDeclaredProperty("Value"); return new DictionaryValue(enumerable.Cast<object>() .Select(kvp => new KeyValuePair<ScalarValue, LogEventPropertyValue>( (ScalarValue)limiter.CreatePropertyValue(keyProperty.GetValue(kvp), destructuring), limiter.CreatePropertyValue(valueProperty.GetValue(kvp), destructuring))) .Where(kvp => kvp.Key.Value != null)); } return new SequenceValue( enumerable.Cast<object>().Select(o => limiter.CreatePropertyValue(o, destructuring))); } if (destructuring == Destructuring.Destructure) { var type = value.GetType(); var typeTag = type.Name; if (typeTag.Length <= 0 || IsCompilerGeneratedType(type)) { typeTag = null; } return new StructureValue(GetProperties(value, limiter), typeTag); } return new ScalarValue(value.ToString()); }
LogEventPropertyValue CreatePropertyValue(object value, Destructuring destructuring, int depth) { if (value == null) { return(new ScalarValue(null)); } if (destructuring == Destructuring.Stringify) { return(new ScalarValue(value.ToString())); } var valueType = value.GetType(); var limiter = new DepthLimiter(depth, _maximumDestructuringDepth, this); foreach (var scalarConversionPolicy in _scalarConversionPolicies) { ScalarValue converted; if (scalarConversionPolicy.TryConvertToScalar(value, limiter, out converted)) { return(converted); } } if (destructuring == Destructuring.Destructure) { foreach (var destructuringPolicy in _destructuringPolicies) { LogEventPropertyValue result; if (destructuringPolicy.TryDestructure(value, limiter, out result)) { return(result); } } } var enumerable = value as IEnumerable; if (enumerable != null) { // Only dictionaries with 'scalar' keys are permitted, as // more complex keys may not serialize to unique values for // representation in sinks. This check strengthens the expectation // that resulting dictionary is representable in JSON as well // as richer formats (e.g. XML, .NET type-aware...). // Only actual dictionaries are supported, as arbitrary types // can implement multiple IDictionary interfaces and thus introduce // multiple different interpretations. if (IsValueTypeDictionary(valueType)) { var typeInfo = typeof(KeyValuePair <,>).MakeGenericType(valueType.GenericTypeArguments).GetTypeInfo(); var keyProperty = typeInfo.GetDeclaredProperty("Key"); var valueProperty = typeInfo.GetDeclaredProperty("Value"); return(new DictionaryValue(enumerable.Cast <object>() .Select(kvp => new KeyValuePair <ScalarValue, LogEventPropertyValue>( (ScalarValue)limiter.CreatePropertyValue(keyProperty.GetValue(kvp), destructuring), limiter.CreatePropertyValue(valueProperty.GetValue(kvp), destructuring))) .Where(kvp => kvp.Key.Value != null))); } return(new SequenceValue( enumerable.Cast <object>().Select(o => limiter.CreatePropertyValue(o, destructuring)))); } if (destructuring == Destructuring.Destructure) { var type = value.GetType(); var typeTag = type.Name; if (typeTag.Length <= 0 || IsCompilerGeneratedType(type)) { typeTag = null; } return(new StructureValue(GetProperties(value, limiter), typeTag)); } return(new ScalarValue(value.ToString())); }
LogEventPropertyValue CreatePropertyValue(object value, Destructuring destructuring, int depth) { if (value == null) return new ScalarValue(null); if (destructuring == Destructuring.Stringify) return new ScalarValue(value.ToString()); var valueType = value.GetType(); var limiter = new DepthLimiter(depth, _maximumDestructuringDepth, this); foreach (var scalarConversionPolicy in _scalarConversionPolicies) { ScalarValue converted; if (scalarConversionPolicy.TryConvertToScalar(value, limiter, out converted)) return converted; } if (destructuring == Destructuring.Destructure) { foreach (var destructuringPolicy in _destructuringPolicies) { LogEventPropertyValue result; if (destructuringPolicy.TryDestructure(value, limiter, out result)) return result; } } var enumerable = value as IEnumerable; if (enumerable != null) { // Only dictionaries with 'scalar' keys are permitted, as // more complex keys may not serialize to unique values for // representation in sinks. This check strengthens the expectation // that resulting dictionary is representable in JSON as well // as richer formats (e.g. XML, .NET type-aware...). // Only actual dictionaries are supported, as arbitrary types // can implement multiple IDictionary interfaces and thus introduce // multiple different interpretations. if (IsValueTypeDictionary(valueType)) { Func<object, object> getKey; Func<object, object> getValue; #if USE_REFLECTION_40 PropertyInfo keyProperty = null; getKey = o => (keyProperty ?? (keyProperty = o.GetType().GetProperty("Key"))).GetValue(o, null); PropertyInfo valueProperty = null; getValue = o => (valueProperty ?? (valueProperty = o.GetType().GetProperty("Value"))).GetValue(o, null); #else PropertyInfo keyProperty = null; getKey = o => (keyProperty ?? (keyProperty = o.GetType().GetRuntimeProperty("Key"))).GetValue(o); PropertyInfo valueProperty = null; getValue = o => (valueProperty ?? (valueProperty = o.GetType().GetRuntimeProperty("Value"))).GetValue(o); #endif return new DictionaryValue(enumerable .Cast<object>() .Where(o => o != null) .Select(o => new { Key = getKey(o), Value = getValue(o) }) .Select(o => new KeyValuePair<ScalarValue, LogEventPropertyValue>( key: (ScalarValue)limiter.CreatePropertyValue(o.Key, destructuring), value: limiter.CreatePropertyValue(o.Value, destructuring)) ) ); } return new SequenceValue( enumerable.Cast<object>().Select(o => limiter.CreatePropertyValue(o, destructuring))); } if (destructuring == Destructuring.Destructure) { var typeTag = value.GetType().Name; if (typeTag.Length <= 0 || !char.IsLetter(typeTag[0])) typeTag = null; return new StructureValue(GetProperties(value, limiter), typeTag); } return new ScalarValue(value.ToString()); }