From 56f81c668a4df58caf1b0bf4668f1445d5b9b3db Mon Sep 17 00:00:00 2001 From: rekhoff Date: Mon, 29 Sep 2025 13:59:31 -0700 Subject: [PATCH 01/14] Resolved misc warnings in C# bindings code --- crates/bindings-csharp/BSATN.Codegen/Type.cs | 22 ++++++++-------- .../BSATN.Runtime/BSATN/Runtime.cs | 14 +++++++--- .../bindings-csharp/BSATN.Runtime/Builtins.cs | 26 +++++++++---------- crates/bindings-csharp/Codegen/Module.cs | 14 +++++----- .../Runtime/Internal/Module.cs | 2 +- 5 files changed, 42 insertions(+), 36 deletions(-) diff --git a/crates/bindings-csharp/BSATN.Codegen/Type.cs b/crates/bindings-csharp/BSATN.Codegen/Type.cs index 4bfbf45ec7e..0ba58eb61d8 100644 --- a/crates/bindings-csharp/BSATN.Codegen/Type.cs +++ b/crates/bindings-csharp/BSATN.Codegen/Type.cs @@ -594,16 +594,16 @@ public override string ToString() => write = "value.WriteFields(writer);"; - var declHashName = (MemberDeclaration decl) => $"___hash{decl.Name}"; + string DeclHashName(MemberDeclaration decl) => $"___hash{decl.Name}"; getHashCode = $$""" - {{string.Join("\n", bsatnDecls.Select(decl => decl.Type.GetHashCodeStatement(decl.Name, declHashName(decl))))}} - return {{JoinOrValue( - " ^\n ", - bsatnDecls.Select(declHashName), - "0" // if there are no members, the hash is 0. - )}}; - """; + {{string.Join("\n", bsatnDecls.Select(decl => decl.Type.GetHashCodeStatement(decl.Name, DeclHashName(decl))))}} + return {{JoinOrValue( + " ^\n ", + bsatnDecls.Select((Func?)DeclHashName), + "0" // if there are no members, the hash is 0. + )}}; + """; } extensions.Contents.Append( @@ -643,7 +643,7 @@ public override int GetHashCode() // If we are a reference type, various equality methods need to take nullable references. // If we are a value type, everything is pleasantly by-value. var fullNameMaybeRef = $"{FullName}{(Scope.IsStruct ? "" : "?")}"; - var declEqualsName = (MemberDeclaration decl) => $"___eq{decl.Name}"; + string DeclEqualsName(MemberDeclaration decl) => $"___eq{decl.Name}"; extensions.Contents.Append( $$""" @@ -652,10 +652,10 @@ public override int GetHashCode() public bool Equals({{fullNameMaybeRef}} that) { {{(Scope.IsStruct ? "" : "if (((object?)that) == null) { return false; }\n ")}} - {{string.Join("\n", bsatnDecls.Select(decl => decl.Type.EqualsStatement($"this.{decl.Name}", $"that.{decl.Name}", declEqualsName(decl))))}} + {{string.Join("\n", bsatnDecls.Select(decl => decl.Type.EqualsStatement($"this.{decl.Name}", $"that.{decl.Name}", DeclEqualsName(decl))))}} return {{JoinOrValue( " &&\n ", - bsatnDecls.Select(declEqualsName), + bsatnDecls.Select((Func?)DeclEqualsName), "true" // if there are no elements, the structs are equal :) )}}; } diff --git a/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs b/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs index bce87b273bc..e24c161cd2c 100644 --- a/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs +++ b/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs @@ -129,7 +129,11 @@ public interface IReadWrite /// Note: the [Type] macro rejects enums with explicitly set values (see Codegen.Tests), /// so this array is guaranteed to be continuous and indexed starting from 0. /// - private static readonly T[] TagToValue = Enum.GetValues(typeof(T)).Cast().ToArray(); +#if NET8_0_OR_GREATER + private static readonly T[] TagToValue = System.Enum.GetValues(); +#else + private static readonly T[] TagToValue = System.Enum.GetValues(typeof(T)).Cast().ToArray(); +#endif public T Read(BinaryReader reader) { @@ -177,9 +181,11 @@ public AlgebraicType GetAlgebraicType(ITypeRegistrar registrar) => registrar.RegisterType( (_) => new AlgebraicType.Sum( - Enum.GetNames(typeof(T)) - .Select(name => new AggregateElement(name, AlgebraicType.Unit)) - .ToArray() +#if NET8_0_OR_GREATER + [.. System.Enum.GetNames().Select(name => new AggregateElement(name, AlgebraicType.Unit))] +#else + [.. System.Enum.GetNames(typeof(T)).Select(name => new AggregateElement(name, AlgebraicType.Unit))] +#endif ) ); } diff --git a/crates/bindings-csharp/BSATN.Runtime/Builtins.cs b/crates/bindings-csharp/BSATN.Runtime/Builtins.cs index a3478d18023..09b3895a2c8 100644 --- a/crates/bindings-csharp/BSATN.Runtime/Builtins.cs +++ b/crates/bindings-csharp/BSATN.Runtime/Builtins.cs @@ -331,7 +331,7 @@ public static implicit operator DateTimeOffset(Timestamp t) => DateTimeOffset.UnixEpoch.AddTicks(t.MicrosecondsSinceUnixEpoch * Util.TicksPerMicrosecond); public static implicit operator Timestamp(DateTimeOffset offset) => - new Timestamp(offset.Subtract(DateTimeOffset.UnixEpoch).Ticks / Util.TicksPerMicrosecond); + new(offset.Subtract(DateTimeOffset.UnixEpoch).Ticks / Util.TicksPerMicrosecond); // For backwards-compatibility. public readonly DateTimeOffset ToStd() => this; @@ -347,7 +347,7 @@ public override readonly string ToString() public static readonly Timestamp UNIX_EPOCH = new(0); public static Timestamp FromTimeDurationSinceUnixEpoch(TimeDuration timeDuration) => - new Timestamp(timeDuration.Microseconds); + new(timeDuration.Microseconds); public readonly TimeDuration ToTimeDurationSinceUnixEpoch() => TimeDurationSince(UNIX_EPOCH); @@ -360,12 +360,12 @@ public readonly TimeDuration TimeDurationSince(Timestamp earlier) => new TimeDuration(checked(MicrosecondsSinceUnixEpoch - earlier.MicrosecondsSinceUnixEpoch)); public static Timestamp operator +(Timestamp point, TimeDuration interval) => - new Timestamp(checked(point.MicrosecondsSinceUnixEpoch + interval.Microseconds)); + new(checked(point.MicrosecondsSinceUnixEpoch + interval.Microseconds)); public static Timestamp operator -(Timestamp point, TimeDuration interval) => - new Timestamp(checked(point.MicrosecondsSinceUnixEpoch - interval.Microseconds)); + new(checked(point.MicrosecondsSinceUnixEpoch - interval.Microseconds)); - public int CompareTo(Timestamp that) + public readonly int CompareTo(Timestamp that) { return this.MicrosecondsSinceUnixEpoch.CompareTo(that.MicrosecondsSinceUnixEpoch); } @@ -466,10 +466,10 @@ public static implicit operator TimeDuration(TimeSpan timeSpan) => new(timeSpan.Ticks / Util.TicksPerMicrosecond); public static TimeDuration operator +(TimeDuration lhs, TimeDuration rhs) => - new TimeDuration(checked(lhs.Microseconds + rhs.Microseconds)); + new(checked(lhs.Microseconds + rhs.Microseconds)); public static TimeDuration operator -(TimeDuration lhs, TimeDuration rhs) => - new TimeDuration(checked(lhs.Microseconds + rhs.Microseconds)); + new(checked(lhs.Microseconds - rhs.Microseconds)); // For backwards-compatibility. public readonly TimeSpan ToStd() => this; @@ -548,7 +548,7 @@ long microsSinceUnixEpoch // --- auto-generated --- private ScheduleAt() { } - internal enum @enum : byte + internal enum EnumTag : byte { Interval, Time, @@ -560,15 +560,15 @@ public sealed record Time(Timestamp Time_) : ScheduleAt; public readonly partial struct BSATN : IReadWrite { - internal static readonly SpacetimeDB.BSATN.Enum<@enum> __enumTag = new(); + internal static readonly SpacetimeDB.BSATN.Enum __enumTag = new(); internal static readonly TimeDuration.BSATN Interval = new(); internal static readonly Timestamp.BSATN Time = new(); public ScheduleAt Read(BinaryReader reader) => __enumTag.Read(reader) switch { - @enum.Interval => new Interval(Interval.Read(reader)), - @enum.Time => new Time(Time.Read(reader)), + EnumTag.Interval => new Interval(Interval.Read(reader)), + EnumTag.Time => new Time(Time.Read(reader)), _ => throw new InvalidOperationException( "Invalid tag value, this state should be unreachable." ), @@ -579,12 +579,12 @@ public void Write(BinaryWriter writer, ScheduleAt value) switch (value) { case Interval(var inner): - __enumTag.Write(writer, @enum.Interval); + __enumTag.Write(writer, EnumTag.Interval); Interval.Write(writer, inner); break; case Time(var inner): - __enumTag.Write(writer, @enum.Time); + __enumTag.Write(writer, EnumTag.Time); Time.Write(writer, inner); break; } diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index fb9f1d6fd79..57a1ee0f149 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -466,7 +466,7 @@ public ulong Delete({{argsBounds}}) => } } - public record struct View(string viewName, string tableName, string view, string getter); + public record struct View(string ViewName, string TableName, string ViewCode, string GetterCode); public IEnumerable GenerateViews() { @@ -539,7 +539,7 @@ v.Scheduled is { } scheduled } } - public record Constraint(ColumnDeclaration Col, int Pos, ColumnAttrs Attr) + public record struct Constraint(ColumnDeclaration Col, int Pos, ColumnAttrs Attr) { public ViewIndex ToIndex() => new(new ColumnRef(Pos, Col.Name)); } @@ -853,8 +853,8 @@ public void Initialize(IncrementalGeneratorInitializationContext context) tables .SelectMany((t, ct) => t.GenerateViews()) .WithTrackingName("SpacetimeDB.Table.GenerateViews"), - v => v.viewName, - v => v.tableName + v => v.ViewName, + v => v.TableName ); var rlsFilters = context @@ -919,11 +919,11 @@ internal ReducerContext(Identity identity, ConnectionId? connectionId, Random ra } namespace Internal.TableHandles { - {{string.Join("\n", tableViews.Select(v => v.view))}} + {{string.Join("\n", tableViews.Select(v => v.ViewCode))}} } public sealed class Local { - {{string.Join("\n", tableViews.Select(v => v.getter))}} + {{string.Join("\n", tableViews.Select(v => v.GetterCode))}} } } @@ -949,7 +949,7 @@ public static void Main() { )}} {{string.Join( "\n", - tableViews.Select(t => $"SpacetimeDB.Internal.Module.RegisterTable<{t.tableName}, SpacetimeDB.Internal.TableHandles.{t.viewName}>();") + tableViews.Select(t => $"SpacetimeDB.Internal.Module.RegisterTable<{t.TableName}, SpacetimeDB.Internal.TableHandles.{t.ViewName}>();") )}} {{string.Join( "\n", diff --git a/crates/bindings-csharp/Runtime/Internal/Module.cs b/crates/bindings-csharp/Runtime/Internal/Module.cs index ecd079e1ad8..b3e526f3d49 100644 --- a/crates/bindings-csharp/Runtime/Internal/Module.cs +++ b/crates/bindings-csharp/Runtime/Internal/Module.cs @@ -11,7 +11,7 @@ partial class RawModuleDefV9 // Fix it up to a different mangling scheme if it causes problems. private static string GetFriendlyName(Type type) => type.IsGenericType - ? $"{type.Name.Remove(type.Name.IndexOf('`'))}_{string.Join("_", type.GetGenericArguments().Select(GetFriendlyName))}" + ? $"{type.Name[..type.Name.IndexOf('`')]}_{string.Join("_", type.GetGenericArguments().Select(GetFriendlyName))}" : type.Name; private void RegisterTypeName(AlgebraicType.Ref typeRef) From 9d1f1f0e300c0c9f7f19a7e8b0a966a70edc5043 Mon Sep 17 00:00:00 2001 From: rekhoff Date: Mon, 29 Sep 2025 14:12:53 -0700 Subject: [PATCH 02/14] Corrected formatting errors --- .../bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs | 12 ++++++++++-- crates/bindings-csharp/Codegen/Module.cs | 7 ++++++- 2 files changed, 16 insertions(+), 3 deletions(-) diff --git a/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs b/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs index e24c161cd2c..6c551fe6e92 100644 --- a/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs +++ b/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs @@ -182,9 +182,17 @@ public AlgebraicType GetAlgebraicType(ITypeRegistrar registrar) => (_) => new AlgebraicType.Sum( #if NET8_0_OR_GREATER - [.. System.Enum.GetNames().Select(name => new AggregateElement(name, AlgebraicType.Unit))] + [ + .. System + .Enum.GetNames() + .Select(name => new AggregateElement(name, AlgebraicType.Unit)), + ] #else - [.. System.Enum.GetNames(typeof(T)).Select(name => new AggregateElement(name, AlgebraicType.Unit))] + [ + .. System + .Enum.GetNames(typeof(T)) + .Select(name => new AggregateElement(name, AlgebraicType.Unit)), + ] #endif ) ); diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index 57a1ee0f149..6132d5f520b 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -466,7 +466,12 @@ public ulong Delete({{argsBounds}}) => } } - public record struct View(string ViewName, string TableName, string ViewCode, string GetterCode); + public record struct View( + string ViewName, + string TableName, + string ViewCode, + string GetterCode + ); public IEnumerable GenerateViews() { From 8044b756ee0e861df53a25901fbf301455d384d1 Mon Sep 17 00:00:00 2001 From: rekhoff Date: Mon, 29 Sep 2025 14:20:11 -0700 Subject: [PATCH 03/14] Add dotnet version for GitHub .Net tests --- .github/workflows/csharp-test.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.github/workflows/csharp-test.yml b/.github/workflows/csharp-test.yml index 2017060baa7..4a811898f06 100644 --- a/.github/workflows/csharp-test.yml +++ b/.github/workflows/csharp-test.yml @@ -43,6 +43,8 @@ jobs: - name: Run .NET tests working-directory: sdks/csharp run: dotnet test -warnaserror + with: + dotnet-version: '8.x' - name: Verify C# formatting working-directory: sdks/csharp From 485de5a1b9ac3a95a4998d9d86e8b836a9531d15 Mon Sep 17 00:00:00 2001 From: rekhoff Date: Mon, 29 Sep 2025 15:21:16 -0700 Subject: [PATCH 04/14] Resolved additional warnings during C# bindings tests --- .../BSATN.Runtime/BSATN/AlgebraicType.cs | 13 +++---------- crates/bindings-csharp/BSATN.Runtime/Builtins.cs | 2 +- crates/bindings-csharp/Codegen/Module.cs | 2 +- 3 files changed, 5 insertions(+), 12 deletions(-) diff --git a/crates/bindings-csharp/BSATN.Runtime/BSATN/AlgebraicType.cs b/crates/bindings-csharp/BSATN.Runtime/BSATN/AlgebraicType.cs index 603feae5c78..2c0a0f0f7a9 100644 --- a/crates/bindings-csharp/BSATN.Runtime/BSATN/AlgebraicType.cs +++ b/crates/bindings-csharp/BSATN.Runtime/BSATN/AlgebraicType.cs @@ -6,17 +6,10 @@ public interface ITypeRegistrar } [SpacetimeDB.Type] -public partial struct AggregateElement +public partial struct AggregateElement(string? name, AlgebraicType algebraicType) { - public string? Name; - - public AlgebraicType AlgebraicType; - - public AggregateElement(string name, AlgebraicType algebraicType) - { - Name = name; - AlgebraicType = algebraicType; - } + public string? Name = name; + public AlgebraicType AlgebraicType = algebraicType; } [SpacetimeDB.Type] diff --git a/crates/bindings-csharp/BSATN.Runtime/Builtins.cs b/crates/bindings-csharp/BSATN.Runtime/Builtins.cs index 09b3895a2c8..0675dc6137f 100644 --- a/crates/bindings-csharp/BSATN.Runtime/Builtins.cs +++ b/crates/bindings-csharp/BSATN.Runtime/Builtins.cs @@ -357,7 +357,7 @@ public static Timestamp FromTimeSpanSinceUnixEpoch(TimeSpan timeSpan) => public readonly TimeSpan ToTimeSpanSinceUnixEpoch() => (TimeSpan)ToTimeDurationSinceUnixEpoch(); public readonly TimeDuration TimeDurationSince(Timestamp earlier) => - new TimeDuration(checked(MicrosecondsSinceUnixEpoch - earlier.MicrosecondsSinceUnixEpoch)); + new(checked(MicrosecondsSinceUnixEpoch - earlier.MicrosecondsSinceUnixEpoch)); public static Timestamp operator +(Timestamp point, TimeDuration interval) => new(checked(point.MicrosecondsSinceUnixEpoch + interval.Microseconds)); diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index 6132d5f520b..aab179caca6 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -544,7 +544,7 @@ v.Scheduled is { } scheduled } } - public record struct Constraint(ColumnDeclaration Col, int Pos, ColumnAttrs Attr) + public readonly record struct Constraint(ColumnDeclaration Col, int Pos, ColumnAttrs Attr) { public ViewIndex ToIndex() => new(new ColumnRef(Pos, Col.Name)); } From 9528c86f07c397358c20af88e77400c845c8f654 Mon Sep 17 00:00:00 2001 From: rekhoff Date: Mon, 29 Sep 2025 16:13:12 -0700 Subject: [PATCH 05/14] Resolved additional warnings during C# bindings tests --- .../BSATN.Runtime.Tests/Tests.cs | 30 ++++--------------- .../BSATN.Runtime/BSATN/Runtime.cs | 24 +++++++++------ 2 files changed, 21 insertions(+), 33 deletions(-) diff --git a/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs b/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs index c22879a596c..2db1063ce46 100644 --- a/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs +++ b/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs @@ -246,21 +246,7 @@ public BasicDataClass((int x, string y, int? z, string? w) data) } [Type] - public partial struct BasicDataStruct - { - public int X; - public string Y; - public int? Z; - public string? W; - - public BasicDataStruct((int x, string y, int? z, string? w) data) - { - X = data.x; - Y = data.y; - Z = data.z; - W = data.w; - } - } + public partial struct BasicDataStruct(int X, string Y, int? Z, string? W) { } [Type] public partial record BasicDataRecord @@ -315,12 +301,12 @@ public void Add(bool collides) } } - public double CollisionFraction + public readonly double CollisionFraction { get => (double)Collisions / (double)Comparisons; } - public void AssertCollisionsLessThan(double fraction) + public readonly void AssertCollisionsLessThan(double fraction) { Assert.True( CollisionFraction < fraction, @@ -630,14 +616,10 @@ public static void GeneratedNestedListRoundTrip() static readonly Gen<(ContainsNestedList e1, ContainsNestedList e2)> GenTwoContainsNestedList = Gen.Select(GenContainsNestedList, GenContainsNestedList, (e1, e2) => (e1, e2)); - class EnumerableEqualityComparer : EqualityComparer> + class EnumerableEqualityComparer(EqualityComparer equalityComparer) + : EqualityComparer> { - private readonly EqualityComparer EqualityComparer; - - public EnumerableEqualityComparer(EqualityComparer equalityComparer) - { - EqualityComparer = equalityComparer; - } + private readonly EqualityComparer EqualityComparer = equalityComparer; public override bool Equals(IEnumerable? x, IEnumerable? y) => x == null ? y == null : (y == null ? false : x.SequenceEqual(y, EqualityComparer)); diff --git a/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs b/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs index 6c551fe6e92..aec017298e1 100644 --- a/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs +++ b/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs @@ -177,25 +177,31 @@ public void Write(BinaryWriter writer, T value) } } - public AlgebraicType GetAlgebraicType(ITypeRegistrar registrar) => - registrar.RegisterType( + public AlgebraicType GetAlgebraicType(ITypeRegistrar registrar) + { + return registrar.RegisterType( (_) => - new AlgebraicType.Sum( + { #if NET8_0_OR_GREATER + return new AlgebraicType.Sum( [ .. System .Enum.GetNames() .Select(name => new AggregateElement(name, AlgebraicType.Unit)), ] + ); #else - [ - .. System - .Enum.GetNames(typeof(T)) - .Select(name => new AggregateElement(name, AlgebraicType.Unit)), - ] + var names = System.Enum.GetNames(typeof(T)); + var elements = new AggregateElement[names.Length]; + for (var i = 0; i < names.Length; i++) + { + elements[i] = new AggregateElement(names[i], AlgebraicType.Unit); + } + return new AlgebraicType.Sum(elements); #endif - ) + } ); + } } public readonly struct RefOption : IReadWrite From 348aa2a65ddce0132cd1e7b0f5fbd563d38cbee0 Mon Sep 17 00:00:00 2001 From: rekhoff Date: Mon, 29 Sep 2025 17:08:35 -0700 Subject: [PATCH 06/14] Resolved additional warnings during C# bindings tests --- .../BSATN.Runtime.Tests/Tests.cs | 24 ++++++------------- .../BSATN.Runtime/BSATN/Runtime.cs | 13 +++++++++- 2 files changed, 19 insertions(+), 18 deletions(-) diff --git a/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs b/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs index 2db1063ce46..e1387e387e2 100644 --- a/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs +++ b/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs @@ -246,25 +246,15 @@ public BasicDataClass((int x, string y, int? z, string? w) data) } [Type] - public partial struct BasicDataStruct(int X, string Y, int? Z, string? W) { } - - [Type] - public partial record BasicDataRecord + public partial struct BasicDataStruct(int x, string y, int? z, string? w) { - public int X; - public string Y = ""; - public int? Z; - public string? W; - - public BasicDataRecord() { } + public int X = x; + public string Y = y; + public int? Z = z; + public string? W = w; - public BasicDataRecord((int x, string y, int? z, string? w) data) - { - X = data.x; - Y = data.y; - Z = data.z; - W = data.w; - } + public BasicDataStruct((int x, string y, int? z, string? w) data) + : this(data.x, data.y, data.z, data.w) { } } static readonly Gen GenSmallInt = Gen.Int[-5, 5]; diff --git a/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs b/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs index aec017298e1..ccc2fc682a1 100644 --- a/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs +++ b/crates/bindings-csharp/BSATN.Runtime/BSATN/Runtime.cs @@ -132,7 +132,18 @@ public interface IReadWrite #if NET8_0_OR_GREATER private static readonly T[] TagToValue = System.Enum.GetValues(); #else - private static readonly T[] TagToValue = System.Enum.GetValues(typeof(T)).Cast().ToArray(); + private static readonly T[] TagToValue = CreateTagToValue(); + + private static T[] CreateTagToValue() + { + var values = System.Enum.GetValues(typeof(T)); + var result = new T[values.Length]; + for (var i = 0; i < values.Length; i++) + { + result[i] = (T)values.GetValue(i); + } + return result; + } #endif public T Read(BinaryReader reader) From 12a707698279cfdc3966b7568227df8c1c27a282 Mon Sep 17 00:00:00 2001 From: rekhoff Date: Mon, 29 Sep 2025 17:41:33 -0700 Subject: [PATCH 07/14] Adds BasicDataRecord to fix CS0246 error --- crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs b/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs index e1387e387e2..771cef35d88 100644 --- a/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs +++ b/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs @@ -257,6 +257,15 @@ public BasicDataStruct((int x, string y, int? z, string? w) data) : this(data.x, data.y, data.z, data.w) { } } + [Type] + public partial record BasicDataRecord(int X, string Y, int? Z, string? W) + { + public BasicDataRecord() { } + + public BasicDataRecord((int x, string y, int? z, string? w) data) + : this(data.x, data.y, data.z, data.w) { } + } + static readonly Gen GenSmallInt = Gen.Int[-5, 5]; static readonly Gen GenSmallString = Gen.String[Gen.Char.AlphaNumeric, 0, 2]; static readonly Gen GenNullableInt = Gen.Nullable(GenSmallInt); From 8e9721f8254de83d377835ad51f7ef74394b324e Mon Sep 17 00:00:00 2001 From: rekhoff Date: Mon, 29 Sep 2025 18:03:44 -0700 Subject: [PATCH 08/14] Resolve CS8862 error --- crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs b/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs index 771cef35d88..bc49227ff4f 100644 --- a/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs +++ b/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs @@ -260,7 +260,8 @@ public BasicDataStruct((int x, string y, int? z, string? w) data) [Type] public partial record BasicDataRecord(int X, string Y, int? Z, string? W) { - public BasicDataRecord() { } + public BasicDataRecord() + : this(default, "", default, default) { } public BasicDataRecord((int x, string y, int? z, string? w) data) : this(data.x, data.y, data.z, data.w) { } From 185798db4655db068a174398022e8cfd4ff5fd06 Mon Sep 17 00:00:00 2001 From: rekhoff Date: Mon, 29 Sep 2025 19:37:50 -0700 Subject: [PATCH 09/14] Fixes BSATN.Runtime test error --- .../BSATN.Runtime.Tests/Tests.cs | 17 +++++++++++++---- 1 file changed, 13 insertions(+), 4 deletions(-) diff --git a/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs b/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs index bc49227ff4f..620adef4662 100644 --- a/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs +++ b/crates/bindings-csharp/BSATN.Runtime.Tests/Tests.cs @@ -258,13 +258,22 @@ public BasicDataStruct((int x, string y, int? z, string? w) data) } [Type] - public partial record BasicDataRecord(int X, string Y, int? Z, string? W) + public partial record BasicDataRecord { - public BasicDataRecord() - : this(default, "", default, default) { } + public int X; + public string Y = ""; + public int? Z; + public string? W; + + public BasicDataRecord() { } public BasicDataRecord((int x, string y, int? z, string? w) data) - : this(data.x, data.y, data.z, data.w) { } + { + X = data.x; + Y = data.y; + Z = data.z; + W = data.w; + } } static readonly Gen GenSmallInt = Gen.Int[-5, 5]; From b3c7ad596a56455f7db03bd10c14705ee87d50aa Mon Sep 17 00:00:00 2001 From: rekhoff Date: Mon, 29 Sep 2025 22:11:10 -0700 Subject: [PATCH 10/14] Updating global.json import method for csharp tests --- .github/workflows/csharp-test.yml | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/.github/workflows/csharp-test.yml b/.github/workflows/csharp-test.yml index 4a811898f06..31b0ffc1fc6 100644 --- a/.github/workflows/csharp-test.yml +++ b/.github/workflows/csharp-test.yml @@ -18,13 +18,16 @@ jobs: - name: Checkout repository id: checkout-stdb uses: actions/checkout@v4 + + # Copy global.json to the current directory so that the dotnet things use it + - run: cp modules/global.json global.json # Run cheap .NET tests first. If those fail, no need to run expensive Unity tests. - name: Setup dotnet uses: actions/setup-dotnet@v3 with: - global-json-file: modules/global.json + global-json-file: global.json - name: Override NuGet packages run: | @@ -43,8 +46,6 @@ jobs: - name: Run .NET tests working-directory: sdks/csharp run: dotnet test -warnaserror - with: - dotnet-version: '8.x' - name: Verify C# formatting working-directory: sdks/csharp From c2e495e204b7400601d13b5e628b2b33494aa3a5 Mon Sep 17 00:00:00 2001 From: rekhoff Date: Tue, 30 Sep 2025 08:19:34 -0700 Subject: [PATCH 11/14] Removing Android SDK from GitHub runner --- .github/workflows/csharp-test.yml | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/.github/workflows/csharp-test.yml b/.github/workflows/csharp-test.yml index 31b0ffc1fc6..6dc28ca9db1 100644 --- a/.github/workflows/csharp-test.yml +++ b/.github/workflows/csharp-test.yml @@ -15,6 +15,13 @@ jobs: cancel-in-progress: true timeout-minutes: 30 steps: + - run: df -h + - name: "node-cleanup" + run: | + sudo rm -rf /usr/local/lib/android + sudo docker image prune --all --force + sudo docker builder prune -a + - run: df -h - name: Checkout repository id: checkout-stdb uses: actions/checkout@v4 From 2bd5329bf20c9567853054e069bfee78fb8646ab Mon Sep 17 00:00:00 2001 From: rekhoff Date: Tue, 30 Sep 2025 09:31:28 -0700 Subject: [PATCH 12/14] Add comment to node cleanup action Co-authored-by: Zeke Foppa <196249+bfops@users.noreply.github.com> Signed-off-by: rekhoff --- .github/workflows/csharp-test.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/workflows/csharp-test.yml b/.github/workflows/csharp-test.yml index 6dc28ca9db1..20bfe03befc 100644 --- a/.github/workflows/csharp-test.yml +++ b/.github/workflows/csharp-test.yml @@ -16,6 +16,7 @@ jobs: timeout-minutes: 30 steps: - run: df -h + # Free up disk space because otherwise we run out during the test - name: "node-cleanup" run: | sudo rm -rf /usr/local/lib/android From 420107bdafff8cccd408139074feff6464e42843 Mon Sep 17 00:00:00 2001 From: rekhoff Date: Tue, 30 Sep 2025 09:34:28 -0700 Subject: [PATCH 13/14] Removes global.json move for csharp-test.yml in favor of #3297 --- .github/workflows/csharp-test.yml | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/.github/workflows/csharp-test.yml b/.github/workflows/csharp-test.yml index 20bfe03befc..01ba8ea6e6d 100644 --- a/.github/workflows/csharp-test.yml +++ b/.github/workflows/csharp-test.yml @@ -26,16 +26,13 @@ jobs: - name: Checkout repository id: checkout-stdb uses: actions/checkout@v4 - - # Copy global.json to the current directory so that the dotnet things use it - - run: cp modules/global.json global.json # Run cheap .NET tests first. If those fail, no need to run expensive Unity tests. - name: Setup dotnet uses: actions/setup-dotnet@v3 with: - global-json-file: global.json + global-json-file: modules/global.json - name: Override NuGet packages run: | From 7341d680341498d3b42f83aa0ec743af03e06d61 Mon Sep 17 00:00:00 2001 From: rekhoff Date: Tue, 30 Sep 2025 14:15:12 -0700 Subject: [PATCH 14/14] Updated verified files in SDK tests --- ...p_dumpName=LegacySubscribeAll.verified.txt | 400 +++++++++++++--- ...ump_dumpName=SubscribeApplied.verified.txt | 448 ++++++++++++++---- 2 files changed, 700 insertions(+), 148 deletions(-) diff --git a/sdks/csharp/tests~/SnapshotTests.VerifySampleDump_dumpName=LegacySubscribeAll.verified.txt b/sdks/csharp/tests~/SnapshotTests.VerifySampleDump_dumpName=LegacySubscribeAll.verified.txt index 4dd3f646b4f..ad04d010a6e 100644 --- a/sdks/csharp/tests~/SnapshotTests.VerifySampleDump_dumpName=LegacySubscribeAll.verified.txt +++ b/sdks/csharp/tests~/SnapshotTests.VerifySampleDump_dumpName=LegacySubscribeAll.verified.txt @@ -18,8 +18,8 @@ ConnectionId: Guid_1 }, user: { - Identity: Identity_1, - Online: true + identity: Identity_1, + online: true } }, OnInsertUser: { @@ -35,14 +35,26 @@ ConnectionId: Guid_1 }, user: { - Identity: Identity_2, - Online: true + identity: Identity_2, + online: true } }, OnInsertUser: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487763059031, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.IdentityConnected + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -52,14 +64,27 @@ ConnectionId: Guid_1 }, user: { - Identity: Identity_3, - Online: true + identity: Identity_3, + online: true } }, OnUpdateUser: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487768057579, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_1, + CallerConnectionId: Guid_3, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SetName, + name: A + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -69,19 +94,61 @@ ConnectionId: Guid_1 }, oldUser: { - Identity: Identity_1, - Online: true + identity: Identity_1, + online: true }, newUser: { - Identity: Identity_1, - Name: A, - Online: true + identity: Identity_1, + name: A, + online: true } }, + OnSetName: { + Event: { + Timestamp: 1718487768057579, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_1, + CallerConnectionId: Guid_3, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SetName, + name: A + } + }, + Db: { + Message: { + Count: 4 + }, + User: { + Identity: {}, + Count: 3 + } + }, + Reducers: {}, + SetReducerFlags: {}, + IsActive: false, + Identity: Identity_1, + ConnectionId: Guid_1 + }, OnInsertMessage: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487775346381, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Hello, A! + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -91,15 +158,57 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_3, - Sent: 1718487775346381, - Text: Hello, A! + sender: Identity_3, + sent: 1718487775346381, + text: Hello, A! } }, + OnSendMessage: { + Event: { + Timestamp: 1718487775346381, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Hello, A! + } + }, + Db: { + Message: { + Count: 4 + }, + User: { + Identity: {}, + Count: 3 + } + }, + Reducers: {}, + SetReducerFlags: {}, + IsActive: false, + Identity: Identity_1, + ConnectionId: Guid_1 + }, OnUpdateUser: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487777307855, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SetName, + name: B + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -109,19 +218,61 @@ ConnectionId: Guid_1 }, oldUser: { - Identity: Identity_3, - Online: true + identity: Identity_3, + online: true }, newUser: { - Identity: Identity_3, - Name: B, - Online: true + identity: Identity_3, + name: B, + online: true } }, + OnSetName: { + Event: { + Timestamp: 1718487777307855, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SetName, + name: B + } + }, + Db: { + Message: { + Count: 4 + }, + User: { + Identity: {}, + Count: 3 + } + }, + Reducers: {}, + SetReducerFlags: {}, + IsActive: false, + Identity: Identity_1, + ConnectionId: Guid_1 + }, OnInsertMessage: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487783175083, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_1, + CallerConnectionId: Guid_3, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Hello, B! + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -131,15 +282,57 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_1, - Sent: 1718487783175083, - Text: Hello, B! + sender: Identity_1, + sent: 1718487783175083, + text: Hello, B! } }, + OnSendMessage: { + Event: { + Timestamp: 1718487783175083, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_1, + CallerConnectionId: Guid_3, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Hello, B! + } + }, + Db: { + Message: { + Count: 4 + }, + User: { + Identity: {}, + Count: 3 + } + }, + Reducers: {}, + SetReducerFlags: {}, + IsActive: false, + Identity: Identity_1, + ConnectionId: Guid_1 + }, OnInsertMessage: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487787645364, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Goodbye! + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -149,15 +342,56 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_3, - Sent: 1718487787645364, - Text: Goodbye! + sender: Identity_3, + sent: 1718487787645364, + text: Goodbye! } }, + OnSendMessage: { + Event: { + Timestamp: 1718487787645364, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Goodbye! + } + }, + Db: { + Message: { + Count: 4 + }, + User: { + Identity: {}, + Count: 3 + } + }, + Reducers: {}, + SetReducerFlags: {}, + IsActive: false, + Identity: Identity_1, + ConnectionId: Guid_1 + }, OnUpdateUser: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487791901504, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.IdentityDisconnected + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -167,20 +401,33 @@ ConnectionId: Guid_1 }, oldUser: { - Identity: Identity_3, - Name: B, - Online: true + identity: Identity_3, + name: B, + online: true }, newUser: { - Identity: Identity_3, - Name: B, - Online: false + identity: Identity_3, + name: B, + online: false } }, OnInsertMessage: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487794937841, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_1, + CallerConnectionId: Guid_3, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Goodbye! + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -190,49 +437,78 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_1, - Sent: 1718487794937841, - Text: Goodbye! + sender: Identity_1, + sent: 1718487794937841, + text: Goodbye! } + }, + OnSendMessage: { + Event: { + Timestamp: 1718487794937841, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_1, + CallerConnectionId: Guid_3, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Goodbye! + } + }, + Db: { + Message: { + Count: 4 + }, + User: { + Identity: {}, + Count: 3 + } + }, + Reducers: {}, + SetReducerFlags: {}, + IsActive: false, + Identity: Identity_1, + ConnectionId: Guid_1 } }, FinalSnapshot: { User: [ { - Identity: Identity_1, - Name: A, - Online: true + identity: Identity_1, + name: A, + online: true }, { - Identity: Identity_2, - Online: true + identity: Identity_2, + online: true }, { - Identity: Identity_3, - Name: B, - Online: false + identity: Identity_3, + name: B, + online: false } ], Message: [ { - Sender: Identity_3, - Sent: 1718487775346381, - Text: Hello, A! + sender: Identity_3, + sent: 1718487775346381, + text: Hello, A! }, { - Sender: Identity_1, - Sent: 1718487783175083, - Text: Hello, B! + sender: Identity_1, + sent: 1718487783175083, + text: Hello, B! }, { - Sender: Identity_3, - Sent: 1718487787645364, - Text: Goodbye! + sender: Identity_3, + sent: 1718487787645364, + text: Goodbye! }, { - Sender: Identity_1, - Sent: 1718487794937841, - Text: Goodbye! + sender: Identity_1, + sent: 1718487794937841, + text: Goodbye! } ] }, diff --git a/sdks/csharp/tests~/SnapshotTests.VerifySampleDump_dumpName=SubscribeApplied.verified.txt b/sdks/csharp/tests~/SnapshotTests.VerifySampleDump_dumpName=SubscribeApplied.verified.txt index fa31e49891f..9368d6d83a9 100644 --- a/sdks/csharp/tests~/SnapshotTests.VerifySampleDump_dumpName=SubscribeApplied.verified.txt +++ b/sdks/csharp/tests~/SnapshotTests.VerifySampleDump_dumpName=SubscribeApplied.verified.txt @@ -18,8 +18,8 @@ ConnectionId: Guid_1 }, user: { - Identity: Identity_1, - Online: true + identity: Identity_1, + online: true } }, OnInsertUser: { @@ -35,14 +35,26 @@ ConnectionId: Guid_1 }, user: { - Identity: Identity_2, - Online: true + identity: Identity_2, + online: true } }, OnInsertUser: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487763059031, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.IdentityConnected + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -52,14 +64,27 @@ ConnectionId: Guid_1 }, user: { - Identity: Identity_3, - Online: true + identity: Identity_3, + online: true } }, OnUpdateUser: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487768057579, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_1, + CallerConnectionId: Guid_3, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SetName, + name: A + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -69,19 +94,61 @@ ConnectionId: Guid_1 }, oldUser: { - Identity: Identity_1, - Online: true + identity: Identity_1, + online: true }, newUser: { - Identity: Identity_1, - Name: A, - Online: true + identity: Identity_1, + name: A, + online: true } }, + OnSetName: { + Event: { + Timestamp: 1718487768057579, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_1, + CallerConnectionId: Guid_3, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SetName, + name: A + } + }, + Db: { + Message: { + Count: 4 + }, + User: { + Identity: {}, + Count: 3 + } + }, + Reducers: {}, + SetReducerFlags: {}, + IsActive: false, + Identity: Identity_1, + ConnectionId: Guid_1 + }, OnInsertMessage: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487775346381, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Hello, A! + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -91,15 +158,57 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_3, - Sent: 1718487775346381, - Text: Hello, A! + sender: Identity_3, + sent: 1718487775346381, + text: Hello, A! } }, + OnSendMessage: { + Event: { + Timestamp: 1718487775346381, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Hello, A! + } + }, + Db: { + Message: { + Count: 4 + }, + User: { + Identity: {}, + Count: 3 + } + }, + Reducers: {}, + SetReducerFlags: {}, + IsActive: false, + Identity: Identity_1, + ConnectionId: Guid_1 + }, OnUpdateUser: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487777307855, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SetName, + name: B + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -109,19 +218,61 @@ ConnectionId: Guid_1 }, oldUser: { - Identity: Identity_3, - Online: true + identity: Identity_3, + online: true }, newUser: { - Identity: Identity_3, - Name: B, - Online: true + identity: Identity_3, + name: B, + online: true } }, + OnSetName: { + Event: { + Timestamp: 1718487777307855, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SetName, + name: B + } + }, + Db: { + Message: { + Count: 4 + }, + User: { + Identity: {}, + Count: 3 + } + }, + Reducers: {}, + SetReducerFlags: {}, + IsActive: false, + Identity: Identity_1, + ConnectionId: Guid_1 + }, OnInsertMessage: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487783175083, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_1, + CallerConnectionId: Guid_3, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Hello, B! + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -131,15 +282,57 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_1, - Sent: 1718487783175083, - Text: Hello, B! + sender: Identity_1, + sent: 1718487783175083, + text: Hello, B! } }, + OnSendMessage: { + Event: { + Timestamp: 1718487783175083, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_1, + CallerConnectionId: Guid_3, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Hello, B! + } + }, + Db: { + Message: { + Count: 4 + }, + User: { + Identity: {}, + Count: 3 + } + }, + Reducers: {}, + SetReducerFlags: {}, + IsActive: false, + Identity: Identity_1, + ConnectionId: Guid_1 + }, OnInsertMessage: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487787645364, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Goodbye! + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -149,15 +342,56 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_3, - Sent: 1718487787645364, - Text: Goodbye! + sender: Identity_3, + sent: 1718487787645364, + text: Goodbye! } }, + OnSendMessage: { + Event: { + Timestamp: 1718487787645364, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Goodbye! + } + }, + Db: { + Message: { + Count: 4 + }, + User: { + Identity: {}, + Count: 3 + } + }, + Reducers: {}, + SetReducerFlags: {}, + IsActive: false, + Identity: Identity_1, + ConnectionId: Guid_1 + }, OnUpdateUser: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487791901504, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_3, + CallerConnectionId: Guid_2, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.IdentityDisconnected + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -167,20 +401,33 @@ ConnectionId: Guid_1 }, oldUser: { - Identity: Identity_3, - Name: B, - Online: true + identity: Identity_3, + name: B, + online: true }, newUser: { - Identity: Identity_3, - Name: B, - Online: false + identity: Identity_3, + name: B, + online: false } }, OnInsertMessage: { eventContext: { Event: { - $type: Event.UnknownTransaction + $type: Event.Reducer, + ReducerEvent: { + Timestamp: 1718487794937841, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_1, + CallerConnectionId: Guid_3, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Goodbye! + } + } }, Db: {Scrubbed}, Reducers: {Scrubbed}, @@ -190,11 +437,40 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_1, - Sent: 1718487794937841, - Text: Goodbye! + sender: Identity_1, + sent: 1718487794937841, + text: Goodbye! } }, + OnSendMessage: { + Event: { + Timestamp: 1718487794937841, + Status: { + $type: Status.Committed + }, + CallerIdentity: Identity_1, + CallerConnectionId: Guid_3, + EnergyConsumed: {}, + Reducer: { + $type: Reducer.SendMessage, + text: Goodbye! + } + }, + Db: { + Message: { + Count: 4 + }, + User: { + Identity: {}, + Count: 3 + } + }, + Reducers: {}, + SetReducerFlags: {}, + IsActive: false, + Identity: Identity_1, + ConnectionId: Guid_1 + }, OnDeleteMessage: { eventContext: { Event: { @@ -208,9 +484,9 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_3, - Sent: 1718487775346381, - Text: Hello, A! + sender: Identity_3, + sent: 1718487775346381, + text: Hello, A! } }, OnDeleteMessage: { @@ -226,9 +502,9 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_1, - Sent: 1718487783175083, - Text: Hello, B! + sender: Identity_1, + sent: 1718487783175083, + text: Hello, B! } }, OnDeleteMessage: { @@ -244,9 +520,9 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_3, - Sent: 1718487787645364, - Text: Goodbye! + sender: Identity_3, + sent: 1718487787645364, + text: Goodbye! } }, OnDeleteMessage: { @@ -262,9 +538,9 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_1, - Sent: 1718487794937841, - Text: Goodbye! + sender: Identity_1, + sent: 1718487794937841, + text: Goodbye! } }, LogWarning: Subscription Error: $bad query dude, @@ -281,9 +557,9 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_3, - Sent: 1718487775346381, - Text: Hello, A! + sender: Identity_3, + sent: 1718487775346381, + text: Hello, A! } }, OnInsertMessage: { @@ -299,9 +575,9 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_1, - Sent: 1718487783175083, - Text: Hello, B! + sender: Identity_1, + sent: 1718487783175083, + text: Hello, B! } }, OnInsertMessage: { @@ -317,9 +593,9 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_3, - Sent: 1718487787645364, - Text: Goodbye! + sender: Identity_3, + sent: 1718487787645364, + text: Goodbye! } }, OnInsertMessage: { @@ -335,49 +611,49 @@ ConnectionId: Guid_1 }, message: { - Sender: Identity_1, - Sent: 1718487794937841, - Text: Goodbye! + sender: Identity_1, + sent: 1718487794937841, + text: Goodbye! } } }, FinalSnapshot: { User: [ { - Identity: Identity_1, - Name: A, - Online: true + identity: Identity_1, + name: A, + online: true }, { - Identity: Identity_2, - Online: true + identity: Identity_2, + online: true }, { - Identity: Identity_3, - Name: B, - Online: false + identity: Identity_3, + name: B, + online: false } ], Message: [ { - Sender: Identity_1, - Sent: 1718487794937841, - Text: Goodbye! + sender: Identity_1, + sent: 1718487794937841, + text: Goodbye! }, { - Sender: Identity_3, - Sent: 1718487787645364, - Text: Goodbye! + sender: Identity_3, + sent: 1718487787645364, + text: Goodbye! }, { - Sender: Identity_1, - Sent: 1718487783175083, - Text: Hello, B! + sender: Identity_1, + sent: 1718487783175083, + text: Hello, B! }, { - Sender: Identity_3, - Sent: 1718487775346381, - Text: Hello, A! + sender: Identity_3, + sent: 1718487775346381, + text: Hello, A! } ] },