Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -33,5 +33,5 @@ public class AfterDeserializationAttribute : Attribute
/// </summary>
public bool Synchronous { get; set; }

public AfterDeserializationAttribute(bool synchronous = true) => Synchronous = true;
public AfterDeserializationAttribute(bool synchronous = true) => Synchronous = synchronous;
}
29 changes: 29 additions & 0 deletions ModernUO.Serialization.Annotations/AnchoredDateTimeAttribute.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
/*************************************************************************
* ModernUO *
* Copyright 2019-2026 - ModernUO Development Team *
* Email: hi@modernuo.com *
* File: AnchoredDateTimeAttribute.cs *
* *
* This program is free software: you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation, either version 3 of the License, or *
* (at your option) any later version. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program. If not, see <http://www.gnu.org/licenses/>. *
*************************************************************************/

using System;

namespace ModernUO.Serialization;

/// <summary>
/// Hints to the source generator that a serializable DateTime field or property is anchored to
/// the save time: it is written as an absolute value and re-anchored once at load, so downtime
/// does not age it and an unchanged entity serializes to identical bytes. Takes precedence
/// over <see cref="DeltaDateTimeAttribute" /> when both are present.
/// </summary>
[AttributeUsage(AttributeTargets.Field | AttributeTargets.Property)]
public class AnchoredDateTimeAttribute : Attribute
{
}
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ public interface IGenericReader
decimal ReadDecimal();
System.DateTime ReadDateTime();
System.DateTime ReadDeltaTime();
System.DateTime ReadAnchoredTime();
System.TimeSpan ReadTimeSpan();
System.Guid ReadGuid();
int ReadEncodedInt();
Expand Down Expand Up @@ -59,6 +60,7 @@ public interface IGenericWriter
void Write(decimal value);
void Write(System.DateTime value);
void WriteDeltaTime(System.DateTime value);
void WriteAnchoredTime(System.DateTime value);
void Write(System.TimeSpan value);
void Write(System.Guid value);
void WriteEncodedInt(int value);
Expand Down Expand Up @@ -168,6 +170,7 @@ public class Timer
{
public System.TimeSpan Delay { get; set; }
public System.DateTime Next { get; set; }
public static void DelayCall(System.Action callback) { }
}

public static class Core
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -275,6 +275,19 @@ private set
}
}

public System.DateTime LastRested
{
get => _lastRested;
set
{
if (value != _lastRested)
{
_lastRested = value;
Server.ISerializableExtensions.MarkDirty(this);
}
}
}

public BasicFieldsItem(Server.Serial serial)
{
Serial = serial;
Expand Down Expand Up @@ -323,6 +336,8 @@ public virtual void Serialize(Server.IGenericWriter writer)
writer.Write(_floatValue);

writer.Write(_privateSet);

writer.WriteAnchoredTime(_lastRested);
}

public virtual void Deserialize(Server.IGenericReader reader)
Expand Down Expand Up @@ -368,6 +383,8 @@ public virtual void Deserialize(Server.IGenericReader reader)
_floatValue = reader.ReadFloat();

_privateSet = reader.ReadInt();

_lastRested = reader.ReadAnchoredTime();
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,10 @@ public partial class BasicFieldsItem : ISerializable
[SerializableField(19, setter: "private")]
private int _privateSet;

[SerializableField(20)]
[AnchoredDateTime]
private DateTime _lastRested;

public DateTime Created { get; set; }
public Serial Serial { get; }
public bool Deleted => false;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,8 @@ public virtual void Deserialize(Server.IGenericReader reader)
{
MigrateFrom(new V0Content(reader, this));
Server.ISerializableExtensions.MarkDirty(this);
ValidateState();
Server.Timer.DelayCall(RebuildCaches);
return;
}

Expand All @@ -80,6 +82,8 @@ public virtual void Deserialize(Server.IGenericReader reader)
var RefreshTimerNext = reader.ReadDateTime();
var RefreshTimerDelay = RefreshTimerNext == System.DateTime.MinValue ? System.TimeSpan.MinValue : RefreshTimerNext - Server.Core.Now;
DeserializeRefreshTimer(RefreshTimerDelay);
ValidateState();
Server.Timer.DelayCall(RebuildCaches);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -28,5 +28,15 @@ private void MigrateFrom(V0Content content)
{
_name = content.Name;
}

