refactor: moved serialization into core project
This commit is contained in:
82
Engine.Core/Serialization/Utils.cs
Normal file
82
Engine.Core/Serialization/Utils.cs
Normal file
@@ -0,0 +1,82 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Reflection;
|
||||
|
||||
namespace Syntriax.Engine.Core.Serialization;
|
||||
|
||||
internal static class Utils
|
||||
{
|
||||
internal static bool HasAttribute<T>(this MemberInfo memberInfo) where T : Attribute => memberInfo.GetCustomAttribute<T>() is not null;
|
||||
internal static bool IsEnumerable(this Type type) => typeof(System.Collections.IEnumerable).IsAssignableFrom(type) && type != typeof(string);
|
||||
|
||||
internal static TypeData GetTypeData(this Type objectType)
|
||||
{
|
||||
List<EventInfo> eventInfos = objectType.GetEvents(BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public)
|
||||
.OrderBy(ei => ei.Name)
|
||||
.ToList();
|
||||
|
||||
List<FieldInfo> fieldInfos = GetFieldInfosIncludingBaseClasses(objectType, BindingFlags.Instance | BindingFlags.FlattenHierarchy | BindingFlags.NonPublic | BindingFlags.Public)
|
||||
.Where(pi => !eventInfos.Any(ei => pi.Name.CompareTo(ei.Name) == 0)).ToList();
|
||||
|
||||
List<PropertyInfo> propertyInfos = GetPropertyInfosIncludingBaseClasses(objectType, BindingFlags.Instance | BindingFlags.FlattenHierarchy | BindingFlags.Public)
|
||||
.Where(pi => pi.SetMethod is not null && !eventInfos.Any(ei => pi.Name.CompareTo(ei.Name) == 0))
|
||||
.ToList();
|
||||
|
||||
return new TypeData(fieldInfos, propertyInfos);
|
||||
}
|
||||
|
||||
internal static List<FieldInfo> GetFieldInfosIncludingBaseClasses(Type type, BindingFlags bindingFlags)
|
||||
{
|
||||
if (type.BaseType is null)
|
||||
return [.. type.GetFields(bindingFlags)];
|
||||
|
||||
Type currentType = type;
|
||||
FieldInfoComparer fieldComparer = new();
|
||||
HashSet<FieldInfo> fieldInfoList = new(type.GetFields(bindingFlags), fieldComparer);
|
||||
|
||||
while (currentType.BaseType is Type baseType)
|
||||
{
|
||||
currentType = baseType;
|
||||
fieldInfoList.UnionWith(currentType!.GetFields(bindingFlags));
|
||||
}
|
||||
|
||||
return [.. fieldInfoList.OrderBy(fi => fi.Name)];
|
||||
}
|
||||
|
||||
internal static List<PropertyInfo> GetPropertyInfosIncludingBaseClasses(Type type, BindingFlags bindingFlags)
|
||||
{
|
||||
if (type.BaseType is null)
|
||||
return [.. type.GetProperties(bindingFlags)];
|
||||
|
||||
Type currentType = type;
|
||||
PropertyInfoComparer propertyComparer = new();
|
||||
HashSet<PropertyInfo> propertyInfoList = new(type.GetProperties(bindingFlags), propertyComparer);
|
||||
|
||||
while (currentType.BaseType is Type baseType)
|
||||
{
|
||||
currentType = baseType;
|
||||
propertyInfoList.UnionWith(currentType.GetProperties(bindingFlags));
|
||||
}
|
||||
|
||||
return [.. propertyInfoList.OrderBy(pi => pi.Name)];
|
||||
}
|
||||
|
||||
private class FieldInfoComparer : IEqualityComparer<FieldInfo>
|
||||
{
|
||||
public bool Equals(FieldInfo? x, FieldInfo? y) => x?.DeclaringType == y?.DeclaringType && x?.Name == y?.Name;
|
||||
public int GetHashCode(FieldInfo obj) => obj.Name.GetHashCode() ^ obj.DeclaringType!.GetHashCode();
|
||||
}
|
||||
|
||||
private class PropertyInfoComparer : IEqualityComparer<PropertyInfo>
|
||||
{
|
||||
public bool Equals(PropertyInfo? x, PropertyInfo? y) => x?.DeclaringType == y?.DeclaringType && x?.Name == y?.Name;
|
||||
public int GetHashCode(PropertyInfo obj) => obj.Name.GetHashCode() ^ obj.DeclaringType!.GetHashCode();
|
||||
}
|
||||
}
|
||||
|
||||
internal record struct TypeData(IEnumerable<FieldInfo> Fields, IEnumerable<PropertyInfo> Properties)
|
||||
{
|
||||
public static implicit operator (IEnumerable<FieldInfo> fields, IEnumerable<PropertyInfo> properties)(TypeData value) => (value.Fields, value.Properties);
|
||||
public static implicit operator TypeData((IEnumerable<FieldInfo> fields, IEnumerable<PropertyInfo> properties) value) => new(value.fields, value.properties);
|
||||
}
|
Reference in New Issue
Block a user