84 lines
2.5 KiB
C#
84 lines
2.5 KiB
C#
using System.Reflection;
|
|
using System.Runtime.CompilerServices;
|
|
using System.Text;
|
|
using static AyCode.Core.Helpers.JsonUtilities;
|
|
|
|
namespace AyCode.Core.Serializers;
|
|
|
|
/// <summary>
|
|
/// Base class for property accessors used by all serializers.
|
|
/// Contains common property metadata and getter functionality.
|
|
/// </summary>
|
|
public abstract class PropertyAccessorBase
|
|
{
|
|
/// <summary>
|
|
/// Property name.
|
|
/// </summary>
|
|
public string Name { get; }
|
|
|
|
/// <summary>
|
|
/// Pre-encoded UTF8 bytes of property name for fast matching.
|
|
/// </summary>
|
|
public byte[] NameUtf8 { get; }
|
|
|
|
/// <summary>
|
|
/// The property type (may be nullable).
|
|
/// </summary>
|
|
public Type PropertyType { get; }
|
|
|
|
/// <summary>
|
|
/// The underlying type (unwrapped from Nullable if applicable).
|
|
/// </summary>
|
|
public Type UnderlyingType { get; }
|
|
|
|
/// <summary>
|
|
/// Cached TypeCode for fast primitive type dispatch.
|
|
/// </summary>
|
|
public TypeCode PropertyTypeCode { get; }
|
|
|
|
/// <summary>
|
|
/// Whether the property type is nullable.
|
|
/// </summary>
|
|
public bool IsNullable { get; }
|
|
|
|
/// <summary>
|
|
/// The declaring type of this property.
|
|
/// </summary>
|
|
public Type DeclaringType { get; }
|
|
|
|
/// <summary>
|
|
/// True if this property needs recursive scanning (not primitive/string).
|
|
/// Pre-computed to avoid IsPrimitiveOrStringFast() calls in hot path.
|
|
/// </summary>
|
|
public bool IsComplexType { get; }
|
|
|
|
/// <summary>
|
|
/// Compiled getter delegate for reading property values.
|
|
/// </summary>
|
|
protected readonly Func<object, object?> _getter;
|
|
|
|
protected PropertyAccessorBase(PropertyInfo prop, Type declaringType)
|
|
{
|
|
Name = prop.Name;
|
|
NameUtf8 = Encoding.UTF8.GetBytes(prop.Name);
|
|
DeclaringType = declaringType;
|
|
PropertyType = prop.PropertyType;
|
|
|
|
var underlying = Nullable.GetUnderlyingType(PropertyType);
|
|
IsNullable = underlying != null;
|
|
UnderlyingType = underlying ?? PropertyType;
|
|
PropertyTypeCode = Type.GetTypeCode(UnderlyingType);
|
|
|
|
// Pre-compute: is this a complex type that needs recursive handling?
|
|
IsComplexType = !IsPrimitiveOrStringFast(PropertyType);
|
|
|
|
_getter = AcSerializerCommon.CreateCompiledGetter(declaringType, prop);
|
|
}
|
|
|
|
/// <summary>
|
|
/// Gets the property value from the target object.
|
|
/// </summary>
|
|
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
|
public object? GetValue(object obj) => _getter(obj);
|
|
}
|