[AfterDeserialization]
private void ValidateState()
{
}

[AfterDeserialization(false)]
private void RebuildCaches()
{
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -205,7 +205,7 @@ private void GenerateAfterDeserialization(
}
else
{
source.AppendLine($"{indent}Timer.DelayCall({method.MethodName});");
source.AppendLine($"{indent}Server.Timer.DelayCall({method.MethodName});");
}
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,8 @@ SpecialType.System_Decimal and not
{
SpecialType.System_Int32 when attributes.Any(a => a.IsEncodedInt(compilation)) =>
["EncodedInt"],
SpecialType.System_DateTime when attributes.Any(a => a.IsAnchoredDateTime(compilation)) =>
["AnchoredTime"],
SpecialType.System_DateTime when attributes.Any(a => a.IsDeltaDateTime(compilation)) =>
["DeltaTime"],
SpecialType.System_String when attributes.Any(a => a.IsInternString(compilation)) =>
Expand Down Expand Up @@ -114,8 +116,9 @@ public override void GenerateDeserializationMethod(
"double" => "ReadDouble",
"string" => "ReadString",
"decimal" => "ReadDecimal",
date when argument == "DeltaTime" => "ReadDeltaTime",
date => "ReadDateTime",
date when argument == "DeltaTime" => "ReadDeltaTime",
date when argument == "AnchoredTime" => "ReadAnchoredTime",
date => "ReadDateTime",
SymbolMetadata.IPADDRESS_CLASS => "ReadIPAddress",
SymbolMetadata.TIMESPAN_STRUCT => "ReadTimeSpan",
SymbolMetadata.GUID_STRUCT => "ReadGuid",
Expand Down Expand Up @@ -144,9 +147,10 @@ public override void GenerateSerializationMethod(StringBuilder source, string in

var writeMethod = property.Type switch
{
date when argument == "DeltaTime" => "WriteDeltaTime",
"int" when argument == "EncodedInt" => "WriteEncodedInt",
_ => "Write"
date when argument == "DeltaTime" => "WriteDeltaTime",
date when argument == "AnchoredTime" => "WriteAnchoredTime",
"int" when argument == "EncodedInt" => "WriteEncodedInt",
_ => "Write"
};

source.AppendLine($"{indent}writer.{writeMethod}({propertyName});");
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ public static partial class SymbolMetadata
public const string SERIALIZABLE_FIELD_ATTRIBUTE = "ModernUO.Serialization.SerializableFieldAttribute";
public const string SERIALIZABLE_PROPERTY_ATTRIBUTE = "ModernUO.Serialization.SerializablePropertyAttribute";
public const string DELTA_DATE_TIME_ATTRIBUTE = "ModernUO.Serialization.DeltaDateTimeAttribute";
public const string ANCHORED_DATE_TIME_ATTRIBUTE = "ModernUO.Serialization.AnchoredDateTimeAttribute";
public const string INTERN_STRING_ATTRIBUTE = "ModernUO.Serialization.InternStringAttribute";
public const string ENCODED_INT_ATTRIBUTE = "ModernUO.Serialization.EncodedIntAttribute";
public const string CAN_BE_NULL_ATTRIBUTE = "ModernUO.Serialization.CanBeNullAttribute";
Expand Down Expand Up @@ -104,6 +105,9 @@ public bool IsEncodedInt(Compilation compilation) =>
public bool IsDeltaDateTime(Compilation compilation) =>
attr?.IsAttribute(compilation.GetTypeByMetadataName(DELTA_DATE_TIME_ATTRIBUTE)) == true;

public bool IsAnchoredDateTime(Compilation compilation) =>
attr?.IsAttribute(compilation.GetTypeByMetadataName(ANCHORED_DATE_TIME_ATTRIBUTE)) == true;

public bool IsInternString(Compilation compilation) =>
attr?.IsAttribute(compilation.GetTypeByMetadataName(INTERN_STRING_ATTRIBUTE)) == true;

Expand Down
Loading