From 5db9d86a5b8bcad9344316a36ae5738b0a93a20b Mon Sep 17 00:00:00 2001 From: Gregorius Soedharmo Date: Tue, 1 Oct 2024 20:33:12 +0700 Subject: [PATCH 1/2] Update RELEASE_NOTES.md for 1.5.29 release (#7351) * Update RELEASE_NOTES.md for 1.5.28.1 release * update version * Update RELEASE_NOTES.md --------- Co-authored-by: Aaron Stannard --- RELEASE_NOTES.md | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/RELEASE_NOTES.md b/RELEASE_NOTES.md index d3aee3beec5..f7d2f46dc85 100644 --- a/RELEASE_NOTES.md +++ b/RELEASE_NOTES.md @@ -1,3 +1,23 @@ +#### 1.5.29 October 1st 2024 #### + +Akka.NET v1.5.29 is an emergency patch release that addresses a severe bug for persistence users whom also use protobuf serializer. + +* [DData: Remove Hyperion dependency](https://github.com/akkadotnet/akka.net/pull/7337) +* [Streams: Fix SelectAsync race condition bug](https://github.com/akkadotnet/akka.net/pull/7338) +* [Core: Add new IWithTimers API to allow sender override](https://github.com/akkadotnet/akka.net/pull/7341) +* [Persistence: Fix SnapshotMetadata default timestamp value (DateTimeKind.Utc bug)](https://github.com/akkadotnet/akka.net/pull/7349) +* [Core: Fix AskTimeoutException message formatting bug](https://github.com/akkadotnet/akka.net/pull/7350) + +To [see the full set of changes in Akka.NET v1.5.29, click here](https://github.com/akkadotnet/akka.net/milestone/112?closed=1). + +3 contributors since release 1.5.28 + +| COMMITS | LOC+ | LOC- | AUTHOR | +|---------|------|------|---------------------| +| 4 | 177 | 14 | Gregorius Soedharmo | +| 1 | 10 | 10 | Simon Cropp | +| 1 | 0 | 1 | Aaron Stannard | + #### 1.5.28 September 5th 2024 #### Akka.NET v1.5.28 is a release with several bug fixes and improvements. From f5c4e63ce678b3b2f7cb4070c6b8438cf5176b1e Mon Sep 17 00:00:00 2001 From: Gregorius Soedharmo Date: Tue, 1 Oct 2024 21:36:16 +0700 Subject: [PATCH 2/2] Fix unit tests related to the Persistence DateTime bug (#7352) * Fix unit tests related to the Persistence DateTime bug * Refactor additional method calls --- .../LocalSnapshotStoreSpec.cs | 2 +- .../Query/PersistenceIdsSpec.cs | 3 ++- .../SnapshotStoreSerializationSpec.cs | 15 ++++++++++----- .../Snapshot/SnapshotStoreSaveSnapshotSpec.cs | 6 ++++-- .../Snapshot/SnapshotStoreSpec.cs | 9 ++++++--- 5 files changed, 23 insertions(+), 12 deletions(-) diff --git a/src/core/Akka.Persistence.TCK.Tests/LocalSnapshotStoreSpec.cs b/src/core/Akka.Persistence.TCK.Tests/LocalSnapshotStoreSpec.cs index abb96739751..1f184ab6c62 100644 --- a/src/core/Akka.Persistence.TCK.Tests/LocalSnapshotStoreSpec.cs +++ b/src/core/Akka.Persistence.TCK.Tests/LocalSnapshotStoreSpec.cs @@ -42,7 +42,7 @@ protected override void AfterAll() public void LocalSnapshotStore_can_snapshot_actors_with_PersistenceId_containing_invalid_path_characters() { var pid = @"p\/:*?-1"; - SnapshotStore.Tell(new SaveSnapshot(new SnapshotMetadata(pid, 1, Sys.Scheduler.Now.DateTime), "sample data"), TestActor); + SnapshotStore.Tell(new SaveSnapshot(new SnapshotMetadata(pid, 1, Sys.Scheduler.DateTimeNow), "sample data"), TestActor); ExpectMsg(); SnapshotStore.Tell(new LoadSnapshot(pid, SnapshotSelectionCriteria.Latest, long.MaxValue), TestActor); diff --git a/src/core/Akka.Persistence.TCK/Query/PersistenceIdsSpec.cs b/src/core/Akka.Persistence.TCK/Query/PersistenceIdsSpec.cs index 43c69a42dff..c62c0f5e214 100644 --- a/src/core/Akka.Persistence.TCK/Query/PersistenceIdsSpec.cs +++ b/src/core/Akka.Persistence.TCK/Query/PersistenceIdsSpec.cs @@ -247,7 +247,8 @@ protected IActorRef WriteSnapshot(string persistenceId, int n) ExpectMsg($"{persistenceId}-{i}-done"); } - var metadata = new SnapshotMetadata(persistenceId, n + 10, Sys.Scheduler.Now.DateTime); + var metadata = new SnapshotMetadata(persistenceId, n + 10, Sys.Scheduler.DateTimeNow); + metadata.Timestamp.Kind.Should().Be(DateTimeKind.Utc); SnapshotStore.Tell(new SaveSnapshot(metadata, $"s-{n}"), _senderProbe.Ref); _senderProbe.ExpectMsg(); diff --git a/src/core/Akka.Persistence.TCK/Serialization/SnapshotStoreSerializationSpec.cs b/src/core/Akka.Persistence.TCK/Serialization/SnapshotStoreSerializationSpec.cs index 4d8c8fad5fa..b9575c77e3d 100644 --- a/src/core/Akka.Persistence.TCK/Serialization/SnapshotStoreSerializationSpec.cs +++ b/src/core/Akka.Persistence.TCK/Serialization/SnapshotStoreSerializationSpec.cs @@ -69,7 +69,8 @@ public virtual void SnapshotStore_should_serialize_Payload() var snapshot = new Test.MySnapshot("a"); - var metadata = new SnapshotMetadata(Pid, 1, Sys.Scheduler.Now.DateTime); + var metadata = new SnapshotMetadata(Pid, 1, Sys.Scheduler.DateTimeNow); + metadata.Timestamp.Kind.Should().Be(DateTimeKind.Utc); SnapshotStore.Tell(new SaveSnapshot(metadata, snapshot), probe.Ref); probe.ExpectMsg(); @@ -85,7 +86,8 @@ public virtual void SnapshotStore_should_serialize_Payload_with_string_manifest( var snapshot = new Test.MySnapshot2("a"); - var metadata = new SnapshotMetadata(Pid, 1, Sys.Scheduler.Now.DateTime); + var metadata = new SnapshotMetadata(Pid, 1, Sys.Scheduler.DateTimeNow); + metadata.Timestamp.Kind.Should().Be(DateTimeKind.Utc); SnapshotStore.Tell(new SaveSnapshot(metadata, snapshot), probe.Ref); probe.ExpectMsg(); @@ -107,7 +109,8 @@ public virtual void SnapshotStore_should_serialize_AtLeastOnceDeliverySnapshot() }; var atLeastOnceDeliverySnapshot = new AtLeastOnceDeliverySnapshot(17, unconfirmed); - var metadata = new SnapshotMetadata(Pid, 2, Sys.Scheduler.Now.DateTime); + var metadata = new SnapshotMetadata(Pid, 2, Sys.Scheduler.DateTimeNow); + metadata.Timestamp.Kind.Should().Be(DateTimeKind.Utc); SnapshotStore.Tell(new SaveSnapshot(metadata, atLeastOnceDeliverySnapshot), probe.Ref); probe.ExpectMsg(); @@ -123,7 +126,8 @@ public virtual void SnapshotStore_should_serialize_AtLeastOnceDeliverySnapshot_w var unconfirmed = Array.Empty(); var atLeastOnceDeliverySnapshot = new AtLeastOnceDeliverySnapshot(13, unconfirmed); - var metadata = new SnapshotMetadata(Pid, 2, Sys.Scheduler.Now.DateTime); + var metadata = new SnapshotMetadata(Pid, 2, Sys.Scheduler.DateTimeNow); + metadata.Timestamp.Kind.Should().Be(DateTimeKind.Utc); SnapshotStore.Tell(new SaveSnapshot(metadata, atLeastOnceDeliverySnapshot), probe.Ref); probe.ExpectMsg(); @@ -138,7 +142,8 @@ public virtual void SnapshotStore_should_serialize_PersistentFSMSnapshot() var persistentFSMSnapshot = new PersistentFSM.PersistentFSMSnapshot("mystate", "mydata", TimeSpan.FromDays(4)); - var metadata = new SnapshotMetadata(Pid, 2, Sys.Scheduler.Now.DateTime); + var metadata = new SnapshotMetadata(Pid, 2, Sys.Scheduler.DateTimeNow); + metadata.Timestamp.Kind.Should().Be(DateTimeKind.Utc); SnapshotStore.Tell(new SaveSnapshot(metadata, persistentFSMSnapshot), probe.Ref); probe.ExpectMsg(); diff --git a/src/core/Akka.Persistence.TCK/Snapshot/SnapshotStoreSaveSnapshotSpec.cs b/src/core/Akka.Persistence.TCK/Snapshot/SnapshotStoreSaveSnapshotSpec.cs index 035ae4a1ec4..4b5f20599d7 100644 --- a/src/core/Akka.Persistence.TCK/Snapshot/SnapshotStoreSaveSnapshotSpec.cs +++ b/src/core/Akka.Persistence.TCK/Snapshot/SnapshotStoreSaveSnapshotSpec.cs @@ -138,14 +138,16 @@ public async Task MultipleSnapshotsWithSameSeqNo() var snapshotStore = persistence.SnapshotStoreFor(null); var snap = new TestPayload(SenderProbe.Ref); - var metadata = new SnapshotMetadata(PersistenceId, 3, DateTime.Now); + var metadata = new SnapshotMetadata(PersistenceId, 3, DateTime.UtcNow); + metadata.Timestamp.Kind.Should().Be(DateTimeKind.Utc); snapshotStore.Tell(new SaveSnapshot(metadata, snap), SenderProbe); var success = await SenderProbe.ExpectMsgAsync(10.Minutes()); success.Metadata.PersistenceId.Should().Be(metadata.PersistenceId); success.Metadata.Timestamp.Should().Be(metadata.Timestamp); success.Metadata.SequenceNr.Should().Be(metadata.SequenceNr); - metadata = new SnapshotMetadata(PersistenceId, 3, DateTime.Now); + metadata = new SnapshotMetadata(PersistenceId, 3, DateTime.UtcNow); + metadata.Timestamp.Kind.Should().Be(DateTimeKind.Utc); snapshotStore.Tell(new SaveSnapshot(metadata, 3), SenderProbe); success = await SenderProbe.ExpectMsgAsync(); success.Metadata.PersistenceId.Should().Be(metadata.PersistenceId); diff --git a/src/core/Akka.Persistence.TCK/Snapshot/SnapshotStoreSpec.cs b/src/core/Akka.Persistence.TCK/Snapshot/SnapshotStoreSpec.cs index 68879cf8643..1efd1ab2514 100644 --- a/src/core/Akka.Persistence.TCK/Snapshot/SnapshotStoreSpec.cs +++ b/src/core/Akka.Persistence.TCK/Snapshot/SnapshotStoreSpec.cs @@ -102,7 +102,8 @@ private IEnumerable WriteSnapshots() { for (int i = 1; i <= 5; i++) { - var metadata = new SnapshotMetadata(Pid, i + 10, Sys.Scheduler.Now.DateTime); + var metadata = new SnapshotMetadata(Pid, i + 10, Sys.Scheduler.DateTimeNow); + metadata.Timestamp.Kind.Should().Be(DateTimeKind.Utc); SnapshotStore.Tell(new SaveSnapshot(metadata, $"s-{i}"), _senderProbe.Ref); yield return _senderProbe.ExpectMsg().Metadata; } @@ -312,7 +313,8 @@ public virtual void SnapshotStore_should_save_and_overwrite_snapshot_with_same_s [Fact] public virtual void SnapshotStore_should_save_bigger_size_snapshot() { - var metadata = new SnapshotMetadata(Pid, 100, Sys.Scheduler.Now.DateTime); + var metadata = new SnapshotMetadata(Pid, 100, Sys.Scheduler.DateTimeNow); + metadata.Timestamp.Kind.Should().Be(DateTimeKind.Utc); var bigSnapshot = new byte[SnapshotByteSizeLimit]; new Random().NextBytes(bigSnapshot); SnapshotStore.Tell(new SaveSnapshot(metadata, bigSnapshot), _senderProbe.Ref); @@ -326,7 +328,8 @@ public virtual void ShouldSerializeSnapshots() if (!SupportsSerialization) return; var probe = CreateTestProbe(); - var metadata = new SnapshotMetadata(Pid, 100L, Sys.Scheduler.Now.DateTime); + var metadata = new SnapshotMetadata(Pid, 100L, Sys.Scheduler.DateTimeNow); + metadata.Timestamp.Kind.Should().Be(DateTimeKind.Utc); var snap = new TestPayload(probe.Ref); SnapshotStore.Tell(new SaveSnapshot(metadata, snap), _senderProbe.Ref);