From 815024affd86e1f6e5195f9bf308a51eb6f2d524 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 12 Sep 2024 11:46:01 -0400 Subject: [PATCH 01/27] c# client generate --- crates/cli/src/subcommands/generate/csharp.rs | 220 +++++++++--------- 1 file changed, 109 insertions(+), 111 deletions(-) diff --git a/crates/cli/src/subcommands/generate/csharp.rs b/crates/cli/src/subcommands/generate/csharp.rs index 4244f2a095..ff02a339dc 100644 --- a/crates/cli/src/subcommands/generate/csharp.rs +++ b/crates/cli/src/subcommands/generate/csharp.rs @@ -516,7 +516,6 @@ fn autogen_csharp_access_funcs_for_struct( pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &str) -> String { let func_name = &*reducer.name; - // let reducer_pascal_name = func_name.to_case(Case::Pascal); let func_name_pascal_case = func_name.to_case(Case::Pascal); let mut output = CsharpAutogen::new(namespace, &[]); @@ -528,101 +527,46 @@ pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &st "public partial class {func_name_pascal_case}ArgsStruct : IReducerArgs" ); - let mut func_params: String = String::new(); - let mut field_inits: String = String::new(); - indented_block(&mut output, |output| { - writeln!( - output, - "ReducerType IReducerArgs.ReducerType => ReducerType.{func_name_pascal_case};" - ); writeln!(output, "string IReducerArgsBase.ReducerName => \"{func_name}\";"); - writeln!(output, "bool IReducerArgs.InvokeHandler(ReducerEvent reducerEvent) => Reducer.On{func_name_pascal_case}(reducerEvent, this);"); + writeln!(output, "bool IReducerArgs.InvokeHandler(EventContext ctx) => ctx.Reducers.Invoke{func_name_pascal_case}(ctx, this);"); if !reducer.args.is_empty() { writeln!(output); } - for (arg_i, arg) in reducer.args.iter().enumerate() { + for arg in reducer.args.iter() { let name = arg .name .as_deref() .unwrap_or_else(|| panic!("reducer args should have names: {func_name}")); - let arg_name = name.to_case(Case::Camel); - let field_name = name.to_case(Case::Pascal); let arg_type_str = ty_fmt(ctx, &arg.algebraic_type, namespace); + let field_name = name.to_case(Case::Pascal); - if arg_i != 0 { - func_params.push_str(", "); - field_inits.push_str(", "); - } write!(output, "public {arg_type_str} {field_name}"); // Skip default initializer if it's the same as the implicit default. if let Some(default) = default_init(ctx, &arg.algebraic_type) { write!(output, " = {default}"); } writeln!(output, ";"); - write!(func_params, "{arg_type_str} {arg_name}").unwrap(); - write!(field_inits, "{field_name} = {arg_name}").unwrap(); } }); - writeln!(output); - - writeln!(output, "public static partial class Reducer"); - indented_block(&mut output, |output| { - let delegate_separator = if !reducer.args.is_empty() { ", " } else { "" }; - writeln!( - output, - "public delegate void {func_name_pascal_case}Handler(ReducerEvent reducerEvent{delegate_separator}{func_params});" - ); - writeln!( - output, - "public static event {func_name_pascal_case}Handler? On{func_name_pascal_case}Event;" - ); - - writeln!(output); - - writeln!(output, "public static void {func_name_pascal_case}({func_params})"); - indented_block(output, |output| { - writeln!( - output, - "SpacetimeDBClient.instance.InternalCallReducer(new {func_name_pascal_case}ArgsStruct {{ {field_inits} }});" - ); - }); - writeln!(output); - - writeln!( - output, - "public static bool On{func_name_pascal_case}(ReducerEvent reducerEvent, {func_name_pascal_case}ArgsStruct args)" - ); - indented_block(output, |output| { - writeln!(output, "if (On{func_name_pascal_case}Event == null) return false;"); - writeln!(output, "On{func_name_pascal_case}Event("); - // Write out arguments one per line - { - indent_scope!(output); - write!(output, "reducerEvent"); - for (i, arg) in reducer.args.iter().enumerate() { - writeln!(output, ","); - let arg_name = arg - .name - .as_deref() - .map_or_else(|| format!("Arg{i}"), |name| name.to_case(Case::Pascal)); - write!(output, "args.{arg_name}"); - } - writeln!(output); - } - writeln!(output, ");"); - writeln!(output, "return true;"); - }); - }); - writeln!(output); - output.into_inner() } pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) -> Vec<(String, String)> { let mut results = Vec::new(); + let tables = items + .iter() + .filter_map(|i| { + if let GenItem::Table(table) = i { + Some(table) + } + else { + None + } + }); + let reducers: Vec<&ReducerDef> = items .iter() .filter_map(|i| { @@ -640,23 +584,98 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) let mut output = CsharpAutogen::new(namespace, &["SpacetimeDB.ClientApi"]); - writeln!(output, "public enum ReducerType"); + writeln!(output, "public interface IReducerArgs : IReducerArgsBase"); indented_block(&mut output, |output| { - writeln!(output, "None,"); - for reducer_name in &reducer_names { - writeln!(output, "{reducer_name},"); + writeln!(output, "bool InvokeHandler(EventContext ctx);"); + }); + writeln!(output); + + writeln!(output, "public sealed class RemoteTables"); + indented_block(&mut output, |output| { + for table in tables { + let name = &table.schema.table_name; + writeln!(output, "public readonly RemoteTableHandle {} = new();", name, name); } }); writeln!(output); - writeln!(output, "public interface IReducerArgs : IReducerArgsBase"); + writeln!(output, "public sealed class RemoteReducers : RemoteBase"); indented_block(&mut output, |output| { - writeln!(output, "ReducerType ReducerType {{ get; }}"); - writeln!(output, "bool InvokeHandler(ReducerEvent reducerEvent);"); + for reducer in &reducers { + let func_name = &*reducer.name; + let func_name_pascal_case = func_name.to_case(Case::Pascal); + let delegate_separator = if !reducer.args.is_empty() { ", " } else { "" }; + + let mut func_params: String = String::new(); + let mut field_inits: String = String::new(); + + for (arg_i, arg) in reducer.args.iter().enumerate() { + if arg_i != 0 { + func_params.push_str(", "); + field_inits.push_str(", "); + } + + let name = arg + .name + .as_deref() + .unwrap_or_else(|| panic!("reducer args should have names: {func_name}")); + let arg_type_str = ty_fmt(ctx, &arg.algebraic_type, namespace); + let arg_name = name.to_case(Case::Camel); + let field_name = name.to_case(Case::Pascal); + + write!(func_params, "{arg_type_str} {arg_name}").unwrap(); + write!(field_inits, "{field_name} = {arg_name}").unwrap(); + } + + writeln!( + output, + "public delegate void {func_name_pascal_case}Handler(EventContext ctx{delegate_separator}{func_params});" + ); + writeln!( + output, + "public event {func_name_pascal_case}Handler? On{func_name_pascal_case};" + ); + writeln!(output); + + + writeln!(output, "public void {func_name_pascal_case}({func_params})"); + indented_block(output, |output| { + writeln!( + output, + "conn.InternalCallReducer(new {func_name_pascal_case}ArgsStruct {{ {field_inits} }});" + ); + }); + writeln!(output); + + writeln!( + output, + "public bool Invoke{func_name_pascal_case}(EventContext ctx, {func_name_pascal_case}ArgsStruct args)" + ); + indented_block(output, |output| { + writeln!(output, "if (On{func_name_pascal_case} == null) return false;"); + writeln!(output, "On{func_name_pascal_case}("); + // Write out arguments one per line + { + indent_scope!(output); + write!(output, "ctx"); + for (i, arg) in reducer.args.iter().enumerate() { + writeln!(output, ","); + let arg_name = arg + .name + .as_deref() + .map_or_else(|| format!("Arg{i}"), |name| name.to_case(Case::Pascal)); + write!(output, "args.{arg_name}"); + } + writeln!(output); + } + writeln!(output, ");"); + writeln!(output, "return true;"); + }); + } }); writeln!(output); - writeln!(output, "public partial class ReducerEvent : ReducerEventBase"); + writeln!(output, "public partial class EventContext : EventContextBase"); indented_block(&mut output, |output| { writeln!(output, "public IReducerArgs? Args {{ get; }}"); writeln!(output); @@ -664,33 +683,8 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) writeln!(output); writeln!( output, - r#"[Obsolete("ReducerType is deprecated, please match directly on type of .Args instead.")]"# + "public EventContext(DbConnection conn, TransactionUpdate update, IReducerArgs? args) : base(conn.RemoteTables, conn.RemoteReducers, update) => Args = args;" ); - writeln!( - output, - "public ReducerType Reducer => Args?.ReducerType ?? ReducerType.None;" - ); - writeln!(output); - writeln!( - output, - "public ReducerEvent(IReducerArgs? args) : base() => Args = args;" - ); - writeln!( - output, - "public ReducerEvent(TransactionUpdate update, IReducerArgs? args) : base(update) => Args = args;" - ); - writeln!(output); - // Properties for reducer args - for reducer_name in &reducer_names { - writeln!( - output, - r#"[Obsolete("Accessors that implicitly cast `Args` are deprecated, please match `Args` against the desired type explicitly instead.")]"# - ); - writeln!( - output, - "public {reducer_name}ArgsStruct {reducer_name}Args => ({reducer_name}ArgsStruct)Args!;" - ); - } writeln!(output); // Event handlers. writeln!( @@ -702,11 +696,18 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) writeln!( output, - "public class SpacetimeDBClient : SpacetimeDBClientBase" + "public class DbConnection : DbConnectionBase" ); indented_block(&mut output, |output| { - writeln!(output, "protected SpacetimeDBClient()"); + writeln!(output, "public readonly RemoteTables RemoteTables = new();"); + writeln!(output, "public readonly RemoteReducers RemoteReducers = new();"); + writeln!(output); + + writeln!(output, "public DbConnection()"); indented_block(output, |output| { + writeln!(output, "RemoteReducers.Init(this);"); + writeln!(output); + for item in items { if let GenItem::Table(table) = item { writeln!( @@ -719,12 +720,9 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) }); writeln!(output); - writeln!(output, "public static readonly SpacetimeDBClient instance = new();"); - writeln!(output); - writeln!( output, - "protected override ReducerEvent ReducerEventFromDbEvent(TransactionUpdate update)" + "protected override EventContext ReducerEventFromDbEvent(TransactionUpdate update)" ); indented_block(output, |output| { writeln!(output, "var encodedArgs = update.ReducerCall.Args;"); @@ -748,7 +746,7 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) ); } writeln!(output, "}};"); - writeln!(output, "return new ReducerEvent(update, args);"); + writeln!(output, "return new EventContext(this, update, args);"); }); }); From c8f14d213a6b1cce03173b319186673eb970ab4d Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Wed, 18 Sep 2024 00:19:05 -0400 Subject: [PATCH 02/27] Connection types, C# module --- crates/bindings-csharp/BSATN.Runtime/Db.cs | 11 + crates/bindings-csharp/Codegen/Module.cs | 258 +++--- crates/bindings-csharp/Runtime/Attrs.cs | 83 +- .../Runtime/Internal/IReducer.cs | 4 +- .../Runtime/Internal/ITable.cs | 28 +- .../Runtime/Internal/Module.cs | 18 +- crates/bindings-csharp/Runtime/Runtime.cs | 43 +- modules/sdk-test-connect-disconnect-cs/Lib.cs | 38 +- ... => sdk-test-connect-disconnect-cs.csproj} | 2 + modules/sdk-test-cs/Lib.cs | 829 ++++++++++-------- .../{StdbModule.csproj => sdk-test-cs.csproj} | 2 + modules/sdk-test-multi-cs/.gitignore | 2 + modules/sdk-test-multi-cs/Lib.cs | 51 ++ modules/sdk-test-multi-cs/README.md | 3 + .../sdk-test-multi-cs.csproj | 22 + modules/spacetimedb-quickstart-cs/Lib.cs | 39 +- ...> spacetimedb-quickstart-server-cs.csproj} | 4 +- 17 files changed, 882 insertions(+), 555 deletions(-) create mode 100644 crates/bindings-csharp/BSATN.Runtime/Db.cs rename modules/sdk-test-connect-disconnect-cs/{StdbModule.csproj => sdk-test-connect-disconnect-cs.csproj} (87%) rename modules/sdk-test-cs/{StdbModule.csproj => sdk-test-cs.csproj} (89%) create mode 100644 modules/sdk-test-multi-cs/.gitignore create mode 100644 modules/sdk-test-multi-cs/Lib.cs create mode 100644 modules/sdk-test-multi-cs/README.md create mode 100644 modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj rename modules/spacetimedb-quickstart-cs/{StdbModule.csproj => spacetimedb-quickstart-server-cs.csproj} (83%) diff --git a/crates/bindings-csharp/BSATN.Runtime/Db.cs b/crates/bindings-csharp/BSATN.Runtime/Db.cs new file mode 100644 index 0000000000..ede864f654 --- /dev/null +++ b/crates/bindings-csharp/BSATN.Runtime/Db.cs @@ -0,0 +1,11 @@ +namespace SpacetimeDB; + +public abstract class DbContext + where DbView : class, new() +{ + public readonly DbView Db; + + public DbContext() => Db = new(); + + public DbContext(DbView db) => Db = db; +} diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index 5127714b89..adaa7b6abf 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -7,7 +7,7 @@ namespace SpacetimeDB.Codegen; record ColumnDeclaration : MemberDeclaration { - public readonly ColumnAttrs Attrs; + public readonly ImmutableArray<(string?, ColumnAttrs)> Attrs; public readonly bool IsEquatable; public ColumnDeclaration( @@ -19,7 +19,8 @@ bool isEquatable ) : base(name, type, typeInfo) { - Attrs = attrs; + (string?, ColumnAttrs)[] x = [(default(string), attrs)]; + Attrs = x.ToImmutableArray(); IsEquatable = isEquatable; } @@ -28,9 +29,15 @@ public ColumnDeclaration(IFieldSymbol field) { Attrs = field .GetAttributes() - .Where(a => a.AttributeClass?.ToString() == typeof(ColumnAttribute).FullName) - .Select(a => a.ParseAs().Type) - .SingleOrDefault(); + .Select(a => (a.NamedArguments.FirstOrDefault(a => a.Key == "Table").Value.Value as string, + a.AttributeClass?.ToString() switch { + "SpacetimeDB.AutoIncAttribute" => ColumnAttrs.AutoInc, + "SpacetimeDB.PrimaryKeyAttribute" => ColumnAttrs.PrimaryKey, + "SpacetimeDB.UniqueAttribute" => ColumnAttrs.Unique, + "SpacetimeDB.IndexedAttribute" => ColumnAttrs.Indexed, + _ => ColumnAttrs.UnSet, + })) + .ToImmutableArray(); var type = field.Type; @@ -54,7 +61,9 @@ or SpecialType.System_Int64 _ => false, }; - if (Attrs.HasFlag(ColumnAttrs.AutoInc) && !isInteger) + var attrs = Attrs.Aggregate(ColumnAttrs.UnSet, (xs, x) => xs | x.Item2); + + if (attrs.HasFlag(ColumnAttrs.AutoInc) && !isInteger) { throw new Exception( $"{type} {Name} is not valid for AutoInc or Identity as it's not an integer." @@ -75,7 +84,7 @@ or SpecialType.System_Int64 ) && type.NullableAnnotation != NullableAnnotation.Annotated; - if (Attrs.HasFlag(ColumnAttrs.Unique) && !IsEquatable) + if (attrs.HasFlag(ColumnAttrs.Unique) && !IsEquatable) { throw new Exception( $"{type} {Name} is not valid for Identity, PrimaryKey or PrimaryKeyAuto as it's not an equatable primitive." @@ -83,6 +92,10 @@ or SpecialType.System_Int64 } } + public ColumnAttrs GetAttrs(string tableName) => Attrs + .Where(x => x.Item1 == null || x.Item1 == tableName) + .Aggregate(ColumnAttrs.UnSet, (xs, x) => xs | x.Item2); + // For the `TableDesc` constructor. public string GenerateColumnDef() => $"new (nameof({Name}), BSATN.{Name}.GetAlgebraicType(registrar))"; @@ -92,10 +105,30 @@ public string GenerateFilterEntry() => $"new (nameof({Name}), (w, v) => BSATN.{Name}.Write(w, ({Type}) v!))"; } +record TableView { + public readonly TableDeclaration Table; + public readonly string Name; + public readonly bool IsPublic; + public readonly string? Scheduled; + + public TableView(TableDeclaration table, AttributeData data) { + Table = table; + Name = data.NamedArguments.FirstOrDefault(x => x.Key == "Name").Value.Value as string ?? table.ShortName; + + IsPublic = data.NamedArguments.Any(pair => pair is { Key: "Public", Value.Value: true }); + + Scheduled = data.NamedArguments + .Where(pair => pair.Key == "Scheduled") + .Select(pair => (string?)pair.Value.Value) + .SingleOrDefault(); + } +} + record TableDeclaration : BaseTypeDeclaration { - public readonly bool IsPublic; + public readonly string Visibility; public readonly string? Scheduled; + public readonly ImmutableArray Views; private static readonly ColumnDeclaration[] ScheduledColumns = [ @@ -117,10 +150,21 @@ public TableDeclaration(GeneratorAttributeSyntaxContext context) throw new InvalidOperationException("Tagged enums cannot be tables."); } - var attr = context.Attributes.Single().ParseAs(); + Visibility = context.TargetSymbol.DeclaredAccessibility switch { + Accessibility.ProtectedAndInternal + or Accessibility.NotApplicable + or Accessibility.Internal => "internal", + Accessibility.Public => "public", + _ => throw new Exception( + "Table row type visibility must be public or internal." + ), + }; + + var views = context.Attributes + .Where(a => a.AttributeClass?.ToDisplayString() == "SpacetimeDB.TableAttribute"); - IsPublic = attr.Public; - Scheduled = attr.Scheduled; + Views = views.Select(a => new TableView(this, a)).ToImmutableArray(); + Scheduled = Views.FirstOrDefault(t => t.Scheduled != null)?.Scheduled; if (Scheduled is not null) { @@ -133,6 +177,67 @@ public TableDeclaration(GeneratorAttributeSyntaxContext context) protected override ColumnDeclaration ConvertMember(IFieldSymbol field) => new(field); + public IEnumerable GenerateViewFilters(string viewName, string iTable) { + foreach ( + var (f, i) in Members + .Select((field, i) => (field, i)) + .Where(pair => pair.field.IsEquatable) + ) { + var colEqWhere = $"{iTable}.ColEq.Where({i}, {f.Name}, {FullName}.BSATN.{f.Name})"; + + yield return $""" + public IEnumerable<{FullName}> FilterBy{f.Name}({f.Type} {f.Name}) => + {colEqWhere}.Iter(); + """; + + if (f.GetAttrs(viewName).HasFlag(ColumnAttrs.Unique)) { + yield return $""" + public {FullName}? FindBy{f.Name}({f.Type} {f.Name}) => + FilterBy{f.Name}({f.Name}) + .Cast<{FullName}?>() + .SingleOrDefault(); + + public bool DeleteBy{f.Name}({f.Type} {f.Name}) => + {colEqWhere}.Delete(); + + public bool UpdateBy{f.Name}({f.Type} {f.Name}, ref {FullName} @this) => + {colEqWhere}.Update(ref @this); + """; + } + } + } + + public IEnumerable> GenerateViews() { + foreach (var v in Views) { + var autoIncFields = Members + .Where(f => f.GetAttrs(v.Name).HasFlag(ColumnAttrs.AutoInc)) + .Select(f => f.Name); + + var iTable = $"SpacetimeDB.Internal.ITableView<{v.Name}, {FullName}>"; + yield return new((v.Name, FullName), ($$""" + {{Visibility}} readonly struct {{v.Name}} : {{iTable}} { + static void {{iTable}}.ReadGenFields(System.IO.BinaryReader reader, ref {{FullName}} row) { + {{string.Join( + "\n", + autoIncFields.Select(name => + $$""" + if (row.{{name}} == default) + { + row.{{name}} = {{FullName}}.BSATN.{{name}}.Read(reader); + } + """ + ) + )}} + } + public IEnumerable<{{FullName}}> Iter() => {{iTable}}.Iter(); + public IEnumerable<{{FullName}}> Query(System.Linq.Expressions.Expression> predicate) => {{iTable}}.Query(predicate); + public void Insert(ref {{FullName}} row) => {{iTable}}.Insert(ref row); + {{string.Join("\n", GenerateViewFilters(v.Name, iTable))}} + } + """, $"{Visibility} TableViews.{v.Name} {v.Name} => new();")); + } + } + public override Scope.Extensions ToExtensions() { var extensions = base.ToExtensions(); @@ -155,10 +260,6 @@ public override Scope.Extensions ToExtensions() ); } - var autoIncFields = Members - .Where(f => f.Attrs.HasFlag(ColumnAttrs.AutoInc)) - .Select(f => f.Name); - var iTable = $"SpacetimeDB.Internal.ITable<{ShortName}>"; // ITable inherits IStructuralReadWrite, so we can replace the base type instead of appending another one. @@ -167,21 +268,9 @@ public override Scope.Extensions ToExtensions() extensions.Contents.Append( $$""" - void {{iTable}}.ReadGenFields(System.IO.BinaryReader reader) { - {{string.Join( - "\n", - autoIncFields.Select(name => - $$""" - if ({{name}} == default) - { - {{name}} = BSATN.{{name}}.Read(reader); - } - """ - ) - )}} - } - - static SpacetimeDB.Internal.TableDesc {{iTable}}.MakeTableDesc(SpacetimeDB.BSATN.ITypeRegistrar registrar) => new ( + static IEnumerable {{iTable}}.MakeTableDesc(SpacetimeDB.BSATN.ITypeRegistrar registrar) => [ + {{string.Join("\n", Views.Select(v => $$""" + new ( new ( TableName: nameof({{ShortName}}), Columns: [ @@ -193,15 +282,15 @@ public override Scope.Extensions ToExtensions() ",\n", Members // Important: the position must be stored here, before filtering. - .Select((col, pos) => (col, pos)) - .Where(pair => pair.col.Attrs != ColumnAttrs.UnSet) + .Select((col, pos) => (col, pos, col.GetAttrs(v.Name))) + .Where(tuple => tuple.Item3 != ColumnAttrs.UnSet) .Select(pair => $$""" new ( nameof({{ShortName}}), {{pair.pos}}, nameof({{pair.col.Name}}), - SpacetimeDB.ColumnAttrs.{{pair.col.Attrs}} + (SpacetimeDB.ColumnAttrs){{(int)pair.Item3}} ) """ ) @@ -211,68 +300,29 @@ public override Scope.Extensions ToExtensions() // "system" | "user" TableType: "user", // "public" | "private" - TableAccess: "{{(IsPublic ? "public" : "private")}}", - Scheduled: {{(Scheduled is not null ? $"nameof({Scheduled})" : "null")}} + TableAccess: "{{(v.IsPublic ? "public" : "private")}}", + Scheduled: {{(v.Scheduled is not null ? $"nameof({v.Scheduled})" : "null")}} ), (uint) ((SpacetimeDB.BSATN.AlgebraicType.Ref) new BSATN().GetAlgebraicType(registrar)).Ref_ - ); + ), + """))}} + ]; static SpacetimeDB.Internal.Filter {{iTable}}.CreateFilter() => new([ {{string.Join(",\n", Members.Select(f => f.GenerateFilterEntry()))}} ]); - - public static IEnumerable<{{ShortName}}> Iter() => {{iTable}}.Iter(); - public static IEnumerable<{{ShortName}}> Query(System.Linq.Expressions.Expression> predicate) => {{iTable}}.Query(predicate); - public void Insert() => {{iTable}}.Insert(this); """ ); - foreach ( - var (f, i) in Members - .Select((field, i) => (field, i)) - .Where(pair => pair.field.IsEquatable) - ) - { - var colEqWhere = $"{iTable}.ColEq.Where({i}, {f.Name}, BSATN.{f.Name})"; - - extensions.Contents.Append( - $""" - public static IEnumerable<{ShortName}> FilterBy{f.Name}({f.Type} {f.Name}) => - {colEqWhere}.Iter(); - """ - ); - - if (f.Attrs.HasFlag(ColumnAttrs.Unique)) - { - extensions.Contents.Append( - $""" - public static {ShortName}? FindBy{f.Name}({f.Type} {f.Name}) => - FilterBy{f.Name}({f.Name}) - .Cast<{ShortName}?>() - .SingleOrDefault(); - - public static bool DeleteBy{f.Name}({f.Type} {f.Name}) => - {colEqWhere}.Delete(); - - public static bool UpdateBy{f.Name}({f.Type} {f.Name}, {ShortName} @this) => - {colEqWhere}.Update(@this); - """ - ); - } - } - return extensions; } } record ReducerParamDeclaration : MemberDeclaration { - public readonly bool IsContextArg; - public ReducerParamDeclaration(IParameterSymbol param) : base(param.Name, param.Type) { - IsContextArg = Type == "SpacetimeDB.ReducerContext"; } } @@ -299,31 +349,26 @@ public ReducerDeclaration(GeneratorAttributeSyntaxContext context) ExportName = attr.Name ?? Name; FullName = SymbolToName(method); Args = new( - method.Parameters.Select(p => new ReducerParamDeclaration(p)).ToImmutableArray() + method.Parameters.Skip(1).Select(p => new ReducerParamDeclaration(p)).ToImmutableArray() ); Scope = new Scope(methodSyntax.Parent as MemberDeclarationSyntax); } - private IEnumerable NonContextArgs => Args.Where(a => !a.IsContextArg); - public KeyValuePair GenerateClass() { + var args = string.Join(", ", Args.Select(a => $"{a.Name}.Read(reader)")); + var argsSep = args == "" ? "" : ", "; var class_ = $$""" class {{Name}}: SpacetimeDB.Internal.IReducer { - {{MemberDeclaration.GenerateBsatnFields(Accessibility.Private, NonContextArgs)}} + {{MemberDeclaration.GenerateBsatnFields(Accessibility.Private, Args)}} public SpacetimeDB.Internal.ReducerDef MakeReducerDef(SpacetimeDB.BSATN.ITypeRegistrar registrar) => new ( "{{ExportName}}", - [{{MemberDeclaration.GenerateDefs(NonContextArgs)}}] + [{{MemberDeclaration.GenerateDefs(Args)}}] ); - public void Invoke(BinaryReader reader, SpacetimeDB.ReducerContext ctx) { - {{FullName}}( - {{string.Join( - ", ", - Args.Select(a => a.IsContextArg ? "ctx" : $"{a.Name}.Read(reader)") - )}} - ); + public void Invoke(BinaryReader reader, SpacetimeDB.Internal.IReducerContext ctx) { + {{FullName}}((SpacetimeDB.ReducerContext)ctx{{argsSep}}{{args}}); } } """; @@ -339,13 +384,13 @@ public Scope.Extensions GenerateSchedule() $$""" public static void VolatileNonatomicScheduleImmediate{{Name}}({{string.Join( ", ", - NonContextArgs.Select(a => $"{a.Type} {a.Name}") + Args.Select(a => $"{a.Type} {a.Name}") )}}) { using var stream = new MemoryStream(); using var writer = new BinaryWriter(stream); {{string.Join( "\n", - NonContextArgs.Select(a => $"new {a.TypeInfo}().Write(writer, {a.Name});") + Args.Select(a => $"new {a.TypeInfo}().Write(writer, {a.Name});") )}} SpacetimeDB.Internal.IReducer.VolatileNonatomicScheduleImmediate("{{ExportName}}", stream); } @@ -374,8 +419,6 @@ public void Initialize(IncrementalGeneratorInitializationContext context) .WithTrackingName("SpacetimeDB.Table.GenerateExtensions") .RegisterSourceOutputs(context); - var tableNames = tables.Select((t, ct) => t.FullName).Collect(); - var reducers = context .SyntaxProvider.ForAttributeWithMetadataName( fullyQualifiedMetadataName: typeof(ReducerAttribute).FullName, @@ -394,21 +437,24 @@ public void Initialize(IncrementalGeneratorInitializationContext context) .WithTrackingName("SpacetimeDB.Reducer.GenerateClass") .Collect(); + var tableViews = tables + .SelectMany((t, ct) => t.GenerateViews()) + .WithTrackingName("SpacetimeDB.Table.GenerateViews") + .Collect(); + context.RegisterSourceOutput( - tableNames.Combine(addReducers), + tableViews.Combine(addReducers), (context, tuple) => { // Sort tables and reducers by name to match Rust behaviour. // Not really important outside of testing, but for testing // it matters because we commit module-bindings // so they need to match 1:1 between different langs. - var tableNames = tuple.Left.Sort(); + var tableViews = tuple.Left.Sort((a, b) => a.Key.Item1.CompareTo(b.Key.Item1)); var addReducers = tuple.Right.Sort((a, b) => a.Key.CompareTo(b.Key)); // Don't generate the FFI boilerplate if there are no tables or reducers. - if (tableNames.IsEmpty && addReducers.IsEmpty) - { + if (tableViews.IsEmpty && addReducers.IsEmpty) return; - } context.AddSource( "FFI.cs", $$""" @@ -419,6 +465,18 @@ public void Initialize(IncrementalGeneratorInitializationContext context) using System.Runtime.CompilerServices; using System.Runtime.InteropServices; + namespace SpacetimeDB { + public sealed class ReducerContext : BaseReducerContext {} + + namespace TableViews { + {{string.Join("\n", tableViews.Select(v => v.Value.Item1))}} + } + + public sealed class Local { + {{string.Join("\n", tableViews.Select(v => v.Value.Item2))}} + } + } + static class ModuleRegistration { {{string.Join("\n", addReducers.Select(r => r.Value))}} @@ -431,6 +489,8 @@ static class ModuleRegistration { [DynamicDependency(DynamicallyAccessedMemberTypes.PublicMethods, typeof(SpacetimeDB.Internal.Module))] #endif public static void Main() { + SpacetimeDB.Internal.Module.Initialize(new SpacetimeDB.ReducerContext()); + {{string.Join( "\n", addReducers.Select(r => @@ -439,7 +499,7 @@ public static void Main() { )}} {{string.Join( "\n", - tableNames.Select(t => $"SpacetimeDB.Internal.Module.RegisterTable<{t}>();") + tableViews.Select(t => $"SpacetimeDB.Internal.Module.RegisterTable<{t.Key.Item2}>();") )}} } diff --git a/crates/bindings-csharp/Runtime/Attrs.cs b/crates/bindings-csharp/Runtime/Attrs.cs index 648c925dbc..fa660d50c2 100644 --- a/crates/bindings-csharp/Runtime/Attrs.cs +++ b/crates/bindings-csharp/Runtime/Attrs.cs @@ -1,30 +1,5 @@ namespace SpacetimeDB; -public static class ReducerKind -{ - public const string Init = "__init__"; - public const string Update = "__update__"; - public const string Connect = "__identity_connected__"; - public const string Disconnect = "__identity_disconnected__"; -} - -[AttributeUsage(AttributeTargets.Method, Inherited = false, AllowMultiple = false)] -public sealed class ReducerAttribute(string? name = null) : Attribute -{ - public string? Name => name; -} - -[AttributeUsage( - AttributeTargets.Struct | AttributeTargets.Class, - Inherited = false, - AllowMultiple = false -)] -public sealed class TableAttribute : Attribute -{ - public bool Public { get; init; } - public string? Scheduled { get; init; } -} - [Flags] public enum ColumnAttrs : byte { @@ -40,8 +15,60 @@ public enum ColumnAttrs : byte PrimaryKeyIdentity = PrimaryKeyAuto, } -[AttributeUsage(AttributeTargets.Field, Inherited = false, AllowMultiple = false)] -public sealed class ColumnAttribute(ColumnAttrs type) : Attribute +/// +/// Registers a type as the row structure of a SpacetimeDB table, enabling codegen for it. +/// +/// +/// Multiple [Table] attributes per type are supported. This is useful to reuse row types. +/// Each attribute instance must have a unique name and will create a SpacetimeDB table. +/// +/// +[AttributeUsage(AttributeTargets.Struct, AllowMultiple = true)] +public sealed class TableAttribute : Attribute +{ + /// + /// This identifier is used to name the SpacetimeDB table on the host as well as the + /// table handle structures generated to access the table from within a reducer call. + /// + /// Defaults to the nameof of the target type. + /// + public string? Name; + + /// + /// Set to true to make the table visible to everyone. + /// + /// Defaults to the table only being visible to its owner. + /// + public bool Public = false; + +} + +[AttributeUsage(AttributeTargets.Field)] +public abstract class ColumnAttribute : Attribute { - public ColumnAttrs Type => type; + public string? Table; } + +public sealed class AutoIncAttribute : ColumnAttribute { } + +public sealed class PrimaryKeyAttribute : ColumnAttribute { } + +public sealed class UniqueAttribute : ColumnAttribute { } + +public sealed class IndexedAttribute : ColumnAttribute { } + +public static class ReducerKind +{ + public const string Init = "__init__"; + public const string Update = "__update__"; + public const string Connect = "__identity_connected__"; + public const string Disconnect = "__identity_disconnected__"; +} + +[AttributeUsage(AttributeTargets.Method, Inherited = false)] +public sealed class ReducerAttribute : Attribute +{ + public string? Name; +} + + diff --git a/crates/bindings-csharp/Runtime/Internal/IReducer.cs b/crates/bindings-csharp/Runtime/Internal/IReducer.cs index bb5c8e1fa9..3624c06f6e 100644 --- a/crates/bindings-csharp/Runtime/Internal/IReducer.cs +++ b/crates/bindings-csharp/Runtime/Internal/IReducer.cs @@ -3,12 +3,14 @@ namespace SpacetimeDB.Internal; using System.Text; using SpacetimeDB.BSATN; +public interface IReducerContext { } + public interface IReducer { ReducerDef MakeReducerDef(ITypeRegistrar registrar); // This one is not static because we need to be able to store IReducer in a list. - void Invoke(BinaryReader reader, ReducerContext args); + void Invoke(BinaryReader reader, IReducerContext args); public static void VolatileNonatomicScheduleImmediate(string name, MemoryStream args) { diff --git a/crates/bindings-csharp/Runtime/Internal/ITable.cs b/crates/bindings-csharp/Runtime/Internal/ITable.cs index 2233e04db8..7e54c050c2 100644 --- a/crates/bindings-csharp/Runtime/Internal/ITable.cs +++ b/crates/bindings-csharp/Runtime/Internal/ITable.cs @@ -7,12 +7,18 @@ public interface ITable : IStructuralReadWrite where T : ITable, new() { // These are the methods that codegen needs to implement. - void ReadGenFields(BinaryReader reader); - static abstract TableDesc MakeTableDesc(ITypeRegistrar registrar); + static abstract IEnumerable MakeTableDesc(ITypeRegistrar registrar); + static abstract Filter CreateFilter(); +} - // These are static helpers that codegen can use. +public interface ITableView + where View : ITableView + where T : ITable, new() +{ + static abstract void ReadGenFields(BinaryReader reader, ref T row); + // These are static helpers that codegen can use. private abstract class RawTableIterBase { public class Enumerator(FFI.RowIter handle) : IDisposable @@ -105,7 +111,7 @@ public IEnumerable Parse() using var reader = new BinaryReader(stream); while (stream.Position < stream.Length) { - yield return Read(reader); + yield return IStructuralReadWrite.Read(reader); } } } @@ -134,7 +140,7 @@ protected override void IterStart(out FFI.RowIter handle) => private static readonly Lazy tableId_ = new(() => { - var name_bytes = System.Text.Encoding.UTF8.GetBytes(typeof(T).Name); + var name_bytes = System.Text.Encoding.UTF8.GetBytes(typeof(View).Name); FFI._table_id_from_name(name_bytes, (uint)name_bytes.Length, out var out_); return out_; }); @@ -148,17 +154,17 @@ protected override void IterStart(out FFI.RowIter handle) => public static IEnumerable Query(Expression> query) => new RawTableIterFiltered(tableId, filter.Value.Compile(query)).Parse(); - protected static void Insert(T row) + protected static void Insert(ref T row) { // Insert the row. - var bytes = ToBytes(row); + var bytes = IStructuralReadWrite.ToBytes(row); var bytes_len = (uint)bytes.Length; FFI._datastore_insert_bsatn(tableId, bytes, ref bytes_len); // Write back any generated column values. using var stream = new MemoryStream(bytes, 0, (int)bytes_len); using var reader = new BinaryReader(stream); - row.ReadGenFields(reader); + View.ReadGenFields(reader, ref row); } protected readonly ref struct ColEq @@ -175,7 +181,7 @@ private ColEq(FFI.ColId colId, byte[] value) public static ColEq Where(ushort colId, TCol colValue, TColRW rw) where TColRW : IReadWrite { - return new(new FFI.ColId(colId), ToBytes(rw, colValue)); + return new(new FFI.ColId(colId), IStructuralReadWrite.ToBytes(rw, colValue)); } // Note: do not inline FindBy from the Codegen as a helper API here. @@ -188,14 +194,14 @@ public bool Delete() return out_ > 0; } - public bool Update(T row) + public bool Update(ref T row) { // Just like in Rust bindings, updating is just deleting and inserting for now. if (!Delete()) { return false; } - Insert(row); + Insert(ref row); return true; } } diff --git a/crates/bindings-csharp/Runtime/Internal/Module.cs b/crates/bindings-csharp/Runtime/Internal/Module.cs index 425331c015..dbca3725c9 100644 --- a/crates/bindings-csharp/Runtime/Internal/Module.cs +++ b/crates/bindings-csharp/Runtime/Internal/Module.cs @@ -53,6 +53,10 @@ public static class Module private static readonly RawModuleDefV8 moduleDef = new(); private static readonly List reducers = []; + private static IReducerContext? context = null; + + public static void Initialize(IReducerContext ctx) => context = ctx; + readonly struct TypeRegistrar() : ITypeRegistrar { private readonly Dictionary types = []; @@ -95,7 +99,9 @@ public static void RegisterReducer() public static void RegisterTable() where T : ITable, new() { - moduleDef.RegisterTable(T.MakeTableDesc(typeRegistrar)); + foreach (var t in T.MakeTableDesc(typeRegistrar)) { + moduleDef.RegisterTable(t); + } } private static byte[] Consume(this BytesSource source) @@ -183,19 +189,21 @@ BytesSink error ) { // Piece together the sender identity. - var sender = Identity.From( + Runtime.SenderIdentity = Identity.From( MemoryMarshal.AsBytes([sender_0, sender_1, sender_2, sender_3]).ToArray() ); // Piece together the sender address. - var address = Address.From(MemoryMarshal.AsBytes([address_0, address_1]).ToArray()); + Runtime.SenderAddress = Address.From(MemoryMarshal.AsBytes([address_0, address_1]).ToArray()); + + Runtime.Random = new((int)timestamp.MicrosecondsSinceEpoch); + Runtime.Timestamp = timestamp.ToStd(); try { using var stream = new MemoryStream(args.Consume()); using var reader = new BinaryReader(stream); - var context = new ReducerContext(sender, address, timestamp); - reducers[(int)id].Invoke(reader, context); + reducers[(int)id].Invoke(reader, context!); if (stream.Position != stream.Length) { throw new Exception("Unrecognised extra bytes in the reducer arguments"); diff --git a/crates/bindings-csharp/Runtime/Runtime.cs b/crates/bindings-csharp/Runtime/Runtime.cs index 054b0fbbb5..9105c23287 100644 --- a/crates/bindings-csharp/Runtime/Runtime.cs +++ b/crates/bindings-csharp/Runtime/Runtime.cs @@ -4,30 +4,6 @@ namespace SpacetimeDB; using SpacetimeDB.BSATN; using SpacetimeDB.Internal; -public class ReducerContext -{ - public readonly Identity Sender; - public readonly DateTimeOffset Time; - public readonly Address? Address; - - /// - /// A reducer-specific instance of `System.Random` that is seeded by current reducer's timestamp. This object is unchanged throught the entire reducer call - /// - public readonly Random Rng; - - internal ReducerContext( - Identity senderIdentity, - Address? senderAddress, - DateTimeOffsetRepr timestamp - ) - { - Sender = senderIdentity; - Address = senderAddress; - Time = timestamp.ToStd(); - Rng = new Random((int)timestamp.MicrosecondsSinceEpoch); - } -} - // [SpacetimeDB.Type] - we have custom representation of time in microseconds, so implementing BSATN manually public abstract partial record ScheduleAt : SpacetimeDB.TaggedEnum<(DateTimeOffset Time, TimeSpan Interval)> @@ -81,3 +57,22 @@ public AlgebraicType GetAlgebraicType(ITypeRegistrar registrar) => ); } } + +public abstract class BaseReducerContext : DbContext, IReducerContext + where DbView : class, new() +{ + public Identity Sender => Runtime.SenderIdentity!; + public Address Address => Runtime.SenderAddress!; + public DateTimeOffset Timestamp => Runtime.Timestamp!; +} + +public static class Runtime +{ + public static Random Random { get; internal set; } = new(); + + public static Identity? SenderIdentity { get; internal set; } + + public static Address? SenderAddress { get; internal set; } + + public static DateTimeOffset Timestamp { get; internal set; } +} diff --git a/modules/sdk-test-connect-disconnect-cs/Lib.cs b/modules/sdk-test-connect-disconnect-cs/Lib.cs index 4688033cb4..9991dd61fc 100644 --- a/modules/sdk-test-connect-disconnect-cs/Lib.cs +++ b/modules/sdk-test-connect-disconnect-cs/Lib.cs @@ -1,28 +1,30 @@ +namespace SpacetimeDB.Sdk.Test.ConnectDisconnect; + using SpacetimeDB; -static partial class Module -{ - [SpacetimeDB.Table(Public = true)] - public partial struct Connected - { - public Identity identity; - } +[SpacetimeDB.Table(Public = true)] +public partial struct Connected { + public Identity identity; +} - [SpacetimeDB.Table(Public = true)] - public partial struct Disconnected - { - public Identity identity; - } +[SpacetimeDB.Table(Public = true)] +public partial struct Disconnected { + public Identity identity; +} - [SpacetimeDB.Reducer(ReducerKind.Connect)] - public static void OnConnect(ReducerContext e) +static partial class Module +{ + [SpacetimeDB.Reducer(Name = ReducerKind.Connect)] + public static void OnConnect(ReducerContext ctx) { - new Connected { identity = e.Sender }.Insert(); + var row = new Connected { identity = ctx.Sender }; + ctx.Db.Connected.Insert(ref row); } - [SpacetimeDB.Reducer(ReducerKind.Disconnect)] - public static void OnDisconnect(ReducerContext e) + [SpacetimeDB.Reducer(Name = ReducerKind.Disconnect)] + public static void OnDisconnect(ReducerContext ctx) { - new Disconnected { identity = e.Sender }.Insert(); + var row = new Disconnected { identity = ctx.Sender }; + ctx.Db.Disconnected.Insert(ref row); } } diff --git a/modules/sdk-test-connect-disconnect-cs/StdbModule.csproj b/modules/sdk-test-connect-disconnect-cs/sdk-test-connect-disconnect-cs.csproj similarity index 87% rename from modules/sdk-test-connect-disconnect-cs/StdbModule.csproj rename to modules/sdk-test-connect-disconnect-cs/sdk-test-connect-disconnect-cs.csproj index 7773fe10c0..fbf5b824ad 100644 --- a/modules/sdk-test-connect-disconnect-cs/StdbModule.csproj +++ b/modules/sdk-test-connect-disconnect-cs/sdk-test-connect-disconnect-cs.csproj @@ -1,6 +1,8 @@ + StdbModule + true net8.0 wasi-wasm enable diff --git a/modules/sdk-test-cs/Lib.cs b/modules/sdk-test-cs/Lib.cs index e77fe6890d..918cf8c783 100644 --- a/modules/sdk-test-cs/Lib.cs +++ b/modules/sdk-test-cs/Lib.cs @@ -1,6 +1,8 @@ +namespace SpacetimeDB.Sdk.Test; + using SpacetimeDB; -static partial class Module +public static partial class Module { [SpacetimeDB.Type] public enum SimpleEnum @@ -99,9 +101,10 @@ public partial struct OneU8 } [SpacetimeDB.Reducer] - public static void insert_one_u8(byte n) + public static void insert_one_u8(ReducerContext ctx, byte n) { - new OneU8 { n = n }.Insert(); + var row = new OneU8 { n = n }; + ctx.Db.OneU8.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -111,9 +114,10 @@ public partial struct OneU16 } [SpacetimeDB.Reducer] - public static void insert_one_u16(ushort n) + public static void insert_one_u16(ReducerContext ctx, ushort n) { - new OneU16 { n = n }.Insert(); + var row = new OneU16 { n = n }; + ctx.Db.OneU16.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -123,9 +127,10 @@ public partial struct OneU32 } [SpacetimeDB.Reducer] - public static void insert_one_u32(uint n) + public static void insert_one_u32(ReducerContext ctx, uint n) { - new OneU32 { n = n }.Insert(); + var row = new OneU32 { n = n }; + ctx.Db.OneU32.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -135,9 +140,10 @@ public partial struct OneU64 } [SpacetimeDB.Reducer] - public static void insert_one_u64(ulong n) + public static void insert_one_u64(ReducerContext ctx, ulong n) { - new OneU64 { n = n }.Insert(); + var row = new OneU64 { n = n }; + ctx.Db.OneU64.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -147,9 +153,10 @@ public partial struct OneU128 } [SpacetimeDB.Reducer] - public static void insert_one_u128(U128 n) + public static void insert_one_u128(ReducerContext ctx, U128 n) { - new OneU128 { n = n }.Insert(); + var row = new OneU128 { n = n }; + ctx.Db.OneU128.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -159,9 +166,10 @@ public partial struct OneU256 } [SpacetimeDB.Reducer] - public static void insert_one_u256(U256 n) + public static void insert_one_u256(ReducerContext ctx, U256 n) { - new OneU256 { n = n }.Insert(); + var row = new OneU256 { n = n }; + ctx.Db.OneU256.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -171,9 +179,10 @@ public partial struct OneI8 } [SpacetimeDB.Reducer] - public static void insert_one_i8(sbyte n) + public static void insert_one_i8(ReducerContext ctx, sbyte n) { - new OneI8 { n = n }.Insert(); + var row = new OneI8 { n = n }; + ctx.Db.OneI8.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -183,9 +192,10 @@ public partial struct OneI16 } [SpacetimeDB.Reducer] - public static void insert_one_i16(short n) + public static void insert_one_i16(ReducerContext ctx, short n) { - new OneI16 { n = n }.Insert(); + var row = new OneI16 { n = n }; + ctx.Db.OneI16.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -195,9 +205,10 @@ public partial struct OneI32 } [SpacetimeDB.Reducer] - public static void insert_one_i32(int n) + public static void insert_one_i32(ReducerContext ctx, int n) { - new OneI32 { n = n }.Insert(); + var row = new OneI32 { n = n }; + ctx.Db.OneI32.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -207,9 +218,10 @@ public partial struct OneI64 } [SpacetimeDB.Reducer] - public static void insert_one_i64(long n) + public static void insert_one_i64(ReducerContext ctx, long n) { - new OneI64 { n = n }.Insert(); + var row = new OneI64 { n = n }; + ctx.Db.OneI64.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -219,9 +231,10 @@ public partial struct OneI128 } [SpacetimeDB.Reducer] - public static void insert_one_i128(I128 n) + public static void insert_one_i128(ReducerContext ctx, I128 n) { - new OneI128 { n = n }.Insert(); + var row = new OneI128 { n = n }; + ctx.Db.OneI128.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -231,9 +244,10 @@ public partial struct OneI256 } [SpacetimeDB.Reducer] - public static void insert_one_i256(I256 n) + public static void insert_one_i256(ReducerContext ctx, I256 n) { - new OneI256 { n = n }.Insert(); + var row = new OneI256 { n = n }; + ctx.Db.OneI256.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -243,9 +257,10 @@ public partial struct OneBool } [SpacetimeDB.Reducer] - public static void insert_one_bool(bool b) + public static void insert_one_bool(ReducerContext ctx, bool b) { - new OneBool { b = b }.Insert(); + var row = new OneBool { b = b }; + ctx.Db.OneBool.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -255,9 +270,10 @@ public partial struct OneF32 } [SpacetimeDB.Reducer] - public static void insert_one_f32(float f) + public static void insert_one_f32(ReducerContext ctx, float f) { - new OneF32 { f = f }.Insert(); + var row = new OneF32 { f = f }; + ctx.Db.OneF32.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -267,9 +283,10 @@ public partial struct OneF64 } [SpacetimeDB.Reducer] - public static void insert_one_f64(double f) + public static void insert_one_f64(ReducerContext ctx, double f) { - new OneF64 { f = f }.Insert(); + var row = new OneF64 { f = f }; + ctx.Db.OneF64.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -279,9 +296,10 @@ public partial struct OneString } [SpacetimeDB.Reducer] - public static void insert_one_string(string s) + public static void insert_one_string(ReducerContext ctx, string s) { - new OneString { s = s }.Insert(); + var row = new OneString { s = s }; + ctx.Db.OneString.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -291,9 +309,10 @@ public partial struct OneIdentity } [SpacetimeDB.Reducer] - public static void insert_one_identity(Identity i) + public static void insert_one_identity(ReducerContext ctx, Identity i) { - new OneIdentity { i = i }.Insert(); + var row = new OneIdentity { i = i }; + ctx.Db.OneIdentity.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -303,9 +322,10 @@ public partial struct OneAddress } [SpacetimeDB.Reducer] - public static void insert_one_address(Address a) + public static void insert_one_address(ReducerContext ctx, Address a) { - new OneAddress { a = a }.Insert(); + var row = new OneAddress { a = a }; + ctx.Db.OneAddress.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -315,9 +335,10 @@ public partial struct OneSimpleEnum } [SpacetimeDB.Reducer] - public static void insert_one_simple_enum(SimpleEnum e) + public static void insert_one_simple_enum(ReducerContext ctx, SimpleEnum e) { - new OneSimpleEnum { e = e }.Insert(); + var row = new OneSimpleEnum { e = e }; + ctx.Db.OneSimpleEnum.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -327,9 +348,10 @@ public partial struct OneEnumWithPayload } [SpacetimeDB.Reducer] - public static void insert_one_enum_with_payload(EnumWithPayload e) + public static void insert_one_enum_with_payload(ReducerContext ctx, EnumWithPayload e) { - new OneEnumWithPayload { e = e }.Insert(); + var row = new OneEnumWithPayload { e = e }; + ctx.Db.OneEnumWithPayload.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -339,9 +361,10 @@ public partial struct OneUnitStruct } [SpacetimeDB.Reducer] - public static void insert_one_unit_struct(UnitStruct s) + public static void insert_one_unit_struct(ReducerContext ctx, UnitStruct s) { - new OneUnitStruct { s = s }.Insert(); + var row = new OneUnitStruct { s = s }; + ctx.Db.OneUnitStruct.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -351,9 +374,10 @@ public partial struct OneByteStruct } [SpacetimeDB.Reducer] - public static void insert_one_byte_struct(ByteStruct s) + public static void insert_one_byte_struct(ReducerContext ctx, ByteStruct s) { - new OneByteStruct { s = s }.Insert(); + var row = new OneByteStruct { s = s }; + ctx.Db.OneByteStruct.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -363,9 +387,10 @@ public partial struct OneEveryPrimitiveStruct } [SpacetimeDB.Reducer] - public static void insert_one_every_primitive_struct(EveryPrimitiveStruct s) + public static void insert_one_every_primitive_struct(ReducerContext ctx, EveryPrimitiveStruct s) { - new OneEveryPrimitiveStruct { s = s }.Insert(); + var row = new OneEveryPrimitiveStruct { s = s }; + ctx.Db.OneEveryPrimitiveStruct.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -375,9 +400,10 @@ public partial struct OneEveryVecStruct } [SpacetimeDB.Reducer] - public static void insert_one_every_vec_struct(EveryVecStruct s) + public static void insert_one_every_vec_struct(ReducerContext ctx, EveryVecStruct s) { - new OneEveryVecStruct { s = s }.Insert(); + var row = new OneEveryVecStruct { s = s }; + ctx.Db.OneEveryVecStruct.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -387,9 +413,10 @@ public partial struct VecU8 } [SpacetimeDB.Reducer] - public static void insert_vec_u8(List n) + public static void insert_vec_u8(ReducerContext ctx, List n) { - new VecU8 { n = n }.Insert(); + var row = new VecU8 { n = n }; + ctx.Db.VecU8.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -399,9 +426,10 @@ public partial struct VecU16 } [SpacetimeDB.Reducer] - public static void insert_vec_u16(List n) + public static void insert_vec_u16(ReducerContext ctx, List n) { - new VecU16 { n = n }.Insert(); + var row = new VecU16 { n = n }; + ctx.Db.VecU16.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -411,9 +439,10 @@ public partial struct VecU32 } [SpacetimeDB.Reducer] - public static void insert_vec_u32(List n) + public static void insert_vec_u32(ReducerContext ctx, List n) { - new VecU32 { n = n }.Insert(); + var row = new VecU32 { n = n }; + ctx.Db.VecU32.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -423,9 +452,10 @@ public partial struct VecU64 } [SpacetimeDB.Reducer] - public static void insert_vec_u64(List n) + public static void insert_vec_u64(ReducerContext ctx, List n) { - new VecU64 { n = n }.Insert(); + var row = new VecU64 { n = n }; + ctx.Db.VecU64.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -435,9 +465,10 @@ public partial struct VecU128 } [SpacetimeDB.Reducer] - public static void insert_vec_u128(List n) + public static void insert_vec_u128(ReducerContext ctx, List n) { - new VecU128 { n = n }.Insert(); + var row = new VecU128 { n = n }; + ctx.Db.VecU128.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -447,9 +478,10 @@ public partial struct VecU256 } [SpacetimeDB.Reducer] - public static void insert_vec_u256(List n) + public static void insert_vec_u256(ReducerContext ctx, List n) { - new VecU256 { n = n }.Insert(); + var row = new VecU256 { n = n }; + ctx.Db.VecU256.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -459,9 +491,10 @@ public partial struct VecI8 } [SpacetimeDB.Reducer] - public static void insert_vec_i8(List n) + public static void insert_vec_i8(ReducerContext ctx, List n) { - new VecI8 { n = n }.Insert(); + var row = new VecI8 { n = n }; + ctx.Db.VecI8.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -471,9 +504,10 @@ public partial struct VecI16 } [SpacetimeDB.Reducer] - public static void insert_vec_i16(List n) + public static void insert_vec_i16(ReducerContext ctx, List n) { - new VecI16 { n = n }.Insert(); + var row = new VecI16 { n = n }; + ctx.Db.VecI16.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -483,9 +517,10 @@ public partial struct VecI32 } [SpacetimeDB.Reducer] - public static void insert_vec_i32(List n) + public static void insert_vec_i32(ReducerContext ctx, List n) { - new VecI32 { n = n }.Insert(); + var row = new VecI32 { n = n }; + ctx.Db.VecI32.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -495,9 +530,10 @@ public partial struct VecI64 } [SpacetimeDB.Reducer] - public static void insert_vec_i64(List n) + public static void insert_vec_i64(ReducerContext ctx, List n) { - new VecI64 { n = n }.Insert(); + var row = new VecI64 { n = n }; + ctx.Db.VecI64.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -507,9 +543,10 @@ public partial struct VecI128 } [SpacetimeDB.Reducer] - public static void insert_vec_i128(List n) + public static void insert_vec_i128(ReducerContext ctx, List n) { - new VecI128 { n = n }.Insert(); + var row = new VecI128 { n = n }; + ctx.Db.VecI128.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -519,9 +556,10 @@ public partial struct VecI256 } [SpacetimeDB.Reducer] - public static void insert_vec_i256(List n) + public static void insert_vec_i256(ReducerContext ctx, List n) { - new VecI256 { n = n }.Insert(); + var row = new VecI256 { n = n }; + ctx.Db.VecI256.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -531,9 +569,10 @@ public partial struct VecBool } [SpacetimeDB.Reducer] - public static void insert_vec_bool(List b) + public static void insert_vec_bool(ReducerContext ctx, List b) { - new VecBool { b = b }.Insert(); + var row = new VecBool { b = b }; + ctx.Db.VecBool.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -543,9 +582,10 @@ public partial struct VecF32 } [SpacetimeDB.Reducer] - public static void insert_vec_f32(List f) + public static void insert_vec_f32(ReducerContext ctx, List f) { - new VecF32 { f = f }.Insert(); + var row = new VecF32 { f = f }; + ctx.Db.VecF32.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -555,9 +595,10 @@ public partial struct VecF64 } [SpacetimeDB.Reducer] - public static void insert_vec_f64(List f) + public static void insert_vec_f64(ReducerContext ctx, List f) { - new VecF64 { f = f }.Insert(); + var row = new VecF64 { f = f }; + ctx.Db.VecF64.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -567,9 +608,10 @@ public partial struct VecString } [SpacetimeDB.Reducer] - public static void insert_vec_string(List s) + public static void insert_vec_string(ReducerContext ctx, List s) { - new VecString { s = s }.Insert(); + var row = new VecString { s = s }; + ctx.Db.VecString.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -579,9 +621,10 @@ public partial struct VecIdentity } [SpacetimeDB.Reducer] - public static void insert_vec_identity(List i) + public static void insert_vec_identity(ReducerContext ctx, List i) { - new VecIdentity { i = i }.Insert(); + var row = new VecIdentity { i = i }; + ctx.Db.VecIdentity.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -591,9 +634,10 @@ public partial struct VecAddress } [SpacetimeDB.Reducer] - public static void insert_vec_address(List
a) + public static void insert_vec_address(ReducerContext ctx, List
a) { - new VecAddress { a = a }.Insert(); + var row = new VecAddress { a = a }; + ctx.Db.VecAddress.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -603,9 +647,10 @@ public partial struct VecSimpleEnum } [SpacetimeDB.Reducer] - public static void insert_vec_simple_enum(List e) + public static void insert_vec_simple_enum(ReducerContext ctx, List e) { - new VecSimpleEnum { e = e }.Insert(); + var row = new VecSimpleEnum { e = e }; + ctx.Db.VecSimpleEnum.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -615,9 +660,10 @@ public partial struct VecEnumWithPayload } [SpacetimeDB.Reducer] - public static void insert_vec_enum_with_payload(List e) + public static void insert_vec_enum_with_payload(ReducerContext ctx, List e) { - new VecEnumWithPayload { e = e }.Insert(); + var row = new VecEnumWithPayload { e = e }; + ctx.Db.VecEnumWithPayload.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -627,9 +673,10 @@ public partial struct VecUnitStruct } [SpacetimeDB.Reducer] - public static void insert_vec_unit_struct(List s) + public static void insert_vec_unit_struct(ReducerContext ctx, List s) { - new VecUnitStruct { s = s }.Insert(); + var row = new VecUnitStruct { s = s }; + ctx.Db.VecUnitStruct.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -639,9 +686,10 @@ public partial struct VecByteStruct } [SpacetimeDB.Reducer] - public static void insert_vec_byte_struct(List s) + public static void insert_vec_byte_struct(ReducerContext ctx, List s) { - new VecByteStruct { s = s }.Insert(); + var row = new VecByteStruct { s = s }; + ctx.Db.VecByteStruct.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -651,9 +699,10 @@ public partial struct VecEveryPrimitiveStruct } [SpacetimeDB.Reducer] - public static void insert_vec_every_primitive_struct(List s) + public static void insert_vec_every_primitive_struct(ReducerContext ctx, List s) { - new VecEveryPrimitiveStruct { s = s }.Insert(); + var row = new VecEveryPrimitiveStruct { s = s }; + ctx.Db.VecEveryPrimitiveStruct.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -663,9 +712,10 @@ public partial struct VecEveryVecStruct } [SpacetimeDB.Reducer] - public static void insert_vec_every_vec_struct(List s) + public static void insert_vec_every_vec_struct(ReducerContext ctx, List s) { - new VecEveryVecStruct { s = s }.Insert(); + var row = new VecEveryVecStruct { s = s }; + ctx.Db.VecEveryVecStruct.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -675,9 +725,10 @@ public partial struct OptionI32 } [SpacetimeDB.Reducer] - public static void insert_option_i32(int? n) + public static void insert_option_i32(ReducerContext ctx, int? n) { - new OptionI32 { n = n }.Insert(); + var row = new OptionI32 { n = n }; + ctx.Db.OptionI32.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -687,9 +738,10 @@ public partial struct OptionString } [SpacetimeDB.Reducer] - public static void insert_option_string(string? s) + public static void insert_option_string(ReducerContext ctx, string? s) { - new OptionString { s = s }.Insert(); + var row = new OptionString { s = s }; + ctx.Db.OptionString.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -699,9 +751,10 @@ public partial struct OptionIdentity } [SpacetimeDB.Reducer] - public static void insert_option_identity(Identity? i) + public static void insert_option_identity(ReducerContext ctx, Identity? i) { - new OptionIdentity { i = i }.Insert(); + var row = new OptionIdentity { i = i }; + ctx.Db.OptionIdentity.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -711,9 +764,10 @@ public partial struct OptionSimpleEnum } [SpacetimeDB.Reducer] - public static void insert_option_simple_enum(SimpleEnum? e) + public static void insert_option_simple_enum(ReducerContext ctx, SimpleEnum? e) { - new OptionSimpleEnum { e = e }.Insert(); + var row = new OptionSimpleEnum { e = e }; + ctx.Db.OptionSimpleEnum.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -723,9 +777,10 @@ public partial struct OptionEveryPrimitiveStruct } [SpacetimeDB.Reducer] - public static void insert_option_every_primitive_struct(EveryPrimitiveStruct? s) + public static void insert_option_every_primitive_struct(ReducerContext ctx, EveryPrimitiveStruct? s) { - new OptionEveryPrimitiveStruct { s = s }.Insert(); + var row = new OptionEveryPrimitiveStruct { s = s }; + ctx.Db.OptionEveryPrimitiveStruct.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -735,903 +790,973 @@ public partial struct OptionVecOptionI32 } [SpacetimeDB.Reducer] - public static void insert_option_vec_option_i32(List? v) + public static void insert_option_vec_option_i32(ReducerContext ctx, List? v) { - new OptionVecOptionI32 { v = v }.Insert(); + var row = new OptionVecOptionI32 { v = v }; + ctx.Db.OptionVecOptionI32.Insert(ref row); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueU8 { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public byte n; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_u8(byte n, int data) + public static void insert_unique_u8(ReducerContext ctx, byte n, int data) { - new UniqueU8 { n = n, data = data }.Insert(); + var row = new UniqueU8 { n = n, data = data }; + ctx.Db.UniqueU8.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_u8(byte n, int data) + public static void update_unique_u8(ReducerContext ctx, byte n, int data) { var key = n; - UniqueU8.UpdateByn(key, new UniqueU8 { n = n, data = data }); + var row = new UniqueU8 { n = n, data = data }; + ctx.Db.UniqueU8.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_u8(byte n) + public static void delete_unique_u8(ReducerContext ctx, byte n) { - UniqueU8.DeleteByn(n); + ctx.Db.UniqueU8.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueU16 { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public ushort n; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_u16(ushort n, int data) + public static void insert_unique_u16(ReducerContext ctx, ushort n, int data) { - new UniqueU16 { n = n, data = data }.Insert(); + var row = new UniqueU16 { n = n, data = data }; + ctx.Db.UniqueU16.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_u16(ushort n, int data) + public static void update_unique_u16(ReducerContext ctx, ushort n, int data) { var key = n; - UniqueU16.UpdateByn(key, new UniqueU16 { n = n, data = data }); + var row = new UniqueU16 { n = n, data = data }; + ctx.Db.UniqueU16.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_u16(ushort n) + public static void delete_unique_u16(ReducerContext ctx, ushort n) { - UniqueU16.DeleteByn(n); + ctx.Db.UniqueU16.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueU32 { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public uint n; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_u32(uint n, int data) + public static void insert_unique_u32(ReducerContext ctx, uint n, int data) { - new UniqueU32 { n = n, data = data }.Insert(); + var row = new UniqueU32 { n = n, data = data }; + ctx.Db.UniqueU32.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_u32(uint n, int data) + public static void update_unique_u32(ReducerContext ctx, uint n, int data) { var key = n; - UniqueU32.UpdateByn(key, new UniqueU32 { n = n, data = data }); + var row = new UniqueU32 { n = n, data = data }; + ctx.Db.UniqueU32.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_u32(uint n) + public static void delete_unique_u32(ReducerContext ctx, uint n) { - UniqueU32.DeleteByn(n); + ctx.Db.UniqueU32.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueU64 { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public ulong n; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_u64(ulong n, int data) + public static void insert_unique_u64(ReducerContext ctx, ulong n, int data) { - new UniqueU64 { n = n, data = data }.Insert(); + var row = new UniqueU64 { n = n, data = data }; + ctx.Db.UniqueU64.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_u64(ulong n, int data) + public static void update_unique_u64(ReducerContext ctx, ulong n, int data) { var key = n; - UniqueU64.UpdateByn(key, new UniqueU64 { n = n, data = data }); + var row = new UniqueU64 { n = n, data = data }; + ctx.Db.UniqueU64.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_u64(ulong n) + public static void delete_unique_u64(ReducerContext ctx, ulong n) { - UniqueU64.DeleteByn(n); + ctx.Db.UniqueU64.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueU128 { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public U128 n; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_u128(U128 n, int data) + public static void insert_unique_u128(ReducerContext ctx, U128 n, int data) { - new UniqueU128 { n = n, data = data }.Insert(); + var row = new UniqueU128 { n = n, data = data }; + ctx.Db.UniqueU128.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_u128(U128 n, int data) + public static void update_unique_u128(ReducerContext ctx, U128 n, int data) { var key = n; - UniqueU128.UpdateByn(key, new UniqueU128 { n = n, data = data }); + var row = new UniqueU128 { n = n, data = data }; + ctx.Db.UniqueU128.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_u128(U128 n) + public static void delete_unique_u128(ReducerContext ctx, U128 n) { - UniqueU128.DeleteByn(n); + ctx.Db.UniqueU128.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueU256 { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public U256 n; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_u256(U256 n, int data) + public static void insert_unique_u256(ReducerContext ctx, U256 n, int data) { - new UniqueU256 { n = n, data = data }.Insert(); + var row = new UniqueU256 { n = n, data = data }; + ctx.Db.UniqueU256.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_u256(U256 n, int data) + public static void update_unique_u256(ReducerContext ctx, U256 n, int data) { var key = n; - UniqueU256.UpdateByn(key, new UniqueU256 { n = n, data = data }); + var row = new UniqueU256 { n = n, data = data }; + ctx.Db.UniqueU256.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_u256(U256 n) + public static void delete_unique_u256(ReducerContext ctx, U256 n) { - UniqueU256.DeleteByn(n); + ctx.Db.UniqueU256.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueI8 { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public sbyte n; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_i8(sbyte n, int data) + public static void insert_unique_i8(ReducerContext ctx, sbyte n, int data) { - new UniqueI8 { n = n, data = data }.Insert(); + var row = new UniqueI8 { n = n, data = data }; + ctx.Db.UniqueI8.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_i8(sbyte n, int data) + public static void update_unique_i8(ReducerContext ctx, sbyte n, int data) { var key = n; - UniqueI8.UpdateByn(key, new UniqueI8 { n = n, data = data }); + var row = new UniqueI8 { n = n, data = data }; + ctx.Db.UniqueI8.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_i8(sbyte n) + public static void delete_unique_i8(ReducerContext ctx, sbyte n) { - UniqueI8.DeleteByn(n); + ctx.Db.UniqueI8.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueI16 { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public short n; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_i16(short n, int data) + public static void insert_unique_i16(ReducerContext ctx, short n, int data) { - new UniqueI16 { n = n, data = data }.Insert(); + var row = new UniqueI16 { n = n, data = data }; + ctx.Db.UniqueI16.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_i16(short n, int data) + public static void update_unique_i16(ReducerContext ctx, short n, int data) { var key = n; - UniqueI16.UpdateByn(key, new UniqueI16 { n = n, data = data }); + var row = new UniqueI16 { n = n, data = data }; + ctx.Db.UniqueI16.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_i16(short n) + public static void delete_unique_i16(ReducerContext ctx, short n) { - UniqueI16.DeleteByn(n); + ctx.Db.UniqueI16.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueI32 { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public int n; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_i32(int n, int data) + public static void insert_unique_i32(ReducerContext ctx, int n, int data) { - new UniqueI32 { n = n, data = data }.Insert(); + var row = new UniqueI32 { n = n, data = data }; + ctx.Db.UniqueI32.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_i32(int n, int data) + public static void update_unique_i32(ReducerContext ctx, int n, int data) { var key = n; - UniqueI32.UpdateByn(key, new UniqueI32 { n = n, data = data }); + var row = new UniqueI32 { n = n, data = data }; + ctx.Db.UniqueI32.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_i32(int n) + public static void delete_unique_i32(ReducerContext ctx, int n) { - UniqueI32.DeleteByn(n); + ctx.Db.UniqueI32.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueI64 { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public long n; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_i64(long n, int data) + public static void insert_unique_i64(ReducerContext ctx, long n, int data) { - new UniqueI64 { n = n, data = data }.Insert(); + var row = new UniqueI64 { n = n, data = data }; + ctx.Db.UniqueI64.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_i64(long n, int data) + public static void update_unique_i64(ReducerContext ctx, long n, int data) { var key = n; - UniqueI64.UpdateByn(key, new UniqueI64 { n = n, data = data }); + var row = new UniqueI64 { n = n, data = data }; + ctx.Db.UniqueI64.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_i64(long n) + public static void delete_unique_i64(ReducerContext ctx, long n) { - UniqueI64.DeleteByn(n); + ctx.Db.UniqueI64.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueI128 { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public I128 n; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_i128(I128 n, int data) + public static void insert_unique_i128(ReducerContext ctx, I128 n, int data) { - new UniqueI128 { n = n, data = data }.Insert(); + var row = new UniqueI128 { n = n, data = data }; + ctx.Db.UniqueI128.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_i128(I128 n, int data) + public static void update_unique_i128(ReducerContext ctx, I128 n, int data) { var key = n; - UniqueI128.UpdateByn(key, new UniqueI128 { n = n, data = data }); + var row = new UniqueI128 { n = n, data = data }; + ctx.Db.UniqueI128.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_i128(I128 n) + public static void delete_unique_i128(ReducerContext ctx, I128 n) { - UniqueI128.DeleteByn(n); + ctx.Db.UniqueI128.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueI256 { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public I256 n; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_i256(I256 n, int data) + public static void insert_unique_i256(ReducerContext ctx, I256 n, int data) { - new UniqueI256 { n = n, data = data }.Insert(); + var row = new UniqueI256 { n = n, data = data }; + ctx.Db.UniqueI256.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_i256(I256 n, int data) + public static void update_unique_i256(ReducerContext ctx, I256 n, int data) { var key = n; - UniqueI256.UpdateByn(key, new UniqueI256 { n = n, data = data }); + var row = new UniqueI256 { n = n, data = data }; + ctx.Db.UniqueI256.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_i256(I256 n) + public static void delete_unique_i256(ReducerContext ctx, I256 n) { - UniqueI256.DeleteByn(n); + ctx.Db.UniqueI256.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueBool { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public bool b; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_bool(bool b, int data) + public static void insert_unique_bool(ReducerContext ctx, bool b, int data) { - new UniqueBool { b = b, data = data }.Insert(); + var row = new UniqueBool { b = b, data = data }; + ctx.Db.UniqueBool.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_bool(bool b, int data) + public static void update_unique_bool(ReducerContext ctx, bool b, int data) { var key = b; - UniqueBool.UpdateByb(key, new UniqueBool { b = b, data = data }); + var row = new UniqueBool { b = b, data = data }; + ctx.Db.UniqueBool.UpdateByb(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_bool(bool b) + public static void delete_unique_bool(ReducerContext ctx, bool b) { - UniqueBool.DeleteByb(b); + ctx.Db.UniqueBool.DeleteByb(b); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueString { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public string s; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_string(string s, int data) + public static void insert_unique_string(ReducerContext ctx, string s, int data) { - new UniqueString { s = s, data = data }.Insert(); + var row = new UniqueString { s = s, data = data }; + ctx.Db.UniqueString.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_string(string s, int data) + public static void update_unique_string(ReducerContext ctx, string s, int data) { var key = s; - UniqueString.UpdateBys(key, new UniqueString { s = s, data = data }); + var row = new UniqueString { s = s, data = data }; + ctx.Db.UniqueString.UpdateBys(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_string(string s) + public static void delete_unique_string(ReducerContext ctx, string s) { - UniqueString.DeleteBys(s); + ctx.Db.UniqueString.DeleteBys(s); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueIdentity { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public Identity i; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_identity(Identity i, int data) + public static void insert_unique_identity(ReducerContext ctx, Identity i, int data) { - new UniqueIdentity { i = i, data = data }.Insert(); + var row = new UniqueIdentity { i = i, data = data }; + ctx.Db.UniqueIdentity.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_identity(Identity i, int data) + public static void update_unique_identity(ReducerContext ctx, Identity i, int data) { var key = i; - UniqueIdentity.UpdateByi(key, new UniqueIdentity { i = i, data = data }); + var row = new UniqueIdentity { i = i, data = data }; + ctx.Db.UniqueIdentity.UpdateByi(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_identity(Identity i) + public static void delete_unique_identity(ReducerContext ctx, Identity i) { - UniqueIdentity.DeleteByi(i); + ctx.Db.UniqueIdentity.DeleteByi(i); } [SpacetimeDB.Table(Public = true)] public partial struct UniqueAddress { - [SpacetimeDB.Column(ColumnAttrs.Unique)] + [SpacetimeDB.Unique] public Address a; public int data; } [SpacetimeDB.Reducer] - public static void insert_unique_address(Address a, int data) + public static void insert_unique_address(ReducerContext ctx, Address a, int data) { - new UniqueAddress { a = a, data = data }.Insert(); + var row = new UniqueAddress { a = a, data = data }; + ctx.Db.UniqueAddress.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_unique_address(Address a, int data) + public static void update_unique_address(ReducerContext ctx, Address a, int data) { var key = a; - UniqueAddress.UpdateBya(key, new UniqueAddress { a = a, data = data }); + var row = new UniqueAddress { a = a, data = data }; + ctx.Db.UniqueAddress.UpdateBya(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_unique_address(Address a) + public static void delete_unique_address(ReducerContext ctx, Address a) { - UniqueAddress.DeleteBya(a); + ctx.Db.UniqueAddress.DeleteBya(a); } [SpacetimeDB.Table(Public = true)] public partial struct PkU8 { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public byte n; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_u8(byte n, int data) + public static void insert_pk_u8(ReducerContext ctx, byte n, int data) { - new PkU8 { n = n, data = data }.Insert(); + var row = new PkU8 { n = n, data = data }; + ctx.Db.PkU8.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_u8(byte n, int data) + public static void update_pk_u8(ReducerContext ctx, byte n, int data) { var key = n; - PkU8.UpdateByn(key, new PkU8 { n = n, data = data }); + var row = new PkU8 { n = n, data = data }; + ctx.Db.PkU8.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_u8(byte n) + public static void delete_pk_u8(ReducerContext ctx, byte n) { - PkU8.DeleteByn(n); + ctx.Db.PkU8.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct PkU16 { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public ushort n; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_u16(ushort n, int data) + public static void insert_pk_u16(ReducerContext ctx, ushort n, int data) { - new PkU16 { n = n, data = data }.Insert(); + var row = new PkU16 { n = n, data = data }; + ctx.Db.PkU16.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_u16(ushort n, int data) + public static void update_pk_u16(ReducerContext ctx, ushort n, int data) { var key = n; - PkU16.UpdateByn(key, new PkU16 { n = n, data = data }); + var row = new PkU16 { n = n, data = data }; + ctx.Db.PkU16.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_u16(ushort n) + public static void delete_pk_u16(ReducerContext ctx, ushort n) { - PkU16.DeleteByn(n); + ctx.Db.PkU16.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct PkU32 { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public uint n; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_u32(uint n, int data) + public static void insert_pk_u32(ReducerContext ctx, uint n, int data) { - new PkU32 { n = n, data = data }.Insert(); + var row = new PkU32 { n = n, data = data }; + ctx.Db.PkU32.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_u32(uint n, int data) + public static void update_pk_u32(ReducerContext ctx, uint n, int data) { var key = n; - PkU32.UpdateByn(key, new PkU32 { n = n, data = data }); + var row = new PkU32 { n = n, data = data }; + ctx.Db.PkU32.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_u32(uint n) + public static void delete_pk_u32(ReducerContext ctx, uint n) { - PkU32.DeleteByn(n); + ctx.Db.PkU32.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct PkU64 { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public ulong n; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_u64(ulong n, int data) + public static void insert_pk_u64(ReducerContext ctx, ulong n, int data) { - new PkU64 { n = n, data = data }.Insert(); + var row = new PkU64 { n = n, data = data }; + ctx.Db.PkU64.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_u64(ulong n, int data) + public static void update_pk_u64(ReducerContext ctx, ulong n, int data) { var key = n; - PkU64.UpdateByn(key, new PkU64 { n = n, data = data }); + var row = new PkU64 { n = n, data = data }; + ctx.Db.PkU64.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_u64(ulong n) + public static void delete_pk_u64(ReducerContext ctx, ulong n) { - PkU64.DeleteByn(n); + ctx.Db.PkU64.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct PkU128 { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public U128 n; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_u128(U128 n, int data) + public static void insert_pk_u128(ReducerContext ctx, U128 n, int data) { - new PkU128 { n = n, data = data }.Insert(); + var row = new PkU128 { n = n, data = data }; + ctx.Db.PkU128.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_u128(U128 n, int data) + public static void update_pk_u128(ReducerContext ctx, U128 n, int data) { var key = n; - PkU128.UpdateByn(key, new PkU128 { n = n, data = data }); + var row = new PkU128 { n = n, data = data }; + ctx.Db.PkU128.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_u128(U128 n) + public static void delete_pk_u128(ReducerContext ctx, U128 n) { - PkU128.DeleteByn(n); + ctx.Db.PkU128.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct PkU256 { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public U256 n; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_u256(U256 n, int data) + public static void insert_pk_u256(ReducerContext ctx, U256 n, int data) { - new PkU256 { n = n, data = data }.Insert(); + var row = new PkU256 { n = n, data = data }; + ctx.Db.PkU256.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_u256(U256 n, int data) + public static void update_pk_u256(ReducerContext ctx, U256 n, int data) { var key = n; - PkU256.UpdateByn(key, new PkU256 { n = n, data = data }); + var row = new PkU256 { n = n, data = data }; + ctx.Db.PkU256.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_u256(U256 n) + public static void delete_pk_u256(ReducerContext ctx, U256 n) { - PkU256.DeleteByn(n); + ctx.Db.PkU256.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct PkI8 { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public sbyte n; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_i8(sbyte n, int data) + public static void insert_pk_i8(ReducerContext ctx, sbyte n, int data) { - new PkI8 { n = n, data = data }.Insert(); + var row = new PkI8 { n = n, data = data }; + ctx.Db.PkI8.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_i8(sbyte n, int data) + public static void update_pk_i8(ReducerContext ctx, sbyte n, int data) { var key = n; - PkI8.UpdateByn(key, new PkI8 { n = n, data = data }); + var row = new PkI8 { n = n, data = data }; + ctx.Db.PkI8.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_i8(sbyte n) + public static void delete_pk_i8(ReducerContext ctx, sbyte n) { - PkI8.DeleteByn(n); + ctx.Db.PkI8.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct PkI16 { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public short n; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_i16(short n, int data) + public static void insert_pk_i16(ReducerContext ctx, short n, int data) { - new PkI16 { n = n, data = data }.Insert(); + var row = new PkI16 { n = n, data = data }; + ctx.Db.PkI16.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_i16(short n, int data) + public static void update_pk_i16(ReducerContext ctx, short n, int data) { var key = n; - PkI16.UpdateByn(key, new PkI16 { n = n, data = data }); + var row = new PkI16 { n = n, data = data }; + ctx.Db.PkI16.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_i16(short n) + public static void delete_pk_i16(ReducerContext ctx, short n) { - PkI16.DeleteByn(n); + ctx.Db.PkI16.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct PkI32 { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public int n; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_i32(int n, int data) + public static void insert_pk_i32(ReducerContext ctx, int n, int data) { - new PkI32 { n = n, data = data }.Insert(); + var row = new PkI32 { n = n, data = data }; + ctx.Db.PkI32.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_i32(int n, int data) + public static void update_pk_i32(ReducerContext ctx, int n, int data) { var key = n; - PkI32.UpdateByn(key, new PkI32 { n = n, data = data }); + var row = new PkI32 { n = n, data = data }; + ctx.Db.PkI32.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_i32(int n) + public static void delete_pk_i32(ReducerContext ctx, int n) { - PkI32.DeleteByn(n); + ctx.Db.PkI32.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct PkI64 { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public long n; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_i64(long n, int data) + public static void insert_pk_i64(ReducerContext ctx, long n, int data) { - new PkI64 { n = n, data = data }.Insert(); + var row = new PkI64 { n = n, data = data }; + ctx.Db.PkI64.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_i64(long n, int data) + public static void update_pk_i64(ReducerContext ctx, long n, int data) { var key = n; - PkI64.UpdateByn(key, new PkI64 { n = n, data = data }); + var row = new PkI64 { n = n, data = data }; + ctx.Db.PkI64.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_i64(long n) + public static void delete_pk_i64(ReducerContext ctx, long n) { - PkI64.DeleteByn(n); + ctx.Db.PkI64.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct PkI128 { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public I128 n; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_i128(I128 n, int data) + public static void insert_pk_i128(ReducerContext ctx, I128 n, int data) { - new PkI128 { n = n, data = data }.Insert(); + var row = new PkI128 { n = n, data = data }; + ctx.Db.PkI128.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_i128(I128 n, int data) + public static void update_pk_i128(ReducerContext ctx, I128 n, int data) { var key = n; - PkI128.UpdateByn(key, new PkI128 { n = n, data = data }); + var row = new PkI128 { n = n, data = data }; + ctx.Db.PkI128.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_i128(I128 n) + public static void delete_pk_i128(ReducerContext ctx, I128 n) { - PkI128.DeleteByn(n); + ctx.Db.PkI128.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct PkI256 { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public I256 n; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_i256(I256 n, int data) + public static void insert_pk_i256(ReducerContext ctx, I256 n, int data) { - new PkI256 { n = n, data = data }.Insert(); + var row = new PkI256 { n = n, data = data }; + ctx.Db.PkI256.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_i256(I256 n, int data) + public static void update_pk_i256(ReducerContext ctx, I256 n, int data) { var key = n; - PkI256.UpdateByn(key, new PkI256 { n = n, data = data }); + var row = new PkI256 { n = n, data = data }; + ctx.Db.PkI256.UpdateByn(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_i256(I256 n) + public static void delete_pk_i256(ReducerContext ctx, I256 n) { - PkI256.DeleteByn(n); + ctx.Db.PkI256.DeleteByn(n); } [SpacetimeDB.Table(Public = true)] public partial struct PkBool { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public bool b; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_bool(bool b, int data) + public static void insert_pk_bool(ReducerContext ctx, bool b, int data) { - new PkBool { b = b, data = data }.Insert(); + var row = new PkBool { b = b, data = data }; + ctx.Db.PkBool.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_bool(bool b, int data) + public static void update_pk_bool(ReducerContext ctx, bool b, int data) { var key = b; - PkBool.UpdateByb(key, new PkBool { b = b, data = data }); + var row = new PkBool { b = b, data = data }; + ctx.Db.PkBool.UpdateByb(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_bool(bool b) + public static void delete_pk_bool(ReducerContext ctx, bool b) { - PkBool.DeleteByb(b); + ctx.Db.PkBool.DeleteByb(b); } [SpacetimeDB.Table(Public = true)] public partial struct PkString { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public string s; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_string(string s, int data) + public static void insert_pk_string(ReducerContext ctx, string s, int data) { - new PkString { s = s, data = data }.Insert(); + var row = new PkString { s = s, data = data }; + ctx.Db.PkString.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_string(string s, int data) + public static void update_pk_string(ReducerContext ctx, string s, int data) { var key = s; - PkString.UpdateBys(key, new PkString { s = s, data = data }); + var row = new PkString { s = s, data = data }; + ctx.Db.PkString.UpdateBys(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_string(string s) + public static void delete_pk_string(ReducerContext ctx, string s) { - PkString.DeleteBys(s); + ctx.Db.PkString.DeleteBys(s); } [SpacetimeDB.Table(Public = true)] public partial struct PkIdentity { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public Identity i; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_identity(Identity i, int data) + public static void insert_pk_identity(ReducerContext ctx, Identity i, int data) { - new PkIdentity { i = i, data = data }.Insert(); + var row = new PkIdentity { i = i, data = data }; + ctx.Db.PkIdentity.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_identity(Identity i, int data) + public static void update_pk_identity(ReducerContext ctx, Identity i, int data) { var key = i; - PkIdentity.UpdateByi(key, new PkIdentity { i = i, data = data }); + var row = new PkIdentity { i = i, data = data }; + ctx.Db.PkIdentity.UpdateByi(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_identity(Identity i) + public static void delete_pk_identity(ReducerContext ctx, Identity i) { - PkIdentity.DeleteByi(i); + ctx.Db.PkIdentity.DeleteByi(i); } [SpacetimeDB.Table(Public = true)] public partial struct PkAddress { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKey)] + [SpacetimeDB.PrimaryKey] public Address a; public int data; } [SpacetimeDB.Reducer] - public static void insert_pk_address(Address a, int data) + public static void insert_pk_address(ReducerContext ctx, Address a, int data) { - new PkAddress { a = a, data = data }.Insert(); + var row = new PkAddress { a = a, data = data }; + ctx.Db.PkAddress.Insert(ref row); } [SpacetimeDB.Reducer] - public static void update_pk_address(Address a, int data) + public static void update_pk_address(ReducerContext ctx, Address a, int data) { var key = a; - PkAddress.UpdateBya(key, new PkAddress { a = a, data = data }); + var row = new PkAddress { a = a, data = data }; + ctx.Db.PkAddress.UpdateBya(key, ref row); } [SpacetimeDB.Reducer] - public static void delete_pk_address(Address a) + public static void delete_pk_address(ReducerContext ctx, Address a) { - PkAddress.DeleteBya(a); + ctx.Db.PkAddress.DeleteBya(a); } [SpacetimeDB.Reducer] public static void insert_caller_one_identity(ReducerContext ctx) { - new OneIdentity { i = ctx.Sender }.Insert(); + var row = new OneIdentity { i = ctx.Sender }; + ctx.Db.OneIdentity.Insert(ref row); } [SpacetimeDB.Reducer] public static void insert_caller_vec_identity(ReducerContext ctx) { - new VecIdentity { i = new List { ctx.Sender } }.Insert(); + var row = new VecIdentity { i = new List { ctx.Sender } }; + ctx.Db.VecIdentity.Insert(ref row); } [SpacetimeDB.Reducer] public static void insert_caller_unique_identity(ReducerContext ctx, int data) { - new UniqueIdentity { i = ctx.Sender, data = data }.Insert(); + var row = new UniqueIdentity { i = ctx.Sender, data = data }; + ctx.Db.UniqueIdentity.Insert(ref row); } [SpacetimeDB.Reducer] public static void insert_caller_pk_identity(ReducerContext ctx, int data) { - new PkIdentity { i = ctx.Sender, data = data }.Insert(); + var row = new PkIdentity { i = ctx.Sender, data = data }; + ctx.Db.PkIdentity.Insert(ref row); } [SpacetimeDB.Reducer] public static void insert_caller_one_address(ReducerContext ctx) { - new OneAddress { a = (Address)ctx.Address!, }.Insert(); + var row = new OneAddress { a = (Address)ctx.Address!, }; + ctx.Db.OneAddress.Insert(ref row); } [SpacetimeDB.Reducer] @@ -1648,13 +1773,15 @@ public static void insert_caller_vec_address(ReducerContext ctx) [SpacetimeDB.Reducer] public static void insert_caller_unique_address(ReducerContext ctx, int data) { - new UniqueAddress { a = (Address)ctx.Address!, data = data }.Insert(); + var row = new UniqueAddress { a = (Address)ctx.Address!, data = data }; + ctx.Db.UniqueAddress.Insert(ref row); } [SpacetimeDB.Reducer] public static void insert_caller_pk_address(ReducerContext ctx, int data) { - new PkAddress { a = (Address)ctx.Address!, data = data }.Insert(); + var row = new PkAddress { a = (Address)ctx.Address!, data = data }; + ctx.Db.PkAddress.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -1686,6 +1813,7 @@ public partial struct LargeTable [SpacetimeDB.Reducer] public static void insert_large_table( + ReducerContext ctx, byte a, ushort b, uint c, @@ -1710,8 +1838,7 @@ public static void insert_large_table( EveryVecStruct v ) { - new LargeTable - { + var row = new LargeTable { a = a, b = b, c = c, @@ -1734,19 +1861,20 @@ EveryVecStruct v t = t, u = u, v = v, - }.Insert(); + }; + ctx.Db.LargeTable.Insert(ref row); } [SpacetimeDB.Reducer] - public static void insert_primitives_as_strings(EveryPrimitiveStruct s) + public static void insert_primitives_as_strings(ReducerContext ctx, EveryPrimitiveStruct s) { - new VecString - { + var row = new VecString { s = typeof(EveryPrimitiveStruct) .GetFields() .Select(f => f.GetValue(s)!.ToString()!.ToLowerInvariant()) .ToList() - }.Insert(); + }; + ctx.Db.VecString.Insert(ref row); } [SpacetimeDB.Table(Public = true)] @@ -1757,11 +1885,12 @@ public partial struct TableHoldsTable } [SpacetimeDB.Reducer] - public static void insert_table_holds_table(OneU8 a, VecU8 b) + public static void insert_table_holds_table(ReducerContext ctx, OneU8 a, VecU8 b) { - new TableHoldsTable { a = a, b = b }.Insert(); + var row = new TableHoldsTable { a = a, b = b }; + ctx.Db.TableHoldsTable.Insert(ref row); } [SpacetimeDB.Reducer] - public static void no_op_succeeds() { } + public static void no_op_succeeds(ReducerContext ctx) { } } diff --git a/modules/sdk-test-cs/StdbModule.csproj b/modules/sdk-test-cs/sdk-test-cs.csproj similarity index 89% rename from modules/sdk-test-cs/StdbModule.csproj rename to modules/sdk-test-cs/sdk-test-cs.csproj index a4ec4b0f83..25dc32aea8 100644 --- a/modules/sdk-test-cs/StdbModule.csproj +++ b/modules/sdk-test-cs/sdk-test-cs.csproj @@ -1,6 +1,8 @@ + StdbModule + true net8.0 wasi-wasm enable diff --git a/modules/sdk-test-multi-cs/.gitignore b/modules/sdk-test-multi-cs/.gitignore new file mode 100644 index 0000000000..1746e3269e --- /dev/null +++ b/modules/sdk-test-multi-cs/.gitignore @@ -0,0 +1,2 @@ +bin +obj diff --git a/modules/sdk-test-multi-cs/Lib.cs b/modules/sdk-test-multi-cs/Lib.cs new file mode 100644 index 0000000000..00112c5d27 --- /dev/null +++ b/modules/sdk-test-multi-cs/Lib.cs @@ -0,0 +1,51 @@ +namespace SpacetimeDB.Sdk.Test.Multi; + +using SpacetimeDB; + +[Table(Public = true)] +partial struct User { + [AutoInc] + [PrimaryKey] + public ulong Id; + [Unique] + public Identity Owner; + public string Name; +} + +[Table(Name = "MyTable1", Public = true, Index = "Name")] +[Table(Name = "MyTable2")] +partial struct MyTable { + public string Name; + + [AutoInc] + [PrimaryKey] + public uint Foo; + + [Unique(Table = "MyTable2")] + public uint Bar; +} + +static partial class Module +{ + [Reducer] + public static void AddUser(ReducerContext ctx, string name) { + Runtime.Log($"Hello, {name}"); + + var user = new User() { + Id = ulong.MaxValue, + Owner = ctx.Sender, + Name = name, + }; + ctx.Db.User.Insert(ref user); + } + + [Reducer] + public static void GreetAllUsers(ReducerContext ctx) + { + Runtime.Log("Hello All"); + foreach (var user in ctx.Db.User.Iter()) + { + Runtime.Log($"Hello, {user.Name}!"); + } + } +} \ No newline at end of file diff --git a/modules/sdk-test-multi-cs/README.md b/modules/sdk-test-multi-cs/README.md new file mode 100644 index 0000000000..fff94dde76 --- /dev/null +++ b/modules/sdk-test-multi-cs/README.md @@ -0,0 +1,3 @@ +This C# source code is manually derived from `../sdk-test-connect-disconnect/src/lib.rs` and is supposed to be functionally equivalent. + +Do not add new types or functionality here that is not present in the Rust version, because they're compared against each other. diff --git a/modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj b/modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj new file mode 100644 index 0000000000..dcad219445 --- /dev/null +++ b/modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj @@ -0,0 +1,22 @@ + + + + StdbModule + true + net8.0 + wasi-wasm + enable + enable + + + + + + + + + diff --git a/modules/spacetimedb-quickstart-cs/Lib.cs b/modules/spacetimedb-quickstart-cs/Lib.cs index dabc9ab977..6037e32fba 100644 --- a/modules/spacetimedb-quickstart-cs/Lib.cs +++ b/modules/spacetimedb-quickstart-cs/Lib.cs @@ -1,36 +1,39 @@ +namespace SpacetimeDB.Examples.QuickStart.Server; + using SpacetimeDB; +[Table(Public = true)] +public partial struct Person { + [AutoInc] + [PrimaryKey] + public uint Id; + public string Name; + public byte Age; +} + static partial class Module { - [SpacetimeDB.Table(Public = true)] - public partial struct Person - { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKeyAuto)] - public uint Id; - public string Name; - public byte Age; - } - - [SpacetimeDB.Reducer("add")] - public static void Add(string name, byte age) + [Reducer(Name = "add")] + public static void Add(ReducerContext ctx, string name, byte age) { - new Person { Name = name, Age = age }.Insert(); + var row = new Person { Name = name, Age = age }; + ctx.Db.Person.Insert(ref row); } - [SpacetimeDB.Reducer("say_hello")] - public static void SayHello() + [Reducer(Name = "say_hello")] + public static void SayHello(ReducerContext ctx) { - foreach (var person in Person.Iter()) + foreach (var person in ctx.Db.Person.Iter()) { Log.Info($"Hello, {person.Name}!"); } Log.Info("Hello, World!"); } - [SpacetimeDB.Reducer("list_over_age")] - public static void ListOverAge(byte age) + [Reducer(Name = "list_over_age")] + public static void ListOverAge(ReducerContext ctx, byte age) { - foreach (var person in Person.Query(person => person.Age >= age)) + foreach (var person in ctx.Db.Person.Query(person => person.Age >= age)) { Log.Info($"{person.Name} has age {person.Age} >= {age}"); } diff --git a/modules/spacetimedb-quickstart-cs/StdbModule.csproj b/modules/spacetimedb-quickstart-cs/spacetimedb-quickstart-server-cs.csproj similarity index 83% rename from modules/spacetimedb-quickstart-cs/StdbModule.csproj rename to modules/spacetimedb-quickstart-cs/spacetimedb-quickstart-server-cs.csproj index 7773fe10c0..00ef182a30 100644 --- a/modules/spacetimedb-quickstart-cs/StdbModule.csproj +++ b/modules/spacetimedb-quickstart-cs/spacetimedb-quickstart-server-cs.csproj @@ -1,6 +1,8 @@ - + + StdbModule + true net8.0 wasi-wasm enable From dc4fea4a0a3d3c28f64c1d1014e2f7cc0dbe92d7 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Fri, 20 Sep 2024 10:44:25 -0400 Subject: [PATCH 03/27] Review Feedback --- crates/bindings-csharp/Runtime/Attrs.cs | 4 ++-- .../src/module_bindings/mod.rs | 20 ++++++++++++++++++- modules/sdk-test-connect-disconnect-cs/Lib.cs | 4 ++-- modules/spacetimedb-quickstart-cs/Lib.cs | 6 +++--- 4 files changed, 26 insertions(+), 8 deletions(-) diff --git a/crates/bindings-csharp/Runtime/Attrs.cs b/crates/bindings-csharp/Runtime/Attrs.cs index fa660d50c2..bab2e8b41d 100644 --- a/crates/bindings-csharp/Runtime/Attrs.cs +++ b/crates/bindings-csharp/Runtime/Attrs.cs @@ -66,9 +66,9 @@ public static class ReducerKind } [AttributeUsage(AttributeTargets.Method, Inherited = false)] -public sealed class ReducerAttribute : Attribute +public sealed class ReducerAttribute(string? name = null) : Attribute { - public string? Name; + public string? Name => name; } diff --git a/crates/sdk/tests/connect_disconnect_client/src/module_bindings/mod.rs b/crates/sdk/tests/connect_disconnect_client/src/module_bindings/mod.rs index 4721e2a8f9..94ec48f210 100644 --- a/crates/sdk/tests/connect_disconnect_client/src/module_bindings/mod.rs +++ b/crates/sdk/tests/connect_disconnect_client/src/module_bindings/mod.rs @@ -22,13 +22,20 @@ use std::sync::Arc; pub mod connected; pub mod disconnected; +pub mod on_connect_reducer; +pub mod on_disconnect_reducer; pub use connected::*; pub use disconnected::*; +pub use on_connect_reducer::*; +pub use on_disconnect_reducer::*; #[allow(unused)] #[derive(Serialize, Deserialize, Clone, PartialEq, Debug)] -pub enum ReducerEvent {} +pub enum ReducerEvent { + OnConnect(on_connect_reducer::OnConnectArgs), + OnDisconnect(on_disconnect_reducer::OnDisconnectArgs), +} #[allow(unused)] pub struct Module; @@ -69,6 +76,17 @@ impl SpacetimeModule for Module { let reducer_call = &event.reducer_call; #[allow(clippy::match_single_binding)] match &reducer_call.reducer_name[..] { + "OnConnect" => _reducer_callbacks.handle_event_of_type::( + event, + _state, + ReducerEvent::OnConnect, + ), + "OnDisconnect" => _reducer_callbacks + .handle_event_of_type::( + event, + _state, + ReducerEvent::OnDisconnect, + ), unknown => { spacetimedb_sdk::log::error!("Event on an unknown reducer: {:?}", unknown); None diff --git a/modules/sdk-test-connect-disconnect-cs/Lib.cs b/modules/sdk-test-connect-disconnect-cs/Lib.cs index 9991dd61fc..b5f700a7eb 100644 --- a/modules/sdk-test-connect-disconnect-cs/Lib.cs +++ b/modules/sdk-test-connect-disconnect-cs/Lib.cs @@ -14,14 +14,14 @@ public partial struct Disconnected { static partial class Module { - [SpacetimeDB.Reducer(Name = ReducerKind.Connect)] + [SpacetimeDB.Reducer(ReducerKind.Connect)] public static void OnConnect(ReducerContext ctx) { var row = new Connected { identity = ctx.Sender }; ctx.Db.Connected.Insert(ref row); } - [SpacetimeDB.Reducer(Name = ReducerKind.Disconnect)] + [SpacetimeDB.Reducer(ReducerKind.Disconnect)] public static void OnDisconnect(ReducerContext ctx) { var row = new Disconnected { identity = ctx.Sender }; diff --git a/modules/spacetimedb-quickstart-cs/Lib.cs b/modules/spacetimedb-quickstart-cs/Lib.cs index 6037e32fba..7a23263343 100644 --- a/modules/spacetimedb-quickstart-cs/Lib.cs +++ b/modules/spacetimedb-quickstart-cs/Lib.cs @@ -13,14 +13,14 @@ public partial struct Person { static partial class Module { - [Reducer(Name = "add")] + [Reducer("add")] public static void Add(ReducerContext ctx, string name, byte age) { var row = new Person { Name = name, Age = age }; ctx.Db.Person.Insert(ref row); } - [Reducer(Name = "say_hello")] + [Reducer("say_hello")] public static void SayHello(ReducerContext ctx) { foreach (var person in ctx.Db.Person.Iter()) @@ -30,7 +30,7 @@ public static void SayHello(ReducerContext ctx) Log.Info("Hello, World!"); } - [Reducer(Name = "list_over_age")] + [Reducer("list_over_age")] public static void ListOverAge(ReducerContext ctx, byte age) { foreach (var person in ctx.Db.Person.Query(person => person.Age >= age)) From 2fc3fc94e26f2b615384f3dbd30d3fa10c555a66 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Fri, 20 Sep 2024 14:48:39 -0400 Subject: [PATCH 04/27] Update --- .../Codegen.Tests/fixtures/server/Lib.cs | 23 +- .../server/snapshots/Module#FFI.verified.cs | 349 +++++++++++++++++- .../snapshots/Module#PrivateTable.verified.cs | 45 +-- .../snapshots/Module#PublicTable.verified.cs | 111 +----- ...Module#Timers.SendMessageTimer.verified.cs | 50 +-- crates/bindings-csharp/Codegen/Module.cs | 22 +- crates/bindings-csharp/Runtime/Attrs.cs | 1 + 7 files changed, 393 insertions(+), 208 deletions(-) diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs index 32bbc78912..d066a3ec69 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs @@ -44,7 +44,8 @@ public partial class PrivateTable { } [SpacetimeDB.Table] public partial struct PublicTable { - [SpacetimeDB.Column(ColumnAttrs.PrimaryKeyAuto)] + [SpacetimeDB.AutoInc] + [SpacetimeDB.PrimaryKey] public int Id; public byte ByteField; @@ -81,18 +82,18 @@ public partial struct PublicTable public static partial class Reducers { [SpacetimeDB.Reducer] - public static void InsertData(PublicTable data) + public static void InsertData(ReducerContext ctx, PublicTable data) { - data.Insert(); - Log.Info("New list"); - foreach (var item in PublicTable.Iter()) + ctx.Db.PublicTable.Insert(ref data); + Runtime.Log("New list"); + foreach (var item in ctx.Db.PublicTable.Iter()) { Log.Info($"Item: {item.StringField}"); } } [SpacetimeDB.Reducer] - public static void ScheduleImmediate(PublicTable data) + public static void ScheduleImmediate(ReducerContext ctx, PublicTable data) { VolatileNonatomicScheduleImmediateInsertData(data); } @@ -107,7 +108,7 @@ public static partial class AndClasses [SpacetimeDB.Reducer("test_custom_name_and_reducer_ctx")] public static void InsertData2(ReducerContext ctx, PublicTable data) { - data.Insert(); + ctx.Db.PublicTable.Insert(ref data); } } } @@ -122,7 +123,7 @@ public partial struct SendMessageTimer } [SpacetimeDB.Reducer] - public static void SendScheduledMessage(SendMessageTimer arg) + public static void SendScheduledMessage(ReducerContext ctx, SendMessageTimer arg) { // verify that fields were auto-added ulong id = arg.ScheduledId; @@ -133,10 +134,10 @@ public static void SendScheduledMessage(SendMessageTimer arg) [SpacetimeDB.Reducer(ReducerKind.Init)] public static void Init(ReducerContext ctx) { - new SendMessageTimer - { + var row = new SendMessageTimer { Text = "bot sending a message", ScheduledAt = ctx.Time.AddSeconds(10), - }.Insert(); + }; + ctx.Db.SendMessageTimer.Insert(ref row); } } diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs index 60368e8ec9..d4c1ffb7d7 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs @@ -6,6 +6,330 @@ using System.Runtime.CompilerServices; using System.Runtime.InteropServices; +namespace SpacetimeDB +{ + public sealed class ReducerContext : BaseReducerContext { } + + namespace TableViews + { + public readonly struct PrivateTable + : SpacetimeDB.Internal.ITableView + { + static void SpacetimeDB.Internal.ITableView.ReadGenFields( + System.IO.BinaryReader reader, + ref PrivateTable row + ) { } + + public IEnumerable Iter() => + SpacetimeDB.Internal.ITableView.Iter(); + + public IEnumerable Query( + System.Linq.Expressions.Expression> predicate + ) => SpacetimeDB.Internal.ITableView.Query(predicate); + + public void Insert(ref PrivateTable row) => + SpacetimeDB.Internal.ITableView.Insert(ref row); + } + + public readonly struct PublicTable + : SpacetimeDB.Internal.ITableView + { + static void SpacetimeDB.Internal.ITableView.ReadGenFields( + System.IO.BinaryReader reader, + ref PublicTable row + ) + { + if (row.Id == default) + { + row.Id = PublicTable.BSATN.Id.Read(reader); + } + } + + public IEnumerable Iter() => + SpacetimeDB.Internal.ITableView.Iter(); + + public IEnumerable Query( + System.Linq.Expressions.Expression> predicate + ) => SpacetimeDB.Internal.ITableView.Query(predicate); + + public void Insert(ref PublicTable row) => + SpacetimeDB.Internal.ITableView.Insert(ref row); + + public IEnumerable FilterById(int Id) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 0, + Id, + PublicTable.BSATN.Id + ) + .Iter(); + + public PublicTable? FindById(int Id) => + FilterById(Id).Cast().SingleOrDefault(); + + public bool DeleteById(int Id) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 0, + Id, + PublicTable.BSATN.Id + ) + .Delete(); + + public bool UpdateById(int Id, ref PublicTable @this) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 0, + Id, + PublicTable.BSATN.Id + ) + .Update(ref @this); + + public IEnumerable FilterByByteField(byte ByteField) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 1, + ByteField, + PublicTable.BSATN.ByteField + ) + .Iter(); + + public IEnumerable FilterByUshortField(ushort UshortField) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 2, + UshortField, + PublicTable.BSATN.UshortField + ) + .Iter(); + + public IEnumerable FilterByUintField(uint UintField) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 3, + UintField, + PublicTable.BSATN.UintField + ) + .Iter(); + + public IEnumerable FilterByUlongField(ulong UlongField) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 4, + UlongField, + PublicTable.BSATN.UlongField + ) + .Iter(); + + public IEnumerable FilterByUInt128Field(System.UInt128 UInt128Field) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 5, + UInt128Field, + PublicTable.BSATN.UInt128Field + ) + .Iter(); + + public IEnumerable FilterByU128Field(SpacetimeDB.U128 U128Field) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 6, + U128Field, + PublicTable.BSATN.U128Field + ) + .Iter(); + + public IEnumerable FilterByU256Field(SpacetimeDB.U256 U256Field) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 7, + U256Field, + PublicTable.BSATN.U256Field + ) + .Iter(); + + public IEnumerable FilterBySbyteField(sbyte SbyteField) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 8, + SbyteField, + PublicTable.BSATN.SbyteField + ) + .Iter(); + + public IEnumerable FilterByShortField(short ShortField) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 9, + ShortField, + PublicTable.BSATN.ShortField + ) + .Iter(); + + public IEnumerable FilterByIntField(int IntField) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 10, + IntField, + PublicTable.BSATN.IntField + ) + .Iter(); + + public IEnumerable FilterByLongField(long LongField) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 11, + LongField, + PublicTable.BSATN.LongField + ) + .Iter(); + + public IEnumerable FilterByInt128Field(System.Int128 Int128Field) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 12, + Int128Field, + PublicTable.BSATN.Int128Field + ) + .Iter(); + + public IEnumerable FilterByI128Field(SpacetimeDB.I128 I128Field) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 13, + I128Field, + PublicTable.BSATN.I128Field + ) + .Iter(); + + public IEnumerable FilterByI256Field(SpacetimeDB.I256 I256Field) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 14, + I256Field, + PublicTable.BSATN.I256Field + ) + .Iter(); + + public IEnumerable FilterByBoolField(bool BoolField) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 15, + BoolField, + PublicTable.BSATN.BoolField + ) + .Iter(); + + public IEnumerable FilterByStringField(string StringField) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 18, + StringField, + PublicTable.BSATN.StringField + ) + .Iter(); + + public IEnumerable FilterByIdentityField( + SpacetimeDB.Identity IdentityField + ) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 19, + IdentityField, + PublicTable.BSATN.IdentityField + ) + .Iter(); + + public IEnumerable FilterByAddressField( + SpacetimeDB.Address AddressField + ) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 20, + AddressField, + PublicTable.BSATN.AddressField + ) + .Iter(); + } + + public readonly struct SendMessageTimer + : SpacetimeDB.Internal.ITableView + { + static void SpacetimeDB.Internal.ITableView< + SendMessageTimer, + Timers.SendMessageTimer + >.ReadGenFields(System.IO.BinaryReader reader, ref Timers.SendMessageTimer row) + { + if (row.ScheduledId == default) + { + row.ScheduledId = Timers.SendMessageTimer.BSATN.ScheduledId.Read(reader); + } + } + + public IEnumerable Iter() => + SpacetimeDB.Internal.ITableView.Iter(); + + public IEnumerable Query( + System.Linq.Expressions.Expression> predicate + ) => + SpacetimeDB.Internal.ITableView.Query( + predicate + ); + + public void Insert(ref Timers.SendMessageTimer row) => + SpacetimeDB.Internal.ITableView.Insert( + ref row + ); + + public IEnumerable FilterByText(string Text) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 0, + Text, + Timers.SendMessageTimer.BSATN.Text + ) + .Iter(); + + public IEnumerable FilterByScheduledId(ulong ScheduledId) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 1, + ScheduledId, + Timers.SendMessageTimer.BSATN.ScheduledId + ) + .Iter(); + + public Timers.SendMessageTimer? FindByScheduledId(ulong ScheduledId) => + FilterByScheduledId(ScheduledId).Cast().SingleOrDefault(); + + public bool DeleteByScheduledId(ulong ScheduledId) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 1, + ScheduledId, + Timers.SendMessageTimer.BSATN.ScheduledId + ) + .Delete(); + + public bool UpdateByScheduledId(ulong ScheduledId, ref Timers.SendMessageTimer @this) => + SpacetimeDB + .Internal.ITableView.ColEq.Where( + 1, + ScheduledId, + Timers.SendMessageTimer.BSATN.ScheduledId + ) + .Update(ref @this); + } + } + + public sealed class Local + { + public TableViews.PrivateTable PrivateTable => new(); + public TableViews.PublicTable PublicTable => new(); + public TableViews.SendMessageTimer SendMessageTimer => new(); + } +} + static class ModuleRegistration { class Init : SpacetimeDB.Internal.IReducer @@ -14,9 +338,9 @@ public SpacetimeDB.Internal.ReducerDef MakeReducerDef( SpacetimeDB.BSATN.ITypeRegistrar registrar ) => new("__init__", []); - public void Invoke(BinaryReader reader, SpacetimeDB.ReducerContext ctx) + public void Invoke(BinaryReader reader, SpacetimeDB.Internal.IReducerContext ctx) { - Timers.Init(ctx); + Timers.Init((SpacetimeDB.ReducerContext)ctx); } } @@ -28,9 +352,9 @@ public SpacetimeDB.Internal.ReducerDef MakeReducerDef( SpacetimeDB.BSATN.ITypeRegistrar registrar ) => new("InsertData", [new(nameof(data), data.GetAlgebraicType(registrar))]); - public void Invoke(BinaryReader reader, SpacetimeDB.ReducerContext ctx) + public void Invoke(BinaryReader reader, SpacetimeDB.Internal.IReducerContext ctx) { - Reducers.InsertData(data.Read(reader)); + Reducers.InsertData((SpacetimeDB.ReducerContext)ctx, data.Read(reader)); } } @@ -46,9 +370,12 @@ SpacetimeDB.BSATN.ITypeRegistrar registrar [new(nameof(data), data.GetAlgebraicType(registrar))] ); - public void Invoke(BinaryReader reader, SpacetimeDB.ReducerContext ctx) + public void Invoke(BinaryReader reader, SpacetimeDB.Internal.IReducerContext ctx) { - Test.NestingNamespaces.AndClasses.InsertData2(ctx, data.Read(reader)); + Test.NestingNamespaces.AndClasses.InsertData2( + (SpacetimeDB.ReducerContext)ctx, + data.Read(reader) + ); } } @@ -60,9 +387,9 @@ public SpacetimeDB.Internal.ReducerDef MakeReducerDef( SpacetimeDB.BSATN.ITypeRegistrar registrar ) => new("ScheduleImmediate", [new(nameof(data), data.GetAlgebraicType(registrar))]); - public void Invoke(BinaryReader reader, SpacetimeDB.ReducerContext ctx) + public void Invoke(BinaryReader reader, SpacetimeDB.Internal.IReducerContext ctx) { - Reducers.ScheduleImmediate(data.Read(reader)); + Reducers.ScheduleImmediate((SpacetimeDB.ReducerContext)ctx, data.Read(reader)); } } @@ -74,9 +401,9 @@ public SpacetimeDB.Internal.ReducerDef MakeReducerDef( SpacetimeDB.BSATN.ITypeRegistrar registrar ) => new("SendScheduledMessage", [new(nameof(arg), arg.GetAlgebraicType(registrar))]); - public void Invoke(BinaryReader reader, SpacetimeDB.ReducerContext ctx) + public void Invoke(BinaryReader reader, SpacetimeDB.Internal.IReducerContext ctx) { - Timers.SendScheduledMessage(arg.Read(reader)); + Timers.SendScheduledMessage((SpacetimeDB.ReducerContext)ctx, arg.Read(reader)); } } @@ -93,6 +420,8 @@ public void Invoke(BinaryReader reader, SpacetimeDB.ReducerContext ctx) #endif public static void Main() { + SpacetimeDB.Internal.Module.Initialize(new SpacetimeDB.ReducerContext()); + SpacetimeDB.Internal.Module.RegisterReducer(); SpacetimeDB.Internal.Module.RegisterReducer(); SpacetimeDB.Internal.Module.RegisterReducer(); diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PrivateTable.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PrivateTable.verified.cs index d3bfe38489..915464b0ef 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PrivateTable.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PrivateTable.verified.cs @@ -26,37 +26,30 @@ SpacetimeDB.BSATN.ITypeRegistrar registrar )); } - void SpacetimeDB.Internal.ITable.ReadGenFields(System.IO.BinaryReader reader) { } - - static SpacetimeDB.Internal.TableDesc SpacetimeDB.Internal.ITable.MakeTableDesc( + static IEnumerable SpacetimeDB.Internal.ITable.MakeTableDesc( SpacetimeDB.BSATN.ITypeRegistrar registrar ) => - new( + [ new( - TableName: nameof(PrivateTable), - Columns: [], - Indexes: [], - Constraints: [], - Sequences: [], - // "system" | "user" - TableType: "user", - // "public" | "private" - TableAccess: "private", - Scheduled: null + new( + TableName: nameof(PrivateTable), + Columns: [], + Indexes: [], + Constraints: [], + Sequences: [], + // "system" | "user" + TableType: "user", + // "public" | "private" + TableAccess: "private", + Scheduled: null + ), + (uint) + ( + (SpacetimeDB.BSATN.AlgebraicType.Ref)new BSATN().GetAlgebraicType(registrar) + ).Ref_ ), - (uint) - ((SpacetimeDB.BSATN.AlgebraicType.Ref)new BSATN().GetAlgebraicType(registrar)).Ref_ - ); + ]; static SpacetimeDB.Internal.Filter SpacetimeDB.Internal.ITable.CreateFilter() => new([]); - - public static IEnumerable Iter() => - SpacetimeDB.Internal.ITable.Iter(); - - public static IEnumerable Query( - System.Linq.Expressions.Expression> predicate - ) => SpacetimeDB.Internal.ITable.Query(predicate); - - public void Insert() => SpacetimeDB.Internal.ITable.Insert(this); } // PrivateTable diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs index 92f7325293..6f494ec99c 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs @@ -188,18 +188,10 @@ SpacetimeDB.BSATN.ITypeRegistrar registrar )); } - void SpacetimeDB.Internal.ITable.ReadGenFields(System.IO.BinaryReader reader) - { - if (Id == default) - { - Id = BSATN.Id.Read(reader); - } - } - - static SpacetimeDB.Internal.TableDesc SpacetimeDB.Internal.ITable.MakeTableDesc( + static IEnumerable SpacetimeDB.Internal.ITable.MakeTableDesc( SpacetimeDB.BSATN.ITypeRegistrar registrar ) => - new( + [ new( TableName: nameof(PublicTable), Columns: @@ -270,9 +262,7 @@ SpacetimeDB.BSATN.ITypeRegistrar registrar TableAccess: "private", Scheduled: null ), - (uint) - ((SpacetimeDB.BSATN.AlgebraicType.Ref)new BSATN().GetAlgebraicType(registrar)).Ref_ - ); + ]; static SpacetimeDB.Internal.Filter SpacetimeDB.Internal.ITable.CreateFilter() => new( @@ -357,99 +347,4 @@ static SpacetimeDB.Internal.Filter SpacetimeDB.Internal.ITable.Crea ) ] ); - - public static IEnumerable Iter() => - SpacetimeDB.Internal.ITable.Iter(); - - public static IEnumerable Query( - System.Linq.Expressions.Expression> predicate - ) => SpacetimeDB.Internal.ITable.Query(predicate); - - public void Insert() => SpacetimeDB.Internal.ITable.Insert(this); - - public static IEnumerable FilterById(int Id) => - SpacetimeDB.Internal.ITable.ColEq.Where(0, Id, BSATN.Id).Iter(); - - public static PublicTable? FindById(int Id) => - FilterById(Id).Cast().SingleOrDefault(); - - public static bool DeleteById(int Id) => - SpacetimeDB.Internal.ITable.ColEq.Where(0, Id, BSATN.Id).Delete(); - - public static bool UpdateById(int Id, PublicTable @this) => - SpacetimeDB.Internal.ITable.ColEq.Where(0, Id, BSATN.Id).Update(@this); - - public static IEnumerable FilterByByteField(byte ByteField) => - SpacetimeDB.Internal.ITable.ColEq.Where(1, ByteField, BSATN.ByteField).Iter(); - - public static IEnumerable FilterByUshortField(ushort UshortField) => - SpacetimeDB - .Internal.ITable.ColEq.Where(2, UshortField, BSATN.UshortField) - .Iter(); - - public static IEnumerable FilterByUintField(uint UintField) => - SpacetimeDB.Internal.ITable.ColEq.Where(3, UintField, BSATN.UintField).Iter(); - - public static IEnumerable FilterByUlongField(ulong UlongField) => - SpacetimeDB - .Internal.ITable.ColEq.Where(4, UlongField, BSATN.UlongField) - .Iter(); - - public static IEnumerable FilterByUInt128Field(System.UInt128 UInt128Field) => - SpacetimeDB - .Internal.ITable.ColEq.Where(5, UInt128Field, BSATN.UInt128Field) - .Iter(); - - public static IEnumerable FilterByU128Field(SpacetimeDB.U128 U128Field) => - SpacetimeDB.Internal.ITable.ColEq.Where(6, U128Field, BSATN.U128Field).Iter(); - - public static IEnumerable FilterByU256Field(SpacetimeDB.U256 U256Field) => - SpacetimeDB.Internal.ITable.ColEq.Where(7, U256Field, BSATN.U256Field).Iter(); - - public static IEnumerable FilterBySbyteField(sbyte SbyteField) => - SpacetimeDB - .Internal.ITable.ColEq.Where(8, SbyteField, BSATN.SbyteField) - .Iter(); - - public static IEnumerable FilterByShortField(short ShortField) => - SpacetimeDB - .Internal.ITable.ColEq.Where(9, ShortField, BSATN.ShortField) - .Iter(); - - public static IEnumerable FilterByIntField(int IntField) => - SpacetimeDB.Internal.ITable.ColEq.Where(10, IntField, BSATN.IntField).Iter(); - - public static IEnumerable FilterByLongField(long LongField) => - SpacetimeDB.Internal.ITable.ColEq.Where(11, LongField, BSATN.LongField).Iter(); - - public static IEnumerable FilterByInt128Field(System.Int128 Int128Field) => - SpacetimeDB - .Internal.ITable.ColEq.Where(12, Int128Field, BSATN.Int128Field) - .Iter(); - - public static IEnumerable FilterByI128Field(SpacetimeDB.I128 I128Field) => - SpacetimeDB.Internal.ITable.ColEq.Where(13, I128Field, BSATN.I128Field).Iter(); - - public static IEnumerable FilterByI256Field(SpacetimeDB.I256 I256Field) => - SpacetimeDB.Internal.ITable.ColEq.Where(14, I256Field, BSATN.I256Field).Iter(); - - public static IEnumerable FilterByBoolField(bool BoolField) => - SpacetimeDB.Internal.ITable.ColEq.Where(15, BoolField, BSATN.BoolField).Iter(); - - public static IEnumerable FilterByStringField(string StringField) => - SpacetimeDB - .Internal.ITable.ColEq.Where(18, StringField, BSATN.StringField) - .Iter(); - - public static IEnumerable FilterByIdentityField( - SpacetimeDB.Identity IdentityField - ) => - SpacetimeDB - .Internal.ITable.ColEq.Where(19, IdentityField, BSATN.IdentityField) - .Iter(); - - public static IEnumerable FilterByAddressField(SpacetimeDB.Address AddressField) => - SpacetimeDB - .Internal.ITable.ColEq.Where(20, AddressField, BSATN.AddressField) - .Iter(); } // PublicTable diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs index 646eca5b2a..ebdfc9d408 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs @@ -53,20 +53,10 @@ SpacetimeDB.BSATN.ITypeRegistrar registrar public ulong ScheduledId; public SpacetimeDB.ScheduleAt ScheduledAt; - void SpacetimeDB.Internal.ITable.ReadGenFields( - System.IO.BinaryReader reader - ) - { - if (ScheduledId == default) - { - ScheduledId = BSATN.ScheduledId.Read(reader); - } - } - - static SpacetimeDB.Internal.TableDesc SpacetimeDB.Internal.ITable.MakeTableDesc( + static IEnumerable SpacetimeDB.Internal.ITable.MakeTableDesc( SpacetimeDB.BSATN.ITypeRegistrar registrar ) => - new( + [ new( TableName: nameof(SendMessageTimer), Columns: @@ -92,11 +82,7 @@ SpacetimeDB.BSATN.ITypeRegistrar registrar TableAccess: "private", Scheduled: nameof(SendScheduledMessage) ), - (uint) - ( - (SpacetimeDB.BSATN.AlgebraicType.Ref)new BSATN().GetAlgebraicType(registrar) - ).Ref_ - ); + ]; static SpacetimeDB.Internal.Filter SpacetimeDB.Internal.ITable.CreateFilter() => new( @@ -109,35 +95,5 @@ static SpacetimeDB.Internal.Filter SpacetimeDB.Internal.ITable ) ] ); - - public static IEnumerable Iter() => - SpacetimeDB.Internal.ITable.Iter(); - - public static IEnumerable Query( - System.Linq.Expressions.Expression> predicate - ) => SpacetimeDB.Internal.ITable.Query(predicate); - - public void Insert() => SpacetimeDB.Internal.ITable.Insert(this); - - public static IEnumerable FilterByText(string Text) => - SpacetimeDB.Internal.ITable.ColEq.Where(0, Text, BSATN.Text).Iter(); - - public static IEnumerable FilterByScheduledId(ulong ScheduledId) => - SpacetimeDB - .Internal.ITable.ColEq.Where(1, ScheduledId, BSATN.ScheduledId) - .Iter(); - - public static SendMessageTimer? FindByScheduledId(ulong ScheduledId) => - FilterByScheduledId(ScheduledId).Cast().SingleOrDefault(); - - public static bool DeleteByScheduledId(ulong ScheduledId) => - SpacetimeDB - .Internal.ITable.ColEq.Where(1, ScheduledId, BSATN.ScheduledId) - .Delete(); - - public static bool UpdateByScheduledId(ulong ScheduledId, SendMessageTimer @this) => - SpacetimeDB - .Internal.ITable.ColEq.Where(1, ScheduledId, BSATN.ScheduledId) - .Update(@this); } // SendMessageTimer } // Timers diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index adaa7b6abf..c0d05f67f0 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -160,14 +160,21 @@ or Accessibility.NotApplicable ), }; - var views = context.Attributes - .Where(a => a.AttributeClass?.ToDisplayString() == "SpacetimeDB.TableAttribute"); + Views = context.Attributes + .Where(a => a.AttributeClass?.ToDisplayString() == "SpacetimeDB.TableAttribute") + .Select(a => new TableView(this, a)) + .ToImmutableArray(); - Views = views.Select(a => new TableView(this, a)).ToImmutableArray(); - Scheduled = Views.FirstOrDefault(t => t.Scheduled != null)?.Scheduled; + var schedules = Views.Where(t => t.Scheduled != null).Select(t => t.Scheduled); + var numSchedules = schedules.Count(); + if (numSchedules > 0) { + var distinctSchedules = schedules.Distinct(); + if (numSchedules != Views.Length || distinctSchedules.Count() != 1) { + throw new Exception("When using multiple [Table] attributes with schedule, all [Table] must have the same schedule."); + } + + Scheduled = distinctSchedules.First(); - if (Scheduled is not null) - { // For scheduled tables, we append extra fields early in the pipeline, // both to the type itself and to the BSATN information, as if they // were part of the original declaration. @@ -344,6 +351,9 @@ public ReducerDeclaration(GeneratorAttributeSyntaxContext context) { throw new Exception($"Reducer {method} must return void"); } + if (method.Parameters.FirstOrDefault()?.Type is not INamedTypeSymbol namedType || namedType.Name != "ReducerContext") { + throw new Exception($"Reducer {method} must have a first argument of type ReducerContext"); + } Name = method.Name; ExportName = attr.Name ?? Name; diff --git a/crates/bindings-csharp/Runtime/Attrs.cs b/crates/bindings-csharp/Runtime/Attrs.cs index bab2e8b41d..ae4f062db0 100644 --- a/crates/bindings-csharp/Runtime/Attrs.cs +++ b/crates/bindings-csharp/Runtime/Attrs.cs @@ -41,6 +41,7 @@ public sealed class TableAttribute : Attribute /// public bool Public = false; + public string? Scheduled { get; init; } } [AttributeUsage(AttributeTargets.Field)] From 0e5d8caf3e2603109564d6095de3ed1352315d57 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Fri, 20 Sep 2024 15:32:16 -0400 Subject: [PATCH 05/27] Update --- .../Codegen.Tests/fixtures/server/Lib.cs | 2 +- .../server/snapshots/Module#FFI.verified.cs | 287 ++++++++++-------- .../snapshots/Module#PrivateTable.verified.cs | 2 +- crates/bindings-csharp/Codegen/Module.cs | 42 +-- .../Runtime/Internal/Module.cs | 2 +- crates/bindings-csharp/Runtime/Runtime.cs | 4 +- 6 files changed, 179 insertions(+), 160 deletions(-) diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs index d066a3ec69..2716d0060d 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs @@ -39,7 +39,7 @@ public partial record CustomTaggedEnum : SpacetimeDB.TaggedEnum<(int IntVariant, string StringVariant)>; [SpacetimeDB.Table] -public partial class PrivateTable { } +public partial struct PrivateTable { } [SpacetimeDB.Table] public partial struct PublicTable diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs index d4c1ffb7d7..0d23b126bb 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs @@ -13,311 +13,330 @@ public sealed class ReducerContext : BaseReducerContext { } namespace TableViews { public readonly struct PrivateTable - : SpacetimeDB.Internal.ITableView + : SpacetimeDB.Internal.ITableView { - static void SpacetimeDB.Internal.ITableView.ReadGenFields( - System.IO.BinaryReader reader, - ref PrivateTable row - ) { } + static void SpacetimeDB.Internal.ITableView< + PrivateTable, + global::PrivateTable + >.ReadGenFields(System.IO.BinaryReader reader, ref global::PrivateTable row) { } - public IEnumerable Iter() => - SpacetimeDB.Internal.ITableView.Iter(); + public IEnumerable Iter() => + SpacetimeDB.Internal.ITableView.Iter(); - public IEnumerable Query( - System.Linq.Expressions.Expression> predicate - ) => SpacetimeDB.Internal.ITableView.Query(predicate); + public IEnumerable Query( + System.Linq.Expressions.Expression> predicate + ) => + SpacetimeDB.Internal.ITableView.Query( + predicate + ); - public void Insert(ref PrivateTable row) => - SpacetimeDB.Internal.ITableView.Insert(ref row); + public void Insert(ref global::PrivateTable row) => + SpacetimeDB.Internal.ITableView.Insert(ref row); } public readonly struct PublicTable - : SpacetimeDB.Internal.ITableView + : SpacetimeDB.Internal.ITableView { - static void SpacetimeDB.Internal.ITableView.ReadGenFields( - System.IO.BinaryReader reader, - ref PublicTable row - ) + static void SpacetimeDB.Internal.ITableView< + PublicTable, + global::PublicTable + >.ReadGenFields(System.IO.BinaryReader reader, ref global::PublicTable row) { if (row.Id == default) { - row.Id = PublicTable.BSATN.Id.Read(reader); + row.Id = global::PublicTable.BSATN.Id.Read(reader); } } - public IEnumerable Iter() => - SpacetimeDB.Internal.ITableView.Iter(); + public IEnumerable Iter() => + SpacetimeDB.Internal.ITableView.Iter(); - public IEnumerable Query( - System.Linq.Expressions.Expression> predicate - ) => SpacetimeDB.Internal.ITableView.Query(predicate); + public IEnumerable Query( + System.Linq.Expressions.Expression> predicate + ) => SpacetimeDB.Internal.ITableView.Query(predicate); - public void Insert(ref PublicTable row) => - SpacetimeDB.Internal.ITableView.Insert(ref row); + public void Insert(ref global::PublicTable row) => + SpacetimeDB.Internal.ITableView.Insert(ref row); - public IEnumerable FilterById(int Id) => + public IEnumerable FilterById(int Id) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 0, Id, - PublicTable.BSATN.Id + global::PublicTable.BSATN.Id ) .Iter(); - public PublicTable? FindById(int Id) => - FilterById(Id).Cast().SingleOrDefault(); + public global::PublicTable? FindById(int Id) => + FilterById(Id).Cast().SingleOrDefault(); public bool DeleteById(int Id) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 0, Id, - PublicTable.BSATN.Id + global::PublicTable.BSATN.Id ) .Delete(); - public bool UpdateById(int Id, ref PublicTable @this) => + public bool UpdateById(int Id, ref global::PublicTable @this) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 0, Id, - PublicTable.BSATN.Id + global::PublicTable.BSATN.Id ) .Update(ref @this); - public IEnumerable FilterByByteField(byte ByteField) => + public IEnumerable FilterByByteField(byte ByteField) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 1, ByteField, - PublicTable.BSATN.ByteField + global::PublicTable.BSATN.ByteField ) .Iter(); - public IEnumerable FilterByUshortField(ushort UshortField) => + public IEnumerable FilterByUshortField(ushort UshortField) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 2, UshortField, - PublicTable.BSATN.UshortField + global::PublicTable.BSATN.UshortField ) .Iter(); - public IEnumerable FilterByUintField(uint UintField) => + public IEnumerable FilterByUintField(uint UintField) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 3, UintField, - PublicTable.BSATN.UintField + global::PublicTable.BSATN.UintField ) .Iter(); - public IEnumerable FilterByUlongField(ulong UlongField) => + public IEnumerable FilterByUlongField(ulong UlongField) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 4, UlongField, - PublicTable.BSATN.UlongField + global::PublicTable.BSATN.UlongField ) .Iter(); - public IEnumerable FilterByUInt128Field(System.UInt128 UInt128Field) => + public IEnumerable FilterByUInt128Field( + System.UInt128 UInt128Field + ) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 5, UInt128Field, - PublicTable.BSATN.UInt128Field + global::PublicTable.BSATN.UInt128Field ) .Iter(); - public IEnumerable FilterByU128Field(SpacetimeDB.U128 U128Field) => + public IEnumerable FilterByU128Field(SpacetimeDB.U128 U128Field) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 6, U128Field, - PublicTable.BSATN.U128Field + global::PublicTable.BSATN.U128Field ) .Iter(); - public IEnumerable FilterByU256Field(SpacetimeDB.U256 U256Field) => + public IEnumerable FilterByU256Field(SpacetimeDB.U256 U256Field) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 7, U256Field, - PublicTable.BSATN.U256Field + global::PublicTable.BSATN.U256Field ) .Iter(); - public IEnumerable FilterBySbyteField(sbyte SbyteField) => + public IEnumerable FilterBySbyteField(sbyte SbyteField) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 8, SbyteField, - PublicTable.BSATN.SbyteField + global::PublicTable.BSATN.SbyteField ) .Iter(); - public IEnumerable FilterByShortField(short ShortField) => + public IEnumerable FilterByShortField(short ShortField) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 9, ShortField, - PublicTable.BSATN.ShortField + global::PublicTable.BSATN.ShortField ) .Iter(); - public IEnumerable FilterByIntField(int IntField) => + public IEnumerable FilterByIntField(int IntField) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 10, IntField, - PublicTable.BSATN.IntField + global::PublicTable.BSATN.IntField ) .Iter(); - public IEnumerable FilterByLongField(long LongField) => + public IEnumerable FilterByLongField(long LongField) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 11, LongField, - PublicTable.BSATN.LongField + global::PublicTable.BSATN.LongField ) .Iter(); - public IEnumerable FilterByInt128Field(System.Int128 Int128Field) => + public IEnumerable FilterByInt128Field( + System.Int128 Int128Field + ) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 12, Int128Field, - PublicTable.BSATN.Int128Field + global::PublicTable.BSATN.Int128Field ) .Iter(); - public IEnumerable FilterByI128Field(SpacetimeDB.I128 I128Field) => + public IEnumerable FilterByI128Field(SpacetimeDB.I128 I128Field) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 13, I128Field, - PublicTable.BSATN.I128Field + global::PublicTable.BSATN.I128Field ) .Iter(); - public IEnumerable FilterByI256Field(SpacetimeDB.I256 I256Field) => + public IEnumerable FilterByI256Field(SpacetimeDB.I256 I256Field) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 14, I256Field, - PublicTable.BSATN.I256Field + global::PublicTable.BSATN.I256Field ) .Iter(); - public IEnumerable FilterByBoolField(bool BoolField) => + public IEnumerable FilterByBoolField(bool BoolField) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 15, BoolField, - PublicTable.BSATN.BoolField + global::PublicTable.BSATN.BoolField ) .Iter(); - public IEnumerable FilterByStringField(string StringField) => + public IEnumerable FilterByStringField(string StringField) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 18, StringField, - PublicTable.BSATN.StringField + global::PublicTable.BSATN.StringField ) .Iter(); - public IEnumerable FilterByIdentityField( + public IEnumerable FilterByIdentityField( SpacetimeDB.Identity IdentityField ) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 19, IdentityField, - PublicTable.BSATN.IdentityField + global::PublicTable.BSATN.IdentityField ) .Iter(); - public IEnumerable FilterByAddressField( + public IEnumerable FilterByAddressField( SpacetimeDB.Address AddressField ) => SpacetimeDB - .Internal.ITableView.ColEq.Where( + .Internal.ITableView.ColEq.Where( 20, AddressField, - PublicTable.BSATN.AddressField + global::PublicTable.BSATN.AddressField ) .Iter(); } public readonly struct SendMessageTimer - : SpacetimeDB.Internal.ITableView + : SpacetimeDB.Internal.ITableView { static void SpacetimeDB.Internal.ITableView< SendMessageTimer, - Timers.SendMessageTimer - >.ReadGenFields(System.IO.BinaryReader reader, ref Timers.SendMessageTimer row) + global::Timers.SendMessageTimer + >.ReadGenFields(System.IO.BinaryReader reader, ref global::Timers.SendMessageTimer row) { if (row.ScheduledId == default) { - row.ScheduledId = Timers.SendMessageTimer.BSATN.ScheduledId.Read(reader); + row.ScheduledId = global::Timers.SendMessageTimer.BSATN.ScheduledId.Read( + reader + ); } } - public IEnumerable Iter() => - SpacetimeDB.Internal.ITableView.Iter(); + public IEnumerable Iter() => + SpacetimeDB.Internal.ITableView< + SendMessageTimer, + global::Timers.SendMessageTimer + >.Iter(); - public IEnumerable Query( - System.Linq.Expressions.Expression> predicate + public IEnumerable Query( + System.Linq.Expressions.Expression< + Func + > predicate ) => - SpacetimeDB.Internal.ITableView.Query( - predicate - ); - - public void Insert(ref Timers.SendMessageTimer row) => - SpacetimeDB.Internal.ITableView.Insert( - ref row - ); - - public IEnumerable FilterByText(string Text) => + SpacetimeDB.Internal.ITableView< + SendMessageTimer, + global::Timers.SendMessageTimer + >.Query(predicate); + + public void Insert(ref global::Timers.SendMessageTimer row) => + SpacetimeDB.Internal.ITableView< + SendMessageTimer, + global::Timers.SendMessageTimer + >.Insert(ref row); + + public IEnumerable FilterByText(string Text) => SpacetimeDB - .Internal.ITableView.ColEq.Where( - 0, - Text, - Timers.SendMessageTimer.BSATN.Text - ) + .Internal.ITableView< + SendMessageTimer, + global::Timers.SendMessageTimer + >.ColEq.Where(0, Text, global::Timers.SendMessageTimer.BSATN.Text) .Iter(); - public IEnumerable FilterByScheduledId(ulong ScheduledId) => + public IEnumerable FilterByScheduledId( + ulong ScheduledId + ) => SpacetimeDB - .Internal.ITableView.ColEq.Where( - 1, - ScheduledId, - Timers.SendMessageTimer.BSATN.ScheduledId - ) + .Internal.ITableView< + SendMessageTimer, + global::Timers.SendMessageTimer + >.ColEq.Where(1, ScheduledId, global::Timers.SendMessageTimer.BSATN.ScheduledId) .Iter(); - public Timers.SendMessageTimer? FindByScheduledId(ulong ScheduledId) => - FilterByScheduledId(ScheduledId).Cast().SingleOrDefault(); + public global::Timers.SendMessageTimer? FindByScheduledId(ulong ScheduledId) => + FilterByScheduledId(ScheduledId) + .Cast() + .SingleOrDefault(); public bool DeleteByScheduledId(ulong ScheduledId) => SpacetimeDB - .Internal.ITableView.ColEq.Where( - 1, - ScheduledId, - Timers.SendMessageTimer.BSATN.ScheduledId - ) + .Internal.ITableView< + SendMessageTimer, + global::Timers.SendMessageTimer + >.ColEq.Where(1, ScheduledId, global::Timers.SendMessageTimer.BSATN.ScheduledId) .Delete(); - public bool UpdateByScheduledId(ulong ScheduledId, ref Timers.SendMessageTimer @this) => + public bool UpdateByScheduledId( + ulong ScheduledId, + ref global::Timers.SendMessageTimer @this + ) => SpacetimeDB - .Internal.ITableView.ColEq.Where( - 1, - ScheduledId, - Timers.SendMessageTimer.BSATN.ScheduledId - ) + .Internal.ITableView< + SendMessageTimer, + global::Timers.SendMessageTimer + >.ColEq.Where(1, ScheduledId, global::Timers.SendMessageTimer.BSATN.ScheduledId) .Update(ref @this); } } @@ -427,9 +446,9 @@ public static void Main() SpacetimeDB.Internal.Module.RegisterReducer(); SpacetimeDB.Internal.Module.RegisterReducer(); SpacetimeDB.Internal.Module.RegisterReducer(); - SpacetimeDB.Internal.Module.RegisterTable(); - SpacetimeDB.Internal.Module.RegisterTable(); - SpacetimeDB.Internal.Module.RegisterTable(); + SpacetimeDB.Internal.Module.RegisterTable(); + SpacetimeDB.Internal.Module.RegisterTable(); + SpacetimeDB.Internal.Module.RegisterTable(); } // Exports only work from the main assembly, so we need to generate forwarding methods. diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PrivateTable.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PrivateTable.verified.cs index 915464b0ef..5b43bd94b3 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PrivateTable.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PrivateTable.verified.cs @@ -2,7 +2,7 @@ // #nullable enable -partial class PrivateTable : SpacetimeDB.Internal.ITable +partial struct PrivateTable : SpacetimeDB.Internal.ITable { public void ReadFields(System.IO.BinaryReader reader) { } diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index c0d05f67f0..6c0976fd23 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -7,7 +7,7 @@ namespace SpacetimeDB.Codegen; record ColumnDeclaration : MemberDeclaration { - public readonly ImmutableArray<(string?, ColumnAttrs)> Attrs; + public readonly EquatableArray<(string?, ColumnAttrs)> Attrs; public readonly bool IsEquatable; public ColumnDeclaration( @@ -20,14 +20,14 @@ bool isEquatable : base(name, type, typeInfo) { (string?, ColumnAttrs)[] x = [(default(string), attrs)]; - Attrs = x.ToImmutableArray(); + Attrs = new(x.ToImmutableArray()); IsEquatable = isEquatable; } public ColumnDeclaration(IFieldSymbol field) : base(field) { - Attrs = field + Attrs = new(field .GetAttributes() .Select(a => (a.NamedArguments.FirstOrDefault(a => a.Key == "Table").Value.Value as string, a.AttributeClass?.ToString() switch { @@ -37,7 +37,7 @@ public ColumnDeclaration(IFieldSymbol field) "SpacetimeDB.IndexedAttribute" => ColumnAttrs.Indexed, _ => ColumnAttrs.UnSet, })) - .ToImmutableArray(); + .ToImmutableArray()); var type = field.Type; @@ -106,13 +106,11 @@ public string GenerateFilterEntry() => } record TableView { - public readonly TableDeclaration Table; public readonly string Name; public readonly bool IsPublic; public readonly string? Scheduled; public TableView(TableDeclaration table, AttributeData data) { - Table = table; Name = data.NamedArguments.FirstOrDefault(x => x.Key == "Name").Value.Value as string ?? table.ShortName; IsPublic = data.NamedArguments.Any(pair => pair is { Key: "Public", Value.Value: true }); @@ -128,7 +126,7 @@ record TableDeclaration : BaseTypeDeclaration { public readonly string Visibility; public readonly string? Scheduled; - public readonly ImmutableArray Views; + public readonly EquatableArray Views; private static readonly ColumnDeclaration[] ScheduledColumns = [ @@ -160,10 +158,10 @@ or Accessibility.NotApplicable ), }; - Views = context.Attributes + Views = new(context.Attributes .Where(a => a.AttributeClass?.ToDisplayString() == "SpacetimeDB.TableAttribute") .Select(a => new TableView(this, a)) - .ToImmutableArray(); + .ToImmutableArray()); var schedules = Views.Where(t => t.Scheduled != null).Select(t => t.Scheduled); var numSchedules = schedules.Count(); @@ -190,24 +188,25 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) { .Select((field, i) => (field, i)) .Where(pair => pair.field.IsEquatable) ) { - var colEqWhere = $"{iTable}.ColEq.Where({i}, {f.Name}, {FullName}.BSATN.{f.Name})"; + var globalName = $"global::{FullName}"; + var colEqWhere = $"{iTable}.ColEq.Where({i}, {f.Name}, {globalName}.BSATN.{f.Name})"; yield return $""" - public IEnumerable<{FullName}> FilterBy{f.Name}({f.Type} {f.Name}) => + public IEnumerable<{globalName}> FilterBy{f.Name}({f.Type} {f.Name}) => {colEqWhere}.Iter(); """; if (f.GetAttrs(viewName).HasFlag(ColumnAttrs.Unique)) { yield return $""" - public {FullName}? FindBy{f.Name}({f.Type} {f.Name}) => + public {globalName}? FindBy{f.Name}({f.Type} {f.Name}) => FilterBy{f.Name}({f.Name}) - .Cast<{FullName}?>() + .Cast<{globalName}?>() .SingleOrDefault(); public bool DeleteBy{f.Name}({f.Type} {f.Name}) => {colEqWhere}.Delete(); - public bool UpdateBy{f.Name}({f.Type} {f.Name}, ref {FullName} @this) => + public bool UpdateBy{f.Name}({f.Type} {f.Name}, ref {globalName} @this) => {colEqWhere}.Update(ref @this); """; } @@ -220,25 +219,26 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) { .Where(f => f.GetAttrs(v.Name).HasFlag(ColumnAttrs.AutoInc)) .Select(f => f.Name); - var iTable = $"SpacetimeDB.Internal.ITableView<{v.Name}, {FullName}>"; - yield return new((v.Name, FullName), ($$""" + var globalName = $"global::{FullName}"; + var iTable = $"SpacetimeDB.Internal.ITableView<{v.Name}, {globalName}>"; + yield return new((v.Name, globalName), ($$""" {{Visibility}} readonly struct {{v.Name}} : {{iTable}} { - static void {{iTable}}.ReadGenFields(System.IO.BinaryReader reader, ref {{FullName}} row) { + static void {{iTable}}.ReadGenFields(System.IO.BinaryReader reader, ref {{globalName}} row) { {{string.Join( "\n", autoIncFields.Select(name => $$""" if (row.{{name}} == default) { - row.{{name}} = {{FullName}}.BSATN.{{name}}.Read(reader); + row.{{name}} = {{globalName}}.BSATN.{{name}}.Read(reader); } """ ) )}} } - public IEnumerable<{{FullName}}> Iter() => {{iTable}}.Iter(); - public IEnumerable<{{FullName}}> Query(System.Linq.Expressions.Expression> predicate) => {{iTable}}.Query(predicate); - public void Insert(ref {{FullName}} row) => {{iTable}}.Insert(ref row); + public IEnumerable<{{globalName}}> Iter() => {{iTable}}.Iter(); + public IEnumerable<{{globalName}}> Query(System.Linq.Expressions.Expression> predicate) => {{iTable}}.Query(predicate); + public void Insert(ref {{globalName}} row) => {{iTable}}.Insert(ref row); {{string.Join("\n", GenerateViewFilters(v.Name, iTable))}} } """, $"{Visibility} TableViews.{v.Name} {v.Name} => new();")); diff --git a/crates/bindings-csharp/Runtime/Internal/Module.cs b/crates/bindings-csharp/Runtime/Internal/Module.cs index dbca3725c9..f3a756b49b 100644 --- a/crates/bindings-csharp/Runtime/Internal/Module.cs +++ b/crates/bindings-csharp/Runtime/Internal/Module.cs @@ -197,7 +197,7 @@ BytesSink error Runtime.SenderAddress = Address.From(MemoryMarshal.AsBytes([address_0, address_1]).ToArray()); Runtime.Random = new((int)timestamp.MicrosecondsSinceEpoch); - Runtime.Timestamp = timestamp.ToStd(); + Runtime.Time = timestamp.ToStd(); try { diff --git a/crates/bindings-csharp/Runtime/Runtime.cs b/crates/bindings-csharp/Runtime/Runtime.cs index 9105c23287..f28680b3e3 100644 --- a/crates/bindings-csharp/Runtime/Runtime.cs +++ b/crates/bindings-csharp/Runtime/Runtime.cs @@ -63,7 +63,7 @@ public abstract class BaseReducerContext : DbContext, IReducerCo { public Identity Sender => Runtime.SenderIdentity!; public Address Address => Runtime.SenderAddress!; - public DateTimeOffset Timestamp => Runtime.Timestamp!; + public DateTimeOffset Time => Runtime.Time!; } public static class Runtime @@ -74,5 +74,5 @@ public static class Runtime public static Address? SenderAddress { get; internal set; } - public static DateTimeOffset Timestamp { get; internal set; } + public static DateTimeOffset Time { get; internal set; } } From 07f252612a46c84bae5f4f06f5f8d6cccf3b195d Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Tue, 24 Sep 2024 00:07:59 -0400 Subject: [PATCH 06/27] Review update --- crates/bindings-csharp/BSATN.Runtime/Attrs.cs | 3 +- .../Codegen.Tests/fixtures/server/Lib.cs | 4 +- .../server/snapshots/Module#FFI.verified.cs | 8 +- .../snapshots/Module#PublicTable.verified.cs | 331 ++++++++++++------ ...Module#Timers.SendMessageTimer.verified.cs | 85 +++-- .../snapshots/Type#CustomClass.verified.cs | 2 +- crates/bindings-csharp/Codegen/Module.cs | 100 +++--- crates/bindings-csharp/Runtime/Attrs.cs | 2 +- .../bindings-csharp/Runtime/Internal/FFI.cs | 2 +- .../Runtime/Internal/Module.cs | 6 +- .../bindings-csharp/Runtime/LogStopwatch.cs | 5 +- .../sdk-test-connect-disconnect-cs.csproj | 1 - modules/sdk-test-cs/sdk-test-cs.csproj | 1 - .../sdk-test-multi-cs.csproj | 1 - .../spacetimedb-quickstart-server-cs.csproj | 1 - 15 files changed, 369 insertions(+), 183 deletions(-) diff --git a/crates/bindings-csharp/BSATN.Runtime/Attrs.cs b/crates/bindings-csharp/BSATN.Runtime/Attrs.cs index 6dc073d987..840e0aca96 100644 --- a/crates/bindings-csharp/BSATN.Runtime/Attrs.cs +++ b/crates/bindings-csharp/BSATN.Runtime/Attrs.cs @@ -12,4 +12,5 @@ public sealed class TypeAttribute : Attribute { } // This could be an interface, but using `record` forces C# to check that it can // only be applied on types that are records themselves. public abstract record TaggedEnum - where Variants : struct, ITuple { } + where Variants : struct, ITuple +{ } diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs index 2716d0060d..df6a40cc5d 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs @@ -13,7 +13,7 @@ public partial struct CustomStruct } [SpacetimeDB.Type] -public partial struct CustomClass +public partial class CustomClass { public const int IGNORE_ME = 0; public static readonly string IGNORE_ME_TOO = ""; @@ -22,7 +22,7 @@ public partial struct CustomClass } [StructLayout(LayoutKind.Auto)] -public partial struct CustomClass +public partial class CustomClass { public int IgnoreExtraFields; } diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs index 0d23b126bb..e738171fb3 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs @@ -10,7 +10,7 @@ namespace SpacetimeDB { public sealed class ReducerContext : BaseReducerContext { } - namespace TableViews + namespace Internal.TableHandles { public readonly struct PrivateTable : SpacetimeDB.Internal.ITableView @@ -343,9 +343,9 @@ public bool UpdateByScheduledId( public sealed class Local { - public TableViews.PrivateTable PrivateTable => new(); - public TableViews.PublicTable PublicTable => new(); - public TableViews.SendMessageTimer SendMessageTimer => new(); + public Internal.TableHandles.PrivateTable PrivateTable => new(); + public Internal.TableHandles.PublicTable PublicTable => new(); + public Internal.TableHandles.SendMessageTimer SendMessageTimer => new(); } } diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs index 6f494ec99c..7b24363b14 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs @@ -193,150 +193,285 @@ SpacetimeDB.BSATN.ITypeRegistrar registrar ) => [ new( - TableName: nameof(PublicTable), - Columns: - [ - new(nameof(Id), BSATN.Id.GetAlgebraicType(registrar)), - new(nameof(ByteField), BSATN.ByteField.GetAlgebraicType(registrar)), - new(nameof(UshortField), BSATN.UshortField.GetAlgebraicType(registrar)), - new(nameof(UintField), BSATN.UintField.GetAlgebraicType(registrar)), - new(nameof(UlongField), BSATN.UlongField.GetAlgebraicType(registrar)), - new(nameof(UInt128Field), BSATN.UInt128Field.GetAlgebraicType(registrar)), - new(nameof(U128Field), BSATN.U128Field.GetAlgebraicType(registrar)), - new(nameof(U256Field), BSATN.U256Field.GetAlgebraicType(registrar)), - new(nameof(SbyteField), BSATN.SbyteField.GetAlgebraicType(registrar)), - new(nameof(ShortField), BSATN.ShortField.GetAlgebraicType(registrar)), - new(nameof(IntField), BSATN.IntField.GetAlgebraicType(registrar)), - new(nameof(LongField), BSATN.LongField.GetAlgebraicType(registrar)), - new(nameof(Int128Field), BSATN.Int128Field.GetAlgebraicType(registrar)), - new(nameof(I128Field), BSATN.I128Field.GetAlgebraicType(registrar)), - new(nameof(I256Field), BSATN.I256Field.GetAlgebraicType(registrar)), - new(nameof(BoolField), BSATN.BoolField.GetAlgebraicType(registrar)), - new(nameof(FloatField), BSATN.FloatField.GetAlgebraicType(registrar)), - new(nameof(DoubleField), BSATN.DoubleField.GetAlgebraicType(registrar)), - new(nameof(StringField), BSATN.StringField.GetAlgebraicType(registrar)), - new(nameof(IdentityField), BSATN.IdentityField.GetAlgebraicType(registrar)), - new(nameof(AddressField), BSATN.AddressField.GetAlgebraicType(registrar)), - new( - nameof(CustomStructField), - BSATN.CustomStructField.GetAlgebraicType(registrar) - ), - new( - nameof(CustomClassField), - BSATN.CustomClassField.GetAlgebraicType(registrar) - ), - new(nameof(CustomEnumField), BSATN.CustomEnumField.GetAlgebraicType(registrar)), - new( - nameof(CustomTaggedEnumField), - BSATN.CustomTaggedEnumField.GetAlgebraicType(registrar) - ), - new(nameof(ListField), BSATN.ListField.GetAlgebraicType(registrar)), - new(nameof(DictionaryField), BSATN.DictionaryField.GetAlgebraicType(registrar)), - new( - nameof(NullableValueField), - BSATN.NullableValueField.GetAlgebraicType(registrar) - ), - new( - nameof(NullableReferenceField), - BSATN.NullableReferenceField.GetAlgebraicType(registrar) - ), - new( - nameof(ComplexNestedField), - BSATN.ComplexNestedField.GetAlgebraicType(registrar) - ) - ], - Indexes: [], - Constraints: - [ - new( - nameof(PublicTable), - 0, - nameof(Id), - SpacetimeDB.ColumnAttrs.PrimaryKeyIdentity - ) - ], - Sequences: [], - // "system" | "user" - TableType: "user", - // "public" | "private" - TableAccess: "private", - Scheduled: null + new( + TableName: nameof(PublicTable), + Columns: + [ + new(nameof(Id), global::PublicTable.BSATN.Id.GetAlgebraicType(registrar)), + new( + nameof(ByteField), + global::PublicTable.BSATN.ByteField.GetAlgebraicType(registrar) + ), + new( + nameof(UshortField), + global::PublicTable.BSATN.UshortField.GetAlgebraicType(registrar) + ), + new( + nameof(UintField), + global::PublicTable.BSATN.UintField.GetAlgebraicType(registrar) + ), + new( + nameof(UlongField), + global::PublicTable.BSATN.UlongField.GetAlgebraicType(registrar) + ), + new( + nameof(UInt128Field), + global::PublicTable.BSATN.UInt128Field.GetAlgebraicType(registrar) + ), + new( + nameof(U128Field), + global::PublicTable.BSATN.U128Field.GetAlgebraicType(registrar) + ), + new( + nameof(U256Field), + global::PublicTable.BSATN.U256Field.GetAlgebraicType(registrar) + ), + new( + nameof(SbyteField), + global::PublicTable.BSATN.SbyteField.GetAlgebraicType(registrar) + ), + new( + nameof(ShortField), + global::PublicTable.BSATN.ShortField.GetAlgebraicType(registrar) + ), + new( + nameof(IntField), + global::PublicTable.BSATN.IntField.GetAlgebraicType(registrar) + ), + new( + nameof(LongField), + global::PublicTable.BSATN.LongField.GetAlgebraicType(registrar) + ), + new( + nameof(Int128Field), + global::PublicTable.BSATN.Int128Field.GetAlgebraicType(registrar) + ), + new( + nameof(I128Field), + global::PublicTable.BSATN.I128Field.GetAlgebraicType(registrar) + ), + new( + nameof(I256Field), + global::PublicTable.BSATN.I256Field.GetAlgebraicType(registrar) + ), + new( + nameof(BoolField), + global::PublicTable.BSATN.BoolField.GetAlgebraicType(registrar) + ), + new( + nameof(FloatField), + global::PublicTable.BSATN.FloatField.GetAlgebraicType(registrar) + ), + new( + nameof(DoubleField), + global::PublicTable.BSATN.DoubleField.GetAlgebraicType(registrar) + ), + new( + nameof(StringField), + global::PublicTable.BSATN.StringField.GetAlgebraicType(registrar) + ), + new( + nameof(IdentityField), + global::PublicTable.BSATN.IdentityField.GetAlgebraicType(registrar) + ), + new( + nameof(AddressField), + global::PublicTable.BSATN.AddressField.GetAlgebraicType(registrar) + ), + new( + nameof(CustomStructField), + global::PublicTable.BSATN.CustomStructField.GetAlgebraicType(registrar) + ), + new( + nameof(CustomClassField), + global::PublicTable.BSATN.CustomClassField.GetAlgebraicType(registrar) + ), + new( + nameof(CustomEnumField), + global::PublicTable.BSATN.CustomEnumField.GetAlgebraicType(registrar) + ), + new( + nameof(CustomTaggedEnumField), + global::PublicTable.BSATN.CustomTaggedEnumField.GetAlgebraicType( + registrar + ) + ), + new( + nameof(ListField), + global::PublicTable.BSATN.ListField.GetAlgebraicType(registrar) + ), + new( + nameof(DictionaryField), + global::PublicTable.BSATN.DictionaryField.GetAlgebraicType(registrar) + ), + new( + nameof(NullableValueField), + global::PublicTable.BSATN.NullableValueField.GetAlgebraicType(registrar) + ), + new( + nameof(NullableReferenceField), + global::PublicTable.BSATN.NullableReferenceField.GetAlgebraicType( + registrar + ) + ), + new( + nameof(ComplexNestedField), + global::PublicTable.BSATN.ComplexNestedField.GetAlgebraicType(registrar) + ) + ], + Indexes: [], + Constraints: + [ + new(nameof(PublicTable), 0, nameof(Id), (SpacetimeDB.ColumnAttrs)15) + ], + Sequences: [], + // "system" | "user" + TableType: "user", + // "public" | "private" + TableAccess: "private", + Scheduled: null + ), + (uint) + ( + (SpacetimeDB.BSATN.AlgebraicType.Ref)new BSATN().GetAlgebraicType(registrar) + ).Ref_ ), ]; static SpacetimeDB.Internal.Filter SpacetimeDB.Internal.ITable.CreateFilter() => new( [ - new(nameof(Id), (w, v) => BSATN.Id.Write(w, (int)v!)), - new(nameof(ByteField), (w, v) => BSATN.ByteField.Write(w, (byte)v!)), - new(nameof(UshortField), (w, v) => BSATN.UshortField.Write(w, (ushort)v!)), - new(nameof(UintField), (w, v) => BSATN.UintField.Write(w, (uint)v!)), - new(nameof(UlongField), (w, v) => BSATN.UlongField.Write(w, (ulong)v!)), + new(nameof(Id), (w, v) => global::PublicTable.BSATN.Id.Write(w, (int)v!)), + new( + nameof(ByteField), + (w, v) => global::PublicTable.BSATN.ByteField.Write(w, (byte)v!) + ), + new( + nameof(UshortField), + (w, v) => global::PublicTable.BSATN.UshortField.Write(w, (ushort)v!) + ), + new( + nameof(UintField), + (w, v) => global::PublicTable.BSATN.UintField.Write(w, (uint)v!) + ), + new( + nameof(UlongField), + (w, v) => global::PublicTable.BSATN.UlongField.Write(w, (ulong)v!) + ), new( nameof(UInt128Field), - (w, v) => BSATN.UInt128Field.Write(w, (System.UInt128)v!) + (w, v) => global::PublicTable.BSATN.UInt128Field.Write(w, (System.UInt128)v!) + ), + new( + nameof(U128Field), + (w, v) => global::PublicTable.BSATN.U128Field.Write(w, (SpacetimeDB.U128)v!) + ), + new( + nameof(U256Field), + (w, v) => global::PublicTable.BSATN.U256Field.Write(w, (SpacetimeDB.U256)v!) + ), + new( + nameof(SbyteField), + (w, v) => global::PublicTable.BSATN.SbyteField.Write(w, (sbyte)v!) + ), + new( + nameof(ShortField), + (w, v) => global::PublicTable.BSATN.ShortField.Write(w, (short)v!) + ), + new( + nameof(IntField), + (w, v) => global::PublicTable.BSATN.IntField.Write(w, (int)v!) + ), + new( + nameof(LongField), + (w, v) => global::PublicTable.BSATN.LongField.Write(w, (long)v!) + ), + new( + nameof(Int128Field), + (w, v) => global::PublicTable.BSATN.Int128Field.Write(w, (System.Int128)v!) + ), + new( + nameof(I128Field), + (w, v) => global::PublicTable.BSATN.I128Field.Write(w, (SpacetimeDB.I128)v!) + ), + new( + nameof(I256Field), + (w, v) => global::PublicTable.BSATN.I256Field.Write(w, (SpacetimeDB.I256)v!) + ), + new( + nameof(BoolField), + (w, v) => global::PublicTable.BSATN.BoolField.Write(w, (bool)v!) + ), + new( + nameof(FloatField), + (w, v) => global::PublicTable.BSATN.FloatField.Write(w, (float)v!) + ), + new( + nameof(DoubleField), + (w, v) => global::PublicTable.BSATN.DoubleField.Write(w, (double)v!) + ), + new( + nameof(StringField), + (w, v) => global::PublicTable.BSATN.StringField.Write(w, (string)v!) ), - new(nameof(U128Field), (w, v) => BSATN.U128Field.Write(w, (SpacetimeDB.U128)v!)), - new(nameof(U256Field), (w, v) => BSATN.U256Field.Write(w, (SpacetimeDB.U256)v!)), - new(nameof(SbyteField), (w, v) => BSATN.SbyteField.Write(w, (sbyte)v!)), - new(nameof(ShortField), (w, v) => BSATN.ShortField.Write(w, (short)v!)), - new(nameof(IntField), (w, v) => BSATN.IntField.Write(w, (int)v!)), - new(nameof(LongField), (w, v) => BSATN.LongField.Write(w, (long)v!)), - new(nameof(Int128Field), (w, v) => BSATN.Int128Field.Write(w, (System.Int128)v!)), - new(nameof(I128Field), (w, v) => BSATN.I128Field.Write(w, (SpacetimeDB.I128)v!)), - new(nameof(I256Field), (w, v) => BSATN.I256Field.Write(w, (SpacetimeDB.I256)v!)), - new(nameof(BoolField), (w, v) => BSATN.BoolField.Write(w, (bool)v!)), - new(nameof(FloatField), (w, v) => BSATN.FloatField.Write(w, (float)v!)), - new(nameof(DoubleField), (w, v) => BSATN.DoubleField.Write(w, (double)v!)), - new(nameof(StringField), (w, v) => BSATN.StringField.Write(w, (string)v!)), new( nameof(IdentityField), - (w, v) => BSATN.IdentityField.Write(w, (SpacetimeDB.Identity)v!) + (w, v) => + global::PublicTable.BSATN.IdentityField.Write(w, (SpacetimeDB.Identity)v!) ), new( nameof(AddressField), - (w, v) => BSATN.AddressField.Write(w, (SpacetimeDB.Address)v!) + (w, v) => + global::PublicTable.BSATN.AddressField.Write(w, (SpacetimeDB.Address)v!) ), new( nameof(CustomStructField), - (w, v) => BSATN.CustomStructField.Write(w, (CustomStruct)v!) + (w, v) => global::PublicTable.BSATN.CustomStructField.Write(w, (CustomStruct)v!) ), new( nameof(CustomClassField), - (w, v) => BSATN.CustomClassField.Write(w, (CustomClass)v!) + (w, v) => global::PublicTable.BSATN.CustomClassField.Write(w, (CustomClass)v!) ), new( nameof(CustomEnumField), - (w, v) => BSATN.CustomEnumField.Write(w, (CustomEnum)v!) + (w, v) => global::PublicTable.BSATN.CustomEnumField.Write(w, (CustomEnum)v!) ), new( nameof(CustomTaggedEnumField), - (w, v) => BSATN.CustomTaggedEnumField.Write(w, (CustomTaggedEnum)v!) + (w, v) => + global::PublicTable.BSATN.CustomTaggedEnumField.Write( + w, + (CustomTaggedEnum)v! + ) ), new( nameof(ListField), - (w, v) => BSATN.ListField.Write(w, (System.Collections.Generic.List)v!) + (w, v) => + global::PublicTable.BSATN.ListField.Write( + w, + (System.Collections.Generic.List)v! + ) ), new( nameof(DictionaryField), (w, v) => - BSATN.DictionaryField.Write( + global::PublicTable.BSATN.DictionaryField.Write( w, (System.Collections.Generic.Dictionary)v! ) ), new( nameof(NullableValueField), - (w, v) => BSATN.NullableValueField.Write(w, (int?)v!) + (w, v) => global::PublicTable.BSATN.NullableValueField.Write(w, (int?)v!) ), new( nameof(NullableReferenceField), - (w, v) => BSATN.NullableReferenceField.Write(w, (string?)v!) + (w, v) => global::PublicTable.BSATN.NullableReferenceField.Write(w, (string?)v!) ), new( nameof(ComplexNestedField), (w, v) => - BSATN.ComplexNestedField.Write( + global::PublicTable.BSATN.ComplexNestedField.Write( w, (System.Collections.Generic.Dictionary< CustomEnum, diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs index ebdfc9d408..67865ddea2 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs @@ -58,40 +58,73 @@ SpacetimeDB.BSATN.ITypeRegistrar registrar ) => [ new( - TableName: nameof(SendMessageTimer), - Columns: - [ - new(nameof(Text), BSATN.Text.GetAlgebraicType(registrar)), - new(nameof(ScheduledId), BSATN.ScheduledId.GetAlgebraicType(registrar)), - new(nameof(ScheduledAt), BSATN.ScheduledAt.GetAlgebraicType(registrar)) - ], - Indexes: [], - Constraints: - [ - new( - nameof(SendMessageTimer), - 1, - nameof(ScheduledId), - SpacetimeDB.ColumnAttrs.PrimaryKeyIdentity - ) - ], - Sequences: [], - // "system" | "user" - TableType: "user", - // "public" | "private" - TableAccess: "private", - Scheduled: nameof(SendScheduledMessage) + new( + TableName: nameof(SendMessageTimer), + Columns: + [ + new( + nameof(Text), + global::Timers.SendMessageTimer.BSATN.Text.GetAlgebraicType( + registrar + ) + ), + new( + nameof(ScheduledId), + global::Timers.SendMessageTimer.BSATN.ScheduledId.GetAlgebraicType( + registrar + ) + ), + new( + nameof(ScheduledAt), + global::Timers.SendMessageTimer.BSATN.ScheduledAt.GetAlgebraicType( + registrar + ) + ) + ], + Indexes: [], + Constraints: + [ + new( + nameof(SendMessageTimer), + 1, + nameof(ScheduledId), + (SpacetimeDB.ColumnAttrs)15 + ) + ], + Sequences: [], + // "system" | "user" + TableType: "user", + // "public" | "private" + TableAccess: "private", + Scheduled: nameof(SendScheduledMessage) + ), + (uint) + ( + (SpacetimeDB.BSATN.AlgebraicType.Ref) + new BSATN().GetAlgebraicType(registrar) + ).Ref_ ), ]; static SpacetimeDB.Internal.Filter SpacetimeDB.Internal.ITable.CreateFilter() => new( [ - new(nameof(Text), (w, v) => BSATN.Text.Write(w, (string)v!)), - new(nameof(ScheduledId), (w, v) => BSATN.ScheduledId.Write(w, (ulong)v!)), + new( + nameof(Text), + (w, v) => global::Timers.SendMessageTimer.BSATN.Text.Write(w, (string)v!) + ), + new( + nameof(ScheduledId), + (w, v) => + global::Timers.SendMessageTimer.BSATN.ScheduledId.Write(w, (ulong)v!) + ), new( nameof(ScheduledAt), - (w, v) => BSATN.ScheduledAt.Write(w, (SpacetimeDB.ScheduleAt)v!) + (w, v) => + global::Timers.SendMessageTimer.BSATN.ScheduledAt.Write( + w, + (SpacetimeDB.ScheduleAt)v! + ) ) ] ); diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Type#CustomClass.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Type#CustomClass.verified.cs index f1c7727c41..1ac96f3d0d 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Type#CustomClass.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Type#CustomClass.verified.cs @@ -2,7 +2,7 @@ // #nullable enable -partial struct CustomClass : SpacetimeDB.BSATN.IStructuralReadWrite +partial class CustomClass : SpacetimeDB.BSATN.IStructuralReadWrite { public void ReadFields(System.IO.BinaryReader reader) { diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index 6c0976fd23..82969aaf4b 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -7,10 +7,12 @@ namespace SpacetimeDB.Codegen; record ColumnDeclaration : MemberDeclaration { - public readonly EquatableArray<(string?, ColumnAttrs)> Attrs; + public readonly EquatableArray<(string? table, ColumnAttrs mask)> Attrs; public readonly bool IsEquatable; + public readonly string FullTableName; public ColumnDeclaration( + string tableName, string name, string type, string typeInfo, @@ -22,15 +24,19 @@ bool isEquatable (string?, ColumnAttrs)[] x = [(default(string), attrs)]; Attrs = new(x.ToImmutableArray()); IsEquatable = isEquatable; + FullTableName = tableName; } - public ColumnDeclaration(IFieldSymbol field) + public ColumnDeclaration(string tableName, IFieldSymbol field) : base(field) { + FullTableName = tableName; + Attrs = new(field .GetAttributes() .Select(a => (a.NamedArguments.FirstOrDefault(a => a.Key == "Table").Value.Value as string, - a.AttributeClass?.ToString() switch { + a.AttributeClass?.ToString() switch + { "SpacetimeDB.AutoIncAttribute" => ColumnAttrs.AutoInc, "SpacetimeDB.PrimaryKeyAttribute" => ColumnAttrs.PrimaryKey, "SpacetimeDB.UniqueAttribute" => ColumnAttrs.Unique, @@ -61,7 +67,7 @@ or SpecialType.System_Int64 _ => false, }; - var attrs = Attrs.Aggregate(ColumnAttrs.UnSet, (xs, x) => xs | x.Item2); + var attrs = Attrs.Aggregate(ColumnAttrs.UnSet, (xs, x) => xs | x.mask); if (attrs.HasFlag(ColumnAttrs.AutoInc) && !isInteger) { @@ -93,24 +99,26 @@ or SpecialType.System_Int64 } public ColumnAttrs GetAttrs(string tableName) => Attrs - .Where(x => x.Item1 == null || x.Item1 == tableName) - .Aggregate(ColumnAttrs.UnSet, (xs, x) => xs | x.Item2); + .Where(x => x.table == null || x.table == tableName) + .Aggregate(ColumnAttrs.UnSet, (xs, x) => xs | x.mask); // For the `TableDesc` constructor. public string GenerateColumnDef() => - $"new (nameof({Name}), BSATN.{Name}.GetAlgebraicType(registrar))"; + $"new (nameof({Name}), global::{FullTableName}.BSATN.{Name}.GetAlgebraicType(registrar))"; // For the `Filter` constructor. public string GenerateFilterEntry() => - $"new (nameof({Name}), (w, v) => BSATN.{Name}.Write(w, ({Type}) v!))"; + $"new (nameof({Name}), (w, v) => global::{FullTableName}.BSATN.{Name}.Write(w, ({Type}) v!))"; } -record TableView { +record TableView +{ public readonly string Name; public readonly bool IsPublic; public readonly string? Scheduled; - public TableView(TableDeclaration table, AttributeData data) { + public TableView(TableDeclaration table, AttributeData data) + { Name = data.NamedArguments.FirstOrDefault(x => x.Key == "Name").Value.Value as string ?? table.ShortName; IsPublic = data.NamedArguments.Any(pair => pair is { Key: "Public", Value.Value: true }); @@ -128,10 +136,11 @@ record TableDeclaration : BaseTypeDeclaration public readonly string? Scheduled; public readonly EquatableArray Views; - private static readonly ColumnDeclaration[] ScheduledColumns = + private static ColumnDeclaration[] ScheduledColumns(string tableName) => [ - new("ScheduledId", "ulong", "SpacetimeDB.BSATN.U64", ColumnAttrs.PrimaryKeyAuto, true), + new(tableName, "ScheduledId", "ulong", "SpacetimeDB.BSATN.U64", ColumnAttrs.PrimaryKeyAuto, true), new( + tableName, "ScheduledAt", "SpacetimeDB.ScheduleAt", "SpacetimeDB.ScheduleAt.BSATN", @@ -148,7 +157,8 @@ public TableDeclaration(GeneratorAttributeSyntaxContext context) throw new InvalidOperationException("Tagged enums cannot be tables."); } - Visibility = context.TargetSymbol.DeclaredAccessibility switch { + Visibility = context.TargetSymbol.DeclaredAccessibility switch + { Accessibility.ProtectedAndInternal or Accessibility.NotApplicable or Accessibility.Internal => "internal", @@ -163,31 +173,37 @@ or Accessibility.NotApplicable .Select(a => new TableView(this, a)) .ToImmutableArray()); - var schedules = Views.Where(t => t.Scheduled != null).Select(t => t.Scheduled); + var schedules = Views.Select(t => t.Scheduled); var numSchedules = schedules.Count(); - if (numSchedules > 0) { + if (numSchedules > 0) + { var distinctSchedules = schedules.Distinct(); - if (numSchedules != Views.Length || distinctSchedules.Count() != 1) { + if (numSchedules != Views.Length || distinctSchedules.Count() != 1) + { throw new Exception("When using multiple [Table] attributes with schedule, all [Table] must have the same schedule."); } Scheduled = distinctSchedules.First(); - - // For scheduled tables, we append extra fields early in the pipeline, - // both to the type itself and to the BSATN information, as if they - // were part of the original declaration. - Members = new(Members.Concat(ScheduledColumns).ToImmutableArray()); + if (Scheduled != null) + { + // For scheduled tables, we append extra fields early in the pipeline, + // both to the type itself and to the BSATN information, as if they + // were part of the original declaration. + Members = new(Members.Concat(ScheduledColumns(FullName)).ToImmutableArray()); + } } } - protected override ColumnDeclaration ConvertMember(IFieldSymbol field) => new(field); + protected override ColumnDeclaration ConvertMember(IFieldSymbol field) => new(FullName, field); - public IEnumerable GenerateViewFilters(string viewName, string iTable) { + public IEnumerable GenerateViewFilters(string viewName, string iTable) + { foreach ( var (f, i) in Members .Select((field, i) => (field, i)) .Where(pair => pair.field.IsEquatable) - ) { + ) + { var globalName = $"global::{FullName}"; var colEqWhere = $"{iTable}.ColEq.Where({i}, {f.Name}, {globalName}.BSATN.{f.Name})"; @@ -196,7 +212,8 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) { {colEqWhere}.Iter(); """; - if (f.GetAttrs(viewName).HasFlag(ColumnAttrs.Unique)) { + if (f.GetAttrs(viewName).HasFlag(ColumnAttrs.Unique)) + { yield return $""" public {globalName}? FindBy{f.Name}({f.Type} {f.Name}) => FilterBy{f.Name}({f.Name}) @@ -213,8 +230,10 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) { } } - public IEnumerable> GenerateViews() { - foreach (var v in Views) { + public IEnumerable> GenerateViews() + { + foreach (var v in Views) + { var autoIncFields = Members .Where(f => f.GetAttrs(v.Name).HasFlag(ColumnAttrs.AutoInc)) .Select(f => f.Name); @@ -241,7 +260,7 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) { public void Insert(ref {{globalName}} row) => {{iTable}}.Insert(ref row); {{string.Join("\n", GenerateViewFilters(v.Name, iTable))}} } - """, $"{Visibility} TableViews.{v.Name} {v.Name} => new();")); + """, $"{Visibility} Internal.TableHandles.{v.Name} {v.Name} => new();")); } } @@ -289,15 +308,15 @@ public override Scope.Extensions ToExtensions() ",\n", Members // Important: the position must be stored here, before filtering. - .Select((col, pos) => (col, pos, col.GetAttrs(v.Name))) - .Where(tuple => tuple.Item3 != ColumnAttrs.UnSet) - .Select(pair => + .Select((col, pos) => (col, pos, attr: col.GetAttrs(v.Name))) + .Where(tuple => tuple.attr != ColumnAttrs.UnSet) + .Select(tuple => $$""" new ( nameof({{ShortName}}), - {{pair.pos}}, - nameof({{pair.col.Name}}), - (SpacetimeDB.ColumnAttrs){{(int)pair.Item3}} + {{tuple.pos}}, + nameof({{tuple.col.Name}}), + (SpacetimeDB.ColumnAttrs){{(int)tuple.attr}} ) """ ) @@ -351,7 +370,8 @@ public ReducerDeclaration(GeneratorAttributeSyntaxContext context) { throw new Exception($"Reducer {method} must return void"); } - if (method.Parameters.FirstOrDefault()?.Type is not INamedTypeSymbol namedType || namedType.Name != "ReducerContext") { + if (method.Parameters.FirstOrDefault()?.Type is not INamedTypeSymbol namedType || namedType.Name != "ReducerContext") + { throw new Exception($"Reducer {method} must have a first argument of type ReducerContext"); } @@ -460,7 +480,7 @@ public void Initialize(IncrementalGeneratorInitializationContext context) // Not really important outside of testing, but for testing // it matters because we commit module-bindings // so they need to match 1:1 between different langs. - var tableViews = tuple.Left.Sort((a, b) => a.Key.Item1.CompareTo(b.Key.Item1)); + var tableViews = tuple.Left.Sort((a, b) => a.Key.viewName.CompareTo(b.Key.viewName)); var addReducers = tuple.Right.Sort((a, b) => a.Key.CompareTo(b.Key)); // Don't generate the FFI boilerplate if there are no tables or reducers. if (tableViews.IsEmpty && addReducers.IsEmpty) @@ -478,12 +498,12 @@ public void Initialize(IncrementalGeneratorInitializationContext context) namespace SpacetimeDB { public sealed class ReducerContext : BaseReducerContext {} - namespace TableViews { - {{string.Join("\n", tableViews.Select(v => v.Value.Item1))}} + namespace Internal.TableHandles { + {{string.Join("\n", tableViews.Select(v => v.Value.view))}} } public sealed class Local { - {{string.Join("\n", tableViews.Select(v => v.Value.Item2))}} + {{string.Join("\n", tableViews.Select(v => v.Value.getter))}} } } @@ -509,7 +529,7 @@ public static void Main() { )}} {{string.Join( "\n", - tableViews.Select(t => $"SpacetimeDB.Internal.Module.RegisterTable<{t.Key.Item2}>();") + tableViews.Select(t => $"SpacetimeDB.Internal.Module.RegisterTable<{t.Key.tableName}>();") )}} } diff --git a/crates/bindings-csharp/Runtime/Attrs.cs b/crates/bindings-csharp/Runtime/Attrs.cs index ae4f062db0..1a05f85bc2 100644 --- a/crates/bindings-csharp/Runtime/Attrs.cs +++ b/crates/bindings-csharp/Runtime/Attrs.cs @@ -23,7 +23,7 @@ public enum ColumnAttrs : byte /// Each attribute instance must have a unique name and will create a SpacetimeDB table. /// /// -[AttributeUsage(AttributeTargets.Struct, AllowMultiple = true)] +[AttributeUsage(AttributeTargets.Struct | AttributeTargets.Class, AllowMultiple = true)] public sealed class TableAttribute : Attribute { /// diff --git a/crates/bindings-csharp/Runtime/Internal/FFI.cs b/crates/bindings-csharp/Runtime/Internal/FFI.cs index 444a90b6c2..800ddf4336 100644 --- a/crates/bindings-csharp/Runtime/Internal/FFI.cs +++ b/crates/bindings-csharp/Runtime/Internal/FFI.cs @@ -169,7 +169,7 @@ out RowIter out_ [LibraryImport(StdbNamespace)] public static partial Errno _row_iter_bsatn_advance( RowIter iter_handle, - [MarshalUsing(CountElementName = nameof(buffer_len))] [Out] byte[] buffer, + [MarshalUsing(CountElementName = nameof(buffer_len))][Out] byte[] buffer, ref uint buffer_len ); diff --git a/crates/bindings-csharp/Runtime/Internal/Module.cs b/crates/bindings-csharp/Runtime/Internal/Module.cs index f3a756b49b..dca50f3994 100644 --- a/crates/bindings-csharp/Runtime/Internal/Module.cs +++ b/crates/bindings-csharp/Runtime/Internal/Module.cs @@ -12,7 +12,8 @@ public RawConstraintDefV8(string tableName, ushort colIndex, string colName, Col ConstraintName: $"ct_{tableName}_{colName}_{attrs}", Constraints: (byte)attrs, Columns: [colIndex] - ) { } + ) + { } } partial class RawModuleDefV8 @@ -99,7 +100,8 @@ public static void RegisterReducer() public static void RegisterTable() where T : ITable, new() { - foreach (var t in T.MakeTableDesc(typeRegistrar)) { + foreach (var t in T.MakeTableDesc(typeRegistrar)) + { moduleDef.RegisterTable(t); } } diff --git a/crates/bindings-csharp/Runtime/LogStopwatch.cs b/crates/bindings-csharp/Runtime/LogStopwatch.cs index 7965b98782..319ab2574d 100644 --- a/crates/bindings-csharp/Runtime/LogStopwatch.cs +++ b/crates/bindings-csharp/Runtime/LogStopwatch.cs @@ -1,8 +1,7 @@ -using System.Text; +namespace SpacetimeDB; +using System.Text; using SpacetimeDB.Internal; -namespace SpacetimeDB; - public sealed class LogStopwatch : IDisposable { private readonly FFI.ConsoleTimerId StopwatchId; diff --git a/modules/sdk-test-connect-disconnect-cs/sdk-test-connect-disconnect-cs.csproj b/modules/sdk-test-connect-disconnect-cs/sdk-test-connect-disconnect-cs.csproj index fbf5b824ad..805df19a72 100644 --- a/modules/sdk-test-connect-disconnect-cs/sdk-test-connect-disconnect-cs.csproj +++ b/modules/sdk-test-connect-disconnect-cs/sdk-test-connect-disconnect-cs.csproj @@ -2,7 +2,6 @@ StdbModule - true net8.0 wasi-wasm enable diff --git a/modules/sdk-test-cs/sdk-test-cs.csproj b/modules/sdk-test-cs/sdk-test-cs.csproj index 25dc32aea8..2b0ba60adf 100644 --- a/modules/sdk-test-cs/sdk-test-cs.csproj +++ b/modules/sdk-test-cs/sdk-test-cs.csproj @@ -2,7 +2,6 @@ StdbModule - true net8.0 wasi-wasm enable diff --git a/modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj b/modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj index dcad219445..b32e62e008 100644 --- a/modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj +++ b/modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj @@ -2,7 +2,6 @@ StdbModule - true net8.0 wasi-wasm enable diff --git a/modules/spacetimedb-quickstart-cs/spacetimedb-quickstart-server-cs.csproj b/modules/spacetimedb-quickstart-cs/spacetimedb-quickstart-server-cs.csproj index 00ef182a30..8f459333e3 100644 --- a/modules/spacetimedb-quickstart-cs/spacetimedb-quickstart-server-cs.csproj +++ b/modules/spacetimedb-quickstart-cs/spacetimedb-quickstart-server-cs.csproj @@ -2,7 +2,6 @@ StdbModule - true net8.0 wasi-wasm enable From 11acf2aad68fff82559096c838e2aea795628017 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Wed, 25 Sep 2024 12:01:51 -0400 Subject: [PATCH 07/27] Review update --- crates/bindings-csharp/BSATN.Runtime/Db.cs | 2 +- .../fixtures/server/server.csproj | 1 + .../server/snapshots/Module#FFI.verified.cs | 39 +- crates/bindings-csharp/Codegen/Module.cs | 20 +- .../Runtime/Internal/ITable.cs | 10 +- crates/bindings-csharp/Runtime/Runtime.cs | 2 +- crates/bindings-csharp/SpacetimeSharpSATS.sln | 24 ++ modules/sdk-test-connect-disconnect-cs/Lib.cs | 6 +- modules/sdk-test-cs/Lib.cs | 388 ++++++------------ modules/sdk-test-multi-cs/Lib.cs | 7 +- modules/spacetimedb-quickstart-cs/Lib.cs | 3 +- 11 files changed, 200 insertions(+), 302 deletions(-) diff --git a/crates/bindings-csharp/BSATN.Runtime/Db.cs b/crates/bindings-csharp/BSATN.Runtime/Db.cs index ede864f654..a1039d3468 100644 --- a/crates/bindings-csharp/BSATN.Runtime/Db.cs +++ b/crates/bindings-csharp/BSATN.Runtime/Db.cs @@ -1,6 +1,6 @@ namespace SpacetimeDB; -public abstract class DbContext +public abstract record DbContext where DbView : class, new() { public readonly DbView Db; diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/server.csproj b/crates/bindings-csharp/Codegen.Tests/fixtures/server/server.csproj index 37f8529367..68c9eadab1 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/server.csproj +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/server.csproj @@ -12,6 +12,7 @@ + diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs index e738171fb3..54ee754738 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs @@ -8,17 +8,20 @@ namespace SpacetimeDB { - public sealed class ReducerContext : BaseReducerContext { } + public sealed record ReducerContext : BaseReducerContext { } namespace Internal.TableHandles { public readonly struct PrivateTable : SpacetimeDB.Internal.ITableView { - static void SpacetimeDB.Internal.ITableView< + static global::PrivateTable SpacetimeDB.Internal.ITableView< PrivateTable, global::PrivateTable - >.ReadGenFields(System.IO.BinaryReader reader, ref global::PrivateTable row) { } + >.ReadGenFields(System.IO.BinaryReader reader, global::PrivateTable row) + { + return row; + } public IEnumerable Iter() => SpacetimeDB.Internal.ITableView.Iter(); @@ -30,22 +33,23 @@ static void SpacetimeDB.Internal.ITableView< predicate ); - public void Insert(ref global::PrivateTable row) => - SpacetimeDB.Internal.ITableView.Insert(ref row); + public void Insert(global::PrivateTable row) => + SpacetimeDB.Internal.ITableView.Insert(row); } public readonly struct PublicTable : SpacetimeDB.Internal.ITableView { - static void SpacetimeDB.Internal.ITableView< + static global::PublicTable SpacetimeDB.Internal.ITableView< PublicTable, global::PublicTable - >.ReadGenFields(System.IO.BinaryReader reader, ref global::PublicTable row) + >.ReadGenFields(System.IO.BinaryReader reader, global::PublicTable row) { if (row.Id == default) { row.Id = global::PublicTable.BSATN.Id.Read(reader); } + return row; } public IEnumerable Iter() => @@ -55,8 +59,8 @@ static void SpacetimeDB.Internal.ITableView< System.Linq.Expressions.Expression> predicate ) => SpacetimeDB.Internal.ITableView.Query(predicate); - public void Insert(ref global::PublicTable row) => - SpacetimeDB.Internal.ITableView.Insert(ref row); + public void Insert(global::PublicTable row) => + SpacetimeDB.Internal.ITableView.Insert(row); public IEnumerable FilterById(int Id) => SpacetimeDB @@ -79,14 +83,14 @@ public bool DeleteById(int Id) => ) .Delete(); - public bool UpdateById(int Id, ref global::PublicTable @this) => + public bool UpdateById(int Id, global::PublicTable @this) => SpacetimeDB .Internal.ITableView.ColEq.Where( 0, Id, global::PublicTable.BSATN.Id ) - .Update(ref @this); + .Update(@this); public IEnumerable FilterByByteField(byte ByteField) => SpacetimeDB @@ -262,10 +266,10 @@ SpacetimeDB.Address AddressField public readonly struct SendMessageTimer : SpacetimeDB.Internal.ITableView { - static void SpacetimeDB.Internal.ITableView< + static global::Timers.SendMessageTimer SpacetimeDB.Internal.ITableView< SendMessageTimer, global::Timers.SendMessageTimer - >.ReadGenFields(System.IO.BinaryReader reader, ref global::Timers.SendMessageTimer row) + >.ReadGenFields(System.IO.BinaryReader reader, global::Timers.SendMessageTimer row) { if (row.ScheduledId == default) { @@ -273,6 +277,7 @@ static void SpacetimeDB.Internal.ITableView< reader ); } + return row; } public IEnumerable Iter() => @@ -291,11 +296,11 @@ static void SpacetimeDB.Internal.ITableView< global::Timers.SendMessageTimer >.Query(predicate); - public void Insert(ref global::Timers.SendMessageTimer row) => + public void Insert(global::Timers.SendMessageTimer row) => SpacetimeDB.Internal.ITableView< SendMessageTimer, global::Timers.SendMessageTimer - >.Insert(ref row); + >.Insert(row); public IEnumerable FilterByText(string Text) => SpacetimeDB @@ -330,14 +335,14 @@ public bool DeleteByScheduledId(ulong ScheduledId) => public bool UpdateByScheduledId( ulong ScheduledId, - ref global::Timers.SendMessageTimer @this + global::Timers.SendMessageTimer @this ) => SpacetimeDB .Internal.ITableView< SendMessageTimer, global::Timers.SendMessageTimer >.ColEq.Where(1, ScheduledId, global::Timers.SendMessageTimer.BSATN.ScheduledId) - .Update(ref @this); + .Update(@this); } } diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index 82969aaf4b..c87fea2776 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -21,8 +21,7 @@ bool isEquatable ) : base(name, type, typeInfo) { - (string?, ColumnAttrs)[] x = [(default(string), attrs)]; - Attrs = new(x.ToImmutableArray()); + Attrs = new(ImmutableArray.Create((default(string), attrs))); IsEquatable = isEquatable; FullTableName = tableName; } @@ -34,8 +33,8 @@ public ColumnDeclaration(string tableName, IFieldSymbol field) Attrs = new(field .GetAttributes() - .Select(a => (a.NamedArguments.FirstOrDefault(a => a.Key == "Table").Value.Value as string, - a.AttributeClass?.ToString() switch + .Select(a => (table: a.NamedArguments.FirstOrDefault(a => a.Key == "Table").Value.Value as string, + attr: a.AttributeClass?.ToString() switch { "SpacetimeDB.AutoIncAttribute" => ColumnAttrs.AutoInc, "SpacetimeDB.PrimaryKeyAttribute" => ColumnAttrs.PrimaryKey, @@ -43,6 +42,7 @@ public ColumnDeclaration(string tableName, IFieldSymbol field) "SpacetimeDB.IndexedAttribute" => ColumnAttrs.Indexed, _ => ColumnAttrs.UnSet, })) + .Where(a => a.attr != ColumnAttrs.UnSet) .ToImmutableArray()); var type = field.Type; @@ -169,7 +169,6 @@ or Accessibility.NotApplicable }; Views = new(context.Attributes - .Where(a => a.AttributeClass?.ToDisplayString() == "SpacetimeDB.TableAttribute") .Select(a => new TableView(this, a)) .ToImmutableArray()); @@ -223,8 +222,8 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) public bool DeleteBy{f.Name}({f.Type} {f.Name}) => {colEqWhere}.Delete(); - public bool UpdateBy{f.Name}({f.Type} {f.Name}, ref {globalName} @this) => - {colEqWhere}.Update(ref @this); + public bool UpdateBy{f.Name}({f.Type} {f.Name}, {globalName} @this) => + {colEqWhere}.Update(@this); """; } } @@ -242,7 +241,7 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) var iTable = $"SpacetimeDB.Internal.ITableView<{v.Name}, {globalName}>"; yield return new((v.Name, globalName), ($$""" {{Visibility}} readonly struct {{v.Name}} : {{iTable}} { - static void {{iTable}}.ReadGenFields(System.IO.BinaryReader reader, ref {{globalName}} row) { + static {{globalName}} {{iTable}}.ReadGenFields(System.IO.BinaryReader reader, {{globalName}} row) { {{string.Join( "\n", autoIncFields.Select(name => @@ -254,10 +253,11 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) """ ) )}} + return row; } public IEnumerable<{{globalName}}> Iter() => {{iTable}}.Iter(); public IEnumerable<{{globalName}}> Query(System.Linq.Expressions.Expression> predicate) => {{iTable}}.Query(predicate); - public void Insert(ref {{globalName}} row) => {{iTable}}.Insert(ref row); + public void Insert({{globalName}} row) => {{iTable}}.Insert(row); {{string.Join("\n", GenerateViewFilters(v.Name, iTable))}} } """, $"{Visibility} Internal.TableHandles.{v.Name} {v.Name} => new();")); @@ -496,7 +496,7 @@ public void Initialize(IncrementalGeneratorInitializationContext context) using System.Runtime.InteropServices; namespace SpacetimeDB { - public sealed class ReducerContext : BaseReducerContext {} + public sealed record ReducerContext : BaseReducerContext {} namespace Internal.TableHandles { {{string.Join("\n", tableViews.Select(v => v.Value.view))}} diff --git a/crates/bindings-csharp/Runtime/Internal/ITable.cs b/crates/bindings-csharp/Runtime/Internal/ITable.cs index 7e54c050c2..f5d820ee34 100644 --- a/crates/bindings-csharp/Runtime/Internal/ITable.cs +++ b/crates/bindings-csharp/Runtime/Internal/ITable.cs @@ -16,7 +16,7 @@ public interface ITableView where View : ITableView where T : ITable, new() { - static abstract void ReadGenFields(BinaryReader reader, ref T row); + static abstract T ReadGenFields(BinaryReader reader, T row); // These are static helpers that codegen can use. private abstract class RawTableIterBase @@ -154,7 +154,7 @@ protected override void IterStart(out FFI.RowIter handle) => public static IEnumerable Query(Expression> query) => new RawTableIterFiltered(tableId, filter.Value.Compile(query)).Parse(); - protected static void Insert(ref T row) + protected static T Insert(T row) { // Insert the row. var bytes = IStructuralReadWrite.ToBytes(row); @@ -164,7 +164,7 @@ protected static void Insert(ref T row) // Write back any generated column values. using var stream = new MemoryStream(bytes, 0, (int)bytes_len); using var reader = new BinaryReader(stream); - View.ReadGenFields(reader, ref row); + return View.ReadGenFields(reader, row); } protected readonly ref struct ColEq @@ -194,14 +194,14 @@ public bool Delete() return out_ > 0; } - public bool Update(ref T row) + public bool Update(T row) { // Just like in Rust bindings, updating is just deleting and inserting for now. if (!Delete()) { return false; } - Insert(ref row); + Insert(row); return true; } } diff --git a/crates/bindings-csharp/Runtime/Runtime.cs b/crates/bindings-csharp/Runtime/Runtime.cs index f28680b3e3..e15cf5c10d 100644 --- a/crates/bindings-csharp/Runtime/Runtime.cs +++ b/crates/bindings-csharp/Runtime/Runtime.cs @@ -58,7 +58,7 @@ public AlgebraicType GetAlgebraicType(ITypeRegistrar registrar) => } } -public abstract class BaseReducerContext : DbContext, IReducerContext +public abstract record BaseReducerContext : DbContext, IReducerContext where DbView : class, new() { public Identity Sender => Runtime.SenderIdentity!; diff --git a/crates/bindings-csharp/SpacetimeSharpSATS.sln b/crates/bindings-csharp/SpacetimeSharpSATS.sln index f76a5c6ce3..0cc2abf8a5 100644 --- a/crates/bindings-csharp/SpacetimeSharpSATS.sln +++ b/crates/bindings-csharp/SpacetimeSharpSATS.sln @@ -18,6 +18,14 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "config", "config", "{12907A .editorconfig = .editorconfig EndProjectSection EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "sdk-test-connect-disconnect-cs", "..\..\modules\sdk-test-connect-disconnect-cs\sdk-test-connect-disconnect-cs.csproj", "{5393711C-44B0-4752-B8D0-852C73D6866F}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "sdk-test-cs", "..\..\modules\sdk-test-cs\sdk-test-cs.csproj", "{40F1C615-EDD9-463F-A012-B232F6710FA5}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "spacetimedb-quickstart-server-cs", "..\..\modules\spacetimedb-quickstart-cs\spacetimedb-quickstart-server-cs.csproj", "{FDACD960-168E-44F9-B036-2E29EA391BE7}" +EndProject +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "sdk-test-multi-cs", "..\..\modules\sdk-test-multi-cs\sdk-test-multi-cs.csproj", "{960384A9-D78F-4C07-986A-1D1F3846AEBE}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -44,6 +52,22 @@ Global {2C282EBD-8E37-4F4C-8EE1-E91E21E75FEE}.Debug|Any CPU.Build.0 = Debug|Any CPU {2C282EBD-8E37-4F4C-8EE1-E91E21E75FEE}.Release|Any CPU.ActiveCfg = Release|Any CPU {2C282EBD-8E37-4F4C-8EE1-E91E21E75FEE}.Release|Any CPU.Build.0 = Release|Any CPU + {5393711C-44B0-4752-B8D0-852C73D6866F}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {5393711C-44B0-4752-B8D0-852C73D6866F}.Debug|Any CPU.Build.0 = Debug|Any CPU + {5393711C-44B0-4752-B8D0-852C73D6866F}.Release|Any CPU.ActiveCfg = Release|Any CPU + {5393711C-44B0-4752-B8D0-852C73D6866F}.Release|Any CPU.Build.0 = Release|Any CPU + {40F1C615-EDD9-463F-A012-B232F6710FA5}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {40F1C615-EDD9-463F-A012-B232F6710FA5}.Debug|Any CPU.Build.0 = Debug|Any CPU + {40F1C615-EDD9-463F-A012-B232F6710FA5}.Release|Any CPU.ActiveCfg = Release|Any CPU + {40F1C615-EDD9-463F-A012-B232F6710FA5}.Release|Any CPU.Build.0 = Release|Any CPU + {FDACD960-168E-44F9-B036-2E29EA391BE7}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {FDACD960-168E-44F9-B036-2E29EA391BE7}.Debug|Any CPU.Build.0 = Debug|Any CPU + {FDACD960-168E-44F9-B036-2E29EA391BE7}.Release|Any CPU.ActiveCfg = Release|Any CPU + {FDACD960-168E-44F9-B036-2E29EA391BE7}.Release|Any CPU.Build.0 = Release|Any CPU + {960384A9-D78F-4C07-986A-1D1F3846AEBE}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {960384A9-D78F-4C07-986A-1D1F3846AEBE}.Debug|Any CPU.Build.0 = Debug|Any CPU + {960384A9-D78F-4C07-986A-1D1F3846AEBE}.Release|Any CPU.ActiveCfg = Release|Any CPU + {960384A9-D78F-4C07-986A-1D1F3846AEBE}.Release|Any CPU.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE diff --git a/modules/sdk-test-connect-disconnect-cs/Lib.cs b/modules/sdk-test-connect-disconnect-cs/Lib.cs index b5f700a7eb..054906ed9d 100644 --- a/modules/sdk-test-connect-disconnect-cs/Lib.cs +++ b/modules/sdk-test-connect-disconnect-cs/Lib.cs @@ -17,14 +17,12 @@ static partial class Module [SpacetimeDB.Reducer(ReducerKind.Connect)] public static void OnConnect(ReducerContext ctx) { - var row = new Connected { identity = ctx.Sender }; - ctx.Db.Connected.Insert(ref row); + ctx.Db.Connected.Insert(new Connected { identity = ctx.Sender }); } [SpacetimeDB.Reducer(ReducerKind.Disconnect)] public static void OnDisconnect(ReducerContext ctx) { - var row = new Disconnected { identity = ctx.Sender }; - ctx.Db.Disconnected.Insert(ref row); + ctx.Db.Disconnected.Insert(new Disconnected { identity = ctx.Sender }); } } diff --git a/modules/sdk-test-cs/Lib.cs b/modules/sdk-test-cs/Lib.cs index 918cf8c783..bc5e349526 100644 --- a/modules/sdk-test-cs/Lib.cs +++ b/modules/sdk-test-cs/Lib.cs @@ -103,8 +103,7 @@ public partial struct OneU8 [SpacetimeDB.Reducer] public static void insert_one_u8(ReducerContext ctx, byte n) { - var row = new OneU8 { n = n }; - ctx.Db.OneU8.Insert(ref row); + ctx.Db.OneU8.Insert(new OneU8 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -116,8 +115,7 @@ public partial struct OneU16 [SpacetimeDB.Reducer] public static void insert_one_u16(ReducerContext ctx, ushort n) { - var row = new OneU16 { n = n }; - ctx.Db.OneU16.Insert(ref row); + ctx.Db.OneU16.Insert(new OneU16 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -129,8 +127,7 @@ public partial struct OneU32 [SpacetimeDB.Reducer] public static void insert_one_u32(ReducerContext ctx, uint n) { - var row = new OneU32 { n = n }; - ctx.Db.OneU32.Insert(ref row); + ctx.Db.OneU32.Insert(new OneU32 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -142,8 +139,7 @@ public partial struct OneU64 [SpacetimeDB.Reducer] public static void insert_one_u64(ReducerContext ctx, ulong n) { - var row = new OneU64 { n = n }; - ctx.Db.OneU64.Insert(ref row); + ctx.Db.OneU64.Insert(new OneU64 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -155,8 +151,7 @@ public partial struct OneU128 [SpacetimeDB.Reducer] public static void insert_one_u128(ReducerContext ctx, U128 n) { - var row = new OneU128 { n = n }; - ctx.Db.OneU128.Insert(ref row); + ctx.Db.OneU128.Insert(new OneU128 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -168,8 +163,7 @@ public partial struct OneU256 [SpacetimeDB.Reducer] public static void insert_one_u256(ReducerContext ctx, U256 n) { - var row = new OneU256 { n = n }; - ctx.Db.OneU256.Insert(ref row); + ctx.Db.OneU256.Insert(new OneU256 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -181,8 +175,7 @@ public partial struct OneI8 [SpacetimeDB.Reducer] public static void insert_one_i8(ReducerContext ctx, sbyte n) { - var row = new OneI8 { n = n }; - ctx.Db.OneI8.Insert(ref row); + ctx.Db.OneI8.Insert(new OneI8 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -194,8 +187,7 @@ public partial struct OneI16 [SpacetimeDB.Reducer] public static void insert_one_i16(ReducerContext ctx, short n) { - var row = new OneI16 { n = n }; - ctx.Db.OneI16.Insert(ref row); + ctx.Db.OneI16.Insert(new OneI16 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -207,8 +199,7 @@ public partial struct OneI32 [SpacetimeDB.Reducer] public static void insert_one_i32(ReducerContext ctx, int n) { - var row = new OneI32 { n = n }; - ctx.Db.OneI32.Insert(ref row); + ctx.Db.OneI32.Insert(new OneI32 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -220,8 +211,7 @@ public partial struct OneI64 [SpacetimeDB.Reducer] public static void insert_one_i64(ReducerContext ctx, long n) { - var row = new OneI64 { n = n }; - ctx.Db.OneI64.Insert(ref row); + ctx.Db.OneI64.Insert(new OneI64 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -233,8 +223,7 @@ public partial struct OneI128 [SpacetimeDB.Reducer] public static void insert_one_i128(ReducerContext ctx, I128 n) { - var row = new OneI128 { n = n }; - ctx.Db.OneI128.Insert(ref row); + ctx.Db.OneI128.Insert(new OneI128 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -246,8 +235,7 @@ public partial struct OneI256 [SpacetimeDB.Reducer] public static void insert_one_i256(ReducerContext ctx, I256 n) { - var row = new OneI256 { n = n }; - ctx.Db.OneI256.Insert(ref row); + ctx.Db.OneI256.Insert(new OneI256 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -259,8 +247,7 @@ public partial struct OneBool [SpacetimeDB.Reducer] public static void insert_one_bool(ReducerContext ctx, bool b) { - var row = new OneBool { b = b }; - ctx.Db.OneBool.Insert(ref row); + ctx.Db.OneBool.Insert(new OneBool { b = b }); } [SpacetimeDB.Table(Public = true)] @@ -272,8 +259,7 @@ public partial struct OneF32 [SpacetimeDB.Reducer] public static void insert_one_f32(ReducerContext ctx, float f) { - var row = new OneF32 { f = f }; - ctx.Db.OneF32.Insert(ref row); + ctx.Db.OneF32.Insert(new OneF32 { f = f }); } [SpacetimeDB.Table(Public = true)] @@ -285,8 +271,7 @@ public partial struct OneF64 [SpacetimeDB.Reducer] public static void insert_one_f64(ReducerContext ctx, double f) { - var row = new OneF64 { f = f }; - ctx.Db.OneF64.Insert(ref row); + ctx.Db.OneF64.Insert(new OneF64 { f = f }); } [SpacetimeDB.Table(Public = true)] @@ -298,8 +283,7 @@ public partial struct OneString [SpacetimeDB.Reducer] public static void insert_one_string(ReducerContext ctx, string s) { - var row = new OneString { s = s }; - ctx.Db.OneString.Insert(ref row); + ctx.Db.OneString.Insert(new OneString { s = s }); } [SpacetimeDB.Table(Public = true)] @@ -311,8 +295,7 @@ public partial struct OneIdentity [SpacetimeDB.Reducer] public static void insert_one_identity(ReducerContext ctx, Identity i) { - var row = new OneIdentity { i = i }; - ctx.Db.OneIdentity.Insert(ref row); + ctx.Db.OneIdentity.Insert(new OneIdentity { i = i }); } [SpacetimeDB.Table(Public = true)] @@ -324,8 +307,7 @@ public partial struct OneAddress [SpacetimeDB.Reducer] public static void insert_one_address(ReducerContext ctx, Address a) { - var row = new OneAddress { a = a }; - ctx.Db.OneAddress.Insert(ref row); + ctx.Db.OneAddress.Insert(new OneAddress { a = a }); } [SpacetimeDB.Table(Public = true)] @@ -337,8 +319,7 @@ public partial struct OneSimpleEnum [SpacetimeDB.Reducer] public static void insert_one_simple_enum(ReducerContext ctx, SimpleEnum e) { - var row = new OneSimpleEnum { e = e }; - ctx.Db.OneSimpleEnum.Insert(ref row); + ctx.Db.OneSimpleEnum.Insert(new OneSimpleEnum { e = e }); } [SpacetimeDB.Table(Public = true)] @@ -350,8 +331,7 @@ public partial struct OneEnumWithPayload [SpacetimeDB.Reducer] public static void insert_one_enum_with_payload(ReducerContext ctx, EnumWithPayload e) { - var row = new OneEnumWithPayload { e = e }; - ctx.Db.OneEnumWithPayload.Insert(ref row); + ctx.Db.OneEnumWithPayload.Insert(new OneEnumWithPayload { e = e }); } [SpacetimeDB.Table(Public = true)] @@ -363,8 +343,7 @@ public partial struct OneUnitStruct [SpacetimeDB.Reducer] public static void insert_one_unit_struct(ReducerContext ctx, UnitStruct s) { - var row = new OneUnitStruct { s = s }; - ctx.Db.OneUnitStruct.Insert(ref row); + ctx.Db.OneUnitStruct.Insert(new OneUnitStruct { s = s }); } [SpacetimeDB.Table(Public = true)] @@ -376,8 +355,7 @@ public partial struct OneByteStruct [SpacetimeDB.Reducer] public static void insert_one_byte_struct(ReducerContext ctx, ByteStruct s) { - var row = new OneByteStruct { s = s }; - ctx.Db.OneByteStruct.Insert(ref row); + ctx.Db.OneByteStruct.Insert(new OneByteStruct { s = s }); } [SpacetimeDB.Table(Public = true)] @@ -389,8 +367,7 @@ public partial struct OneEveryPrimitiveStruct [SpacetimeDB.Reducer] public static void insert_one_every_primitive_struct(ReducerContext ctx, EveryPrimitiveStruct s) { - var row = new OneEveryPrimitiveStruct { s = s }; - ctx.Db.OneEveryPrimitiveStruct.Insert(ref row); + ctx.Db.OneEveryPrimitiveStruct.Insert(new OneEveryPrimitiveStruct { s = s }); } [SpacetimeDB.Table(Public = true)] @@ -402,8 +379,7 @@ public partial struct OneEveryVecStruct [SpacetimeDB.Reducer] public static void insert_one_every_vec_struct(ReducerContext ctx, EveryVecStruct s) { - var row = new OneEveryVecStruct { s = s }; - ctx.Db.OneEveryVecStruct.Insert(ref row); + ctx.Db.OneEveryVecStruct.Insert(new OneEveryVecStruct { s = s }); } [SpacetimeDB.Table(Public = true)] @@ -415,8 +391,7 @@ public partial struct VecU8 [SpacetimeDB.Reducer] public static void insert_vec_u8(ReducerContext ctx, List n) { - var row = new VecU8 { n = n }; - ctx.Db.VecU8.Insert(ref row); + ctx.Db.VecU8.Insert(new VecU8 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -428,8 +403,7 @@ public partial struct VecU16 [SpacetimeDB.Reducer] public static void insert_vec_u16(ReducerContext ctx, List n) { - var row = new VecU16 { n = n }; - ctx.Db.VecU16.Insert(ref row); + ctx.Db.VecU16.Insert(new VecU16 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -441,8 +415,7 @@ public partial struct VecU32 [SpacetimeDB.Reducer] public static void insert_vec_u32(ReducerContext ctx, List n) { - var row = new VecU32 { n = n }; - ctx.Db.VecU32.Insert(ref row); + ctx.Db.VecU32.Insert(new VecU32 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -454,8 +427,7 @@ public partial struct VecU64 [SpacetimeDB.Reducer] public static void insert_vec_u64(ReducerContext ctx, List n) { - var row = new VecU64 { n = n }; - ctx.Db.VecU64.Insert(ref row); + ctx.Db.VecU64.Insert(new VecU64 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -467,8 +439,7 @@ public partial struct VecU128 [SpacetimeDB.Reducer] public static void insert_vec_u128(ReducerContext ctx, List n) { - var row = new VecU128 { n = n }; - ctx.Db.VecU128.Insert(ref row); + ctx.Db.VecU128.Insert(new VecU128 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -480,8 +451,7 @@ public partial struct VecU256 [SpacetimeDB.Reducer] public static void insert_vec_u256(ReducerContext ctx, List n) { - var row = new VecU256 { n = n }; - ctx.Db.VecU256.Insert(ref row); + ctx.Db.VecU256.Insert(new VecU256 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -493,8 +463,7 @@ public partial struct VecI8 [SpacetimeDB.Reducer] public static void insert_vec_i8(ReducerContext ctx, List n) { - var row = new VecI8 { n = n }; - ctx.Db.VecI8.Insert(ref row); + ctx.Db.VecI8.Insert(new VecI8 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -506,8 +475,7 @@ public partial struct VecI16 [SpacetimeDB.Reducer] public static void insert_vec_i16(ReducerContext ctx, List n) { - var row = new VecI16 { n = n }; - ctx.Db.VecI16.Insert(ref row); + ctx.Db.VecI16.Insert(new VecI16 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -519,8 +487,7 @@ public partial struct VecI32 [SpacetimeDB.Reducer] public static void insert_vec_i32(ReducerContext ctx, List n) { - var row = new VecI32 { n = n }; - ctx.Db.VecI32.Insert(ref row); + ctx.Db.VecI32.Insert(new VecI32 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -532,8 +499,7 @@ public partial struct VecI64 [SpacetimeDB.Reducer] public static void insert_vec_i64(ReducerContext ctx, List n) { - var row = new VecI64 { n = n }; - ctx.Db.VecI64.Insert(ref row); + ctx.Db.VecI64.Insert(new VecI64 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -545,8 +511,7 @@ public partial struct VecI128 [SpacetimeDB.Reducer] public static void insert_vec_i128(ReducerContext ctx, List n) { - var row = new VecI128 { n = n }; - ctx.Db.VecI128.Insert(ref row); + ctx.Db.VecI128.Insert(new VecI128 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -558,8 +523,7 @@ public partial struct VecI256 [SpacetimeDB.Reducer] public static void insert_vec_i256(ReducerContext ctx, List n) { - var row = new VecI256 { n = n }; - ctx.Db.VecI256.Insert(ref row); + ctx.Db.VecI256.Insert(new VecI256 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -571,8 +535,7 @@ public partial struct VecBool [SpacetimeDB.Reducer] public static void insert_vec_bool(ReducerContext ctx, List b) { - var row = new VecBool { b = b }; - ctx.Db.VecBool.Insert(ref row); + ctx.Db.VecBool.Insert(new VecBool { b = b }); } [SpacetimeDB.Table(Public = true)] @@ -584,8 +547,7 @@ public partial struct VecF32 [SpacetimeDB.Reducer] public static void insert_vec_f32(ReducerContext ctx, List f) { - var row = new VecF32 { f = f }; - ctx.Db.VecF32.Insert(ref row); + ctx.Db.VecF32.Insert(new VecF32 { f = f }); } [SpacetimeDB.Table(Public = true)] @@ -597,8 +559,7 @@ public partial struct VecF64 [SpacetimeDB.Reducer] public static void insert_vec_f64(ReducerContext ctx, List f) { - var row = new VecF64 { f = f }; - ctx.Db.VecF64.Insert(ref row); + ctx.Db.VecF64.Insert(new VecF64 { f = f }); } [SpacetimeDB.Table(Public = true)] @@ -610,8 +571,7 @@ public partial struct VecString [SpacetimeDB.Reducer] public static void insert_vec_string(ReducerContext ctx, List s) { - var row = new VecString { s = s }; - ctx.Db.VecString.Insert(ref row); + ctx.Db.VecString.Insert(new VecString { s = s }); } [SpacetimeDB.Table(Public = true)] @@ -623,8 +583,7 @@ public partial struct VecIdentity [SpacetimeDB.Reducer] public static void insert_vec_identity(ReducerContext ctx, List i) { - var row = new VecIdentity { i = i }; - ctx.Db.VecIdentity.Insert(ref row); + ctx.Db.VecIdentity.Insert(new VecIdentity { i = i }); } [SpacetimeDB.Table(Public = true)] @@ -636,8 +595,7 @@ public partial struct VecAddress [SpacetimeDB.Reducer] public static void insert_vec_address(ReducerContext ctx, List
a) { - var row = new VecAddress { a = a }; - ctx.Db.VecAddress.Insert(ref row); + ctx.Db.VecAddress.Insert(new VecAddress { a = a }); } [SpacetimeDB.Table(Public = true)] @@ -649,8 +607,7 @@ public partial struct VecSimpleEnum [SpacetimeDB.Reducer] public static void insert_vec_simple_enum(ReducerContext ctx, List e) { - var row = new VecSimpleEnum { e = e }; - ctx.Db.VecSimpleEnum.Insert(ref row); + ctx.Db.VecSimpleEnum.Insert(new VecSimpleEnum { e = e }); } [SpacetimeDB.Table(Public = true)] @@ -662,8 +619,7 @@ public partial struct VecEnumWithPayload [SpacetimeDB.Reducer] public static void insert_vec_enum_with_payload(ReducerContext ctx, List e) { - var row = new VecEnumWithPayload { e = e }; - ctx.Db.VecEnumWithPayload.Insert(ref row); + ctx.Db.VecEnumWithPayload.Insert(new VecEnumWithPayload { e = e }); } [SpacetimeDB.Table(Public = true)] @@ -675,8 +631,7 @@ public partial struct VecUnitStruct [SpacetimeDB.Reducer] public static void insert_vec_unit_struct(ReducerContext ctx, List s) { - var row = new VecUnitStruct { s = s }; - ctx.Db.VecUnitStruct.Insert(ref row); + ctx.Db.VecUnitStruct.Insert(new VecUnitStruct { s = s }); } [SpacetimeDB.Table(Public = true)] @@ -688,8 +643,7 @@ public partial struct VecByteStruct [SpacetimeDB.Reducer] public static void insert_vec_byte_struct(ReducerContext ctx, List s) { - var row = new VecByteStruct { s = s }; - ctx.Db.VecByteStruct.Insert(ref row); + ctx.Db.VecByteStruct.Insert(new VecByteStruct { s = s }); } [SpacetimeDB.Table(Public = true)] @@ -701,8 +655,7 @@ public partial struct VecEveryPrimitiveStruct [SpacetimeDB.Reducer] public static void insert_vec_every_primitive_struct(ReducerContext ctx, List s) { - var row = new VecEveryPrimitiveStruct { s = s }; - ctx.Db.VecEveryPrimitiveStruct.Insert(ref row); + ctx.Db.VecEveryPrimitiveStruct.Insert(new VecEveryPrimitiveStruct { s = s }); } [SpacetimeDB.Table(Public = true)] @@ -714,8 +667,7 @@ public partial struct VecEveryVecStruct [SpacetimeDB.Reducer] public static void insert_vec_every_vec_struct(ReducerContext ctx, List s) { - var row = new VecEveryVecStruct { s = s }; - ctx.Db.VecEveryVecStruct.Insert(ref row); + ctx.Db.VecEveryVecStruct.Insert(new VecEveryVecStruct { s = s }); } [SpacetimeDB.Table(Public = true)] @@ -727,8 +679,7 @@ public partial struct OptionI32 [SpacetimeDB.Reducer] public static void insert_option_i32(ReducerContext ctx, int? n) { - var row = new OptionI32 { n = n }; - ctx.Db.OptionI32.Insert(ref row); + ctx.Db.OptionI32.Insert(new OptionI32 { n = n }); } [SpacetimeDB.Table(Public = true)] @@ -740,8 +691,7 @@ public partial struct OptionString [SpacetimeDB.Reducer] public static void insert_option_string(ReducerContext ctx, string? s) { - var row = new OptionString { s = s }; - ctx.Db.OptionString.Insert(ref row); + ctx.Db.OptionString.Insert(new OptionString { s = s }); } [SpacetimeDB.Table(Public = true)] @@ -753,8 +703,7 @@ public partial struct OptionIdentity [SpacetimeDB.Reducer] public static void insert_option_identity(ReducerContext ctx, Identity? i) { - var row = new OptionIdentity { i = i }; - ctx.Db.OptionIdentity.Insert(ref row); + ctx.Db.OptionIdentity.Insert(new OptionIdentity { i = i }); } [SpacetimeDB.Table(Public = true)] @@ -766,8 +715,7 @@ public partial struct OptionSimpleEnum [SpacetimeDB.Reducer] public static void insert_option_simple_enum(ReducerContext ctx, SimpleEnum? e) { - var row = new OptionSimpleEnum { e = e }; - ctx.Db.OptionSimpleEnum.Insert(ref row); + ctx.Db.OptionSimpleEnum.Insert(new OptionSimpleEnum { e = e }); } [SpacetimeDB.Table(Public = true)] @@ -779,8 +727,7 @@ public partial struct OptionEveryPrimitiveStruct [SpacetimeDB.Reducer] public static void insert_option_every_primitive_struct(ReducerContext ctx, EveryPrimitiveStruct? s) { - var row = new OptionEveryPrimitiveStruct { s = s }; - ctx.Db.OptionEveryPrimitiveStruct.Insert(ref row); + ctx.Db.OptionEveryPrimitiveStruct.Insert(new OptionEveryPrimitiveStruct { s = s }); } [SpacetimeDB.Table(Public = true)] @@ -792,8 +739,7 @@ public partial struct OptionVecOptionI32 [SpacetimeDB.Reducer] public static void insert_option_vec_option_i32(ReducerContext ctx, List? v) { - var row = new OptionVecOptionI32 { v = v }; - ctx.Db.OptionVecOptionI32.Insert(ref row); + ctx.Db.OptionVecOptionI32.Insert(new OptionVecOptionI32 { v = v }); } [SpacetimeDB.Table(Public = true)] @@ -807,16 +753,14 @@ public partial struct UniqueU8 [SpacetimeDB.Reducer] public static void insert_unique_u8(ReducerContext ctx, byte n, int data) { - var row = new UniqueU8 { n = n, data = data }; - ctx.Db.UniqueU8.Insert(ref row); + ctx.Db.UniqueU8.Insert(new UniqueU8 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_u8(ReducerContext ctx, byte n, int data) { var key = n; - var row = new UniqueU8 { n = n, data = data }; - ctx.Db.UniqueU8.UpdateByn(key, ref row); + ctx.Db.UniqueU8.UpdateByn(key, new UniqueU8 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -836,16 +780,14 @@ public partial struct UniqueU16 [SpacetimeDB.Reducer] public static void insert_unique_u16(ReducerContext ctx, ushort n, int data) { - var row = new UniqueU16 { n = n, data = data }; - ctx.Db.UniqueU16.Insert(ref row); + ctx.Db.UniqueU16.Insert(new UniqueU16 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_u16(ReducerContext ctx, ushort n, int data) { var key = n; - var row = new UniqueU16 { n = n, data = data }; - ctx.Db.UniqueU16.UpdateByn(key, ref row); + ctx.Db.UniqueU16.UpdateByn(key, new UniqueU16 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -865,16 +807,14 @@ public partial struct UniqueU32 [SpacetimeDB.Reducer] public static void insert_unique_u32(ReducerContext ctx, uint n, int data) { - var row = new UniqueU32 { n = n, data = data }; - ctx.Db.UniqueU32.Insert(ref row); + ctx.Db.UniqueU32.Insert(new UniqueU32 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_u32(ReducerContext ctx, uint n, int data) { var key = n; - var row = new UniqueU32 { n = n, data = data }; - ctx.Db.UniqueU32.UpdateByn(key, ref row); + ctx.Db.UniqueU32.UpdateByn(key, new UniqueU32 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -894,16 +834,14 @@ public partial struct UniqueU64 [SpacetimeDB.Reducer] public static void insert_unique_u64(ReducerContext ctx, ulong n, int data) { - var row = new UniqueU64 { n = n, data = data }; - ctx.Db.UniqueU64.Insert(ref row); + ctx.Db.UniqueU64.Insert(new UniqueU64 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_u64(ReducerContext ctx, ulong n, int data) { var key = n; - var row = new UniqueU64 { n = n, data = data }; - ctx.Db.UniqueU64.UpdateByn(key, ref row); + ctx.Db.UniqueU64.UpdateByn(key, new UniqueU64 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -923,16 +861,14 @@ public partial struct UniqueU128 [SpacetimeDB.Reducer] public static void insert_unique_u128(ReducerContext ctx, U128 n, int data) { - var row = new UniqueU128 { n = n, data = data }; - ctx.Db.UniqueU128.Insert(ref row); + ctx.Db.UniqueU128.Insert(new UniqueU128 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_u128(ReducerContext ctx, U128 n, int data) { var key = n; - var row = new UniqueU128 { n = n, data = data }; - ctx.Db.UniqueU128.UpdateByn(key, ref row); + ctx.Db.UniqueU128.UpdateByn(key, new UniqueU128 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -952,16 +888,14 @@ public partial struct UniqueU256 [SpacetimeDB.Reducer] public static void insert_unique_u256(ReducerContext ctx, U256 n, int data) { - var row = new UniqueU256 { n = n, data = data }; - ctx.Db.UniqueU256.Insert(ref row); + ctx.Db.UniqueU256.Insert(new UniqueU256 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_u256(ReducerContext ctx, U256 n, int data) { var key = n; - var row = new UniqueU256 { n = n, data = data }; - ctx.Db.UniqueU256.UpdateByn(key, ref row); + ctx.Db.UniqueU256.UpdateByn(key, new UniqueU256 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -981,16 +915,14 @@ public partial struct UniqueI8 [SpacetimeDB.Reducer] public static void insert_unique_i8(ReducerContext ctx, sbyte n, int data) { - var row = new UniqueI8 { n = n, data = data }; - ctx.Db.UniqueI8.Insert(ref row); + ctx.Db.UniqueI8.Insert(new UniqueI8 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_i8(ReducerContext ctx, sbyte n, int data) { var key = n; - var row = new UniqueI8 { n = n, data = data }; - ctx.Db.UniqueI8.UpdateByn(key, ref row); + ctx.Db.UniqueI8.UpdateByn(key, new UniqueI8 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1010,16 +942,14 @@ public partial struct UniqueI16 [SpacetimeDB.Reducer] public static void insert_unique_i16(ReducerContext ctx, short n, int data) { - var row = new UniqueI16 { n = n, data = data }; - ctx.Db.UniqueI16.Insert(ref row); + ctx.Db.UniqueI16.Insert(new UniqueI16 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_i16(ReducerContext ctx, short n, int data) { var key = n; - var row = new UniqueI16 { n = n, data = data }; - ctx.Db.UniqueI16.UpdateByn(key, ref row); + ctx.Db.UniqueI16.UpdateByn(key, new UniqueI16 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1039,16 +969,14 @@ public partial struct UniqueI32 [SpacetimeDB.Reducer] public static void insert_unique_i32(ReducerContext ctx, int n, int data) { - var row = new UniqueI32 { n = n, data = data }; - ctx.Db.UniqueI32.Insert(ref row); + ctx.Db.UniqueI32.Insert(new UniqueI32 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_i32(ReducerContext ctx, int n, int data) { var key = n; - var row = new UniqueI32 { n = n, data = data }; - ctx.Db.UniqueI32.UpdateByn(key, ref row); + ctx.Db.UniqueI32.UpdateByn(key, new UniqueI32 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1068,16 +996,14 @@ public partial struct UniqueI64 [SpacetimeDB.Reducer] public static void insert_unique_i64(ReducerContext ctx, long n, int data) { - var row = new UniqueI64 { n = n, data = data }; - ctx.Db.UniqueI64.Insert(ref row); + ctx.Db.UniqueI64.Insert(new UniqueI64 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_i64(ReducerContext ctx, long n, int data) { var key = n; - var row = new UniqueI64 { n = n, data = data }; - ctx.Db.UniqueI64.UpdateByn(key, ref row); + ctx.Db.UniqueI64.UpdateByn(key, new UniqueI64 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1097,16 +1023,14 @@ public partial struct UniqueI128 [SpacetimeDB.Reducer] public static void insert_unique_i128(ReducerContext ctx, I128 n, int data) { - var row = new UniqueI128 { n = n, data = data }; - ctx.Db.UniqueI128.Insert(ref row); + ctx.Db.UniqueI128.Insert(new UniqueI128 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_i128(ReducerContext ctx, I128 n, int data) { var key = n; - var row = new UniqueI128 { n = n, data = data }; - ctx.Db.UniqueI128.UpdateByn(key, ref row); + ctx.Db.UniqueI128.UpdateByn(key, new UniqueI128 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1126,16 +1050,14 @@ public partial struct UniqueI256 [SpacetimeDB.Reducer] public static void insert_unique_i256(ReducerContext ctx, I256 n, int data) { - var row = new UniqueI256 { n = n, data = data }; - ctx.Db.UniqueI256.Insert(ref row); + ctx.Db.UniqueI256.Insert(new UniqueI256 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_i256(ReducerContext ctx, I256 n, int data) { var key = n; - var row = new UniqueI256 { n = n, data = data }; - ctx.Db.UniqueI256.UpdateByn(key, ref row); + ctx.Db.UniqueI256.UpdateByn(key, new UniqueI256 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1155,16 +1077,14 @@ public partial struct UniqueBool [SpacetimeDB.Reducer] public static void insert_unique_bool(ReducerContext ctx, bool b, int data) { - var row = new UniqueBool { b = b, data = data }; - ctx.Db.UniqueBool.Insert(ref row); + ctx.Db.UniqueBool.Insert(new UniqueBool { b = b, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_bool(ReducerContext ctx, bool b, int data) { var key = b; - var row = new UniqueBool { b = b, data = data }; - ctx.Db.UniqueBool.UpdateByb(key, ref row); + ctx.Db.UniqueBool.UpdateByb(key, new UniqueBool { b = b, data = data }); } [SpacetimeDB.Reducer] @@ -1184,16 +1104,14 @@ public partial struct UniqueString [SpacetimeDB.Reducer] public static void insert_unique_string(ReducerContext ctx, string s, int data) { - var row = new UniqueString { s = s, data = data }; - ctx.Db.UniqueString.Insert(ref row); + ctx.Db.UniqueString.Insert(new UniqueString { s = s, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_string(ReducerContext ctx, string s, int data) { var key = s; - var row = new UniqueString { s = s, data = data }; - ctx.Db.UniqueString.UpdateBys(key, ref row); + ctx.Db.UniqueString.UpdateBys(key, new UniqueString { s = s, data = data }); } [SpacetimeDB.Reducer] @@ -1213,16 +1131,14 @@ public partial struct UniqueIdentity [SpacetimeDB.Reducer] public static void insert_unique_identity(ReducerContext ctx, Identity i, int data) { - var row = new UniqueIdentity { i = i, data = data }; - ctx.Db.UniqueIdentity.Insert(ref row); + ctx.Db.UniqueIdentity.Insert(new UniqueIdentity { i = i, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_identity(ReducerContext ctx, Identity i, int data) { var key = i; - var row = new UniqueIdentity { i = i, data = data }; - ctx.Db.UniqueIdentity.UpdateByi(key, ref row); + ctx.Db.UniqueIdentity.UpdateByi(key, new UniqueIdentity { i = i, data = data }); } [SpacetimeDB.Reducer] @@ -1242,16 +1158,14 @@ public partial struct UniqueAddress [SpacetimeDB.Reducer] public static void insert_unique_address(ReducerContext ctx, Address a, int data) { - var row = new UniqueAddress { a = a, data = data }; - ctx.Db.UniqueAddress.Insert(ref row); + ctx.Db.UniqueAddress.Insert(new UniqueAddress { a = a, data = data }); } [SpacetimeDB.Reducer] public static void update_unique_address(ReducerContext ctx, Address a, int data) { var key = a; - var row = new UniqueAddress { a = a, data = data }; - ctx.Db.UniqueAddress.UpdateBya(key, ref row); + ctx.Db.UniqueAddress.UpdateBya(key, new UniqueAddress { a = a, data = data }); } [SpacetimeDB.Reducer] @@ -1271,16 +1185,14 @@ public partial struct PkU8 [SpacetimeDB.Reducer] public static void insert_pk_u8(ReducerContext ctx, byte n, int data) { - var row = new PkU8 { n = n, data = data }; - ctx.Db.PkU8.Insert(ref row); + ctx.Db.PkU8.Insert(new PkU8 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_u8(ReducerContext ctx, byte n, int data) { var key = n; - var row = new PkU8 { n = n, data = data }; - ctx.Db.PkU8.UpdateByn(key, ref row); + ctx.Db.PkU8.UpdateByn(key, new PkU8 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1300,16 +1212,14 @@ public partial struct PkU16 [SpacetimeDB.Reducer] public static void insert_pk_u16(ReducerContext ctx, ushort n, int data) { - var row = new PkU16 { n = n, data = data }; - ctx.Db.PkU16.Insert(ref row); + ctx.Db.PkU16.Insert(new PkU16 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_u16(ReducerContext ctx, ushort n, int data) { var key = n; - var row = new PkU16 { n = n, data = data }; - ctx.Db.PkU16.UpdateByn(key, ref row); + ctx.Db.PkU16.UpdateByn(key, new PkU16 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1329,16 +1239,14 @@ public partial struct PkU32 [SpacetimeDB.Reducer] public static void insert_pk_u32(ReducerContext ctx, uint n, int data) { - var row = new PkU32 { n = n, data = data }; - ctx.Db.PkU32.Insert(ref row); + ctx.Db.PkU32.Insert(new PkU32 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_u32(ReducerContext ctx, uint n, int data) { var key = n; - var row = new PkU32 { n = n, data = data }; - ctx.Db.PkU32.UpdateByn(key, ref row); + ctx.Db.PkU32.UpdateByn(key, new PkU32 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1358,16 +1266,14 @@ public partial struct PkU64 [SpacetimeDB.Reducer] public static void insert_pk_u64(ReducerContext ctx, ulong n, int data) { - var row = new PkU64 { n = n, data = data }; - ctx.Db.PkU64.Insert(ref row); + ctx.Db.PkU64.Insert(new PkU64 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_u64(ReducerContext ctx, ulong n, int data) { var key = n; - var row = new PkU64 { n = n, data = data }; - ctx.Db.PkU64.UpdateByn(key, ref row); + ctx.Db.PkU64.UpdateByn(key, new PkU64 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1387,16 +1293,14 @@ public partial struct PkU128 [SpacetimeDB.Reducer] public static void insert_pk_u128(ReducerContext ctx, U128 n, int data) { - var row = new PkU128 { n = n, data = data }; - ctx.Db.PkU128.Insert(ref row); + ctx.Db.PkU128.Insert(new PkU128 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_u128(ReducerContext ctx, U128 n, int data) { var key = n; - var row = new PkU128 { n = n, data = data }; - ctx.Db.PkU128.UpdateByn(key, ref row); + ctx.Db.PkU128.UpdateByn(key, new PkU128 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1416,16 +1320,14 @@ public partial struct PkU256 [SpacetimeDB.Reducer] public static void insert_pk_u256(ReducerContext ctx, U256 n, int data) { - var row = new PkU256 { n = n, data = data }; - ctx.Db.PkU256.Insert(ref row); + ctx.Db.PkU256.Insert(new PkU256 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_u256(ReducerContext ctx, U256 n, int data) { var key = n; - var row = new PkU256 { n = n, data = data }; - ctx.Db.PkU256.UpdateByn(key, ref row); + ctx.Db.PkU256.UpdateByn(key, new PkU256 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1445,16 +1347,14 @@ public partial struct PkI8 [SpacetimeDB.Reducer] public static void insert_pk_i8(ReducerContext ctx, sbyte n, int data) { - var row = new PkI8 { n = n, data = data }; - ctx.Db.PkI8.Insert(ref row); + ctx.Db.PkI8.Insert(new PkI8 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_i8(ReducerContext ctx, sbyte n, int data) { var key = n; - var row = new PkI8 { n = n, data = data }; - ctx.Db.PkI8.UpdateByn(key, ref row); + ctx.Db.PkI8.UpdateByn(key, new PkI8 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1474,16 +1374,14 @@ public partial struct PkI16 [SpacetimeDB.Reducer] public static void insert_pk_i16(ReducerContext ctx, short n, int data) { - var row = new PkI16 { n = n, data = data }; - ctx.Db.PkI16.Insert(ref row); + ctx.Db.PkI16.Insert(new PkI16 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_i16(ReducerContext ctx, short n, int data) { var key = n; - var row = new PkI16 { n = n, data = data }; - ctx.Db.PkI16.UpdateByn(key, ref row); + ctx.Db.PkI16.UpdateByn(key, new PkI16 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1503,16 +1401,14 @@ public partial struct PkI32 [SpacetimeDB.Reducer] public static void insert_pk_i32(ReducerContext ctx, int n, int data) { - var row = new PkI32 { n = n, data = data }; - ctx.Db.PkI32.Insert(ref row); + ctx.Db.PkI32.Insert(new PkI32 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_i32(ReducerContext ctx, int n, int data) { var key = n; - var row = new PkI32 { n = n, data = data }; - ctx.Db.PkI32.UpdateByn(key, ref row); + ctx.Db.PkI32.UpdateByn(key, new PkI32 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1532,16 +1428,14 @@ public partial struct PkI64 [SpacetimeDB.Reducer] public static void insert_pk_i64(ReducerContext ctx, long n, int data) { - var row = new PkI64 { n = n, data = data }; - ctx.Db.PkI64.Insert(ref row); + ctx.Db.PkI64.Insert(new PkI64 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_i64(ReducerContext ctx, long n, int data) { var key = n; - var row = new PkI64 { n = n, data = data }; - ctx.Db.PkI64.UpdateByn(key, ref row); + ctx.Db.PkI64.UpdateByn(key, new PkI64 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1561,16 +1455,14 @@ public partial struct PkI128 [SpacetimeDB.Reducer] public static void insert_pk_i128(ReducerContext ctx, I128 n, int data) { - var row = new PkI128 { n = n, data = data }; - ctx.Db.PkI128.Insert(ref row); + ctx.Db.PkI128.Insert(new PkI128 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_i128(ReducerContext ctx, I128 n, int data) { var key = n; - var row = new PkI128 { n = n, data = data }; - ctx.Db.PkI128.UpdateByn(key, ref row); + ctx.Db.PkI128.UpdateByn(key, new PkI128 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1590,16 +1482,14 @@ public partial struct PkI256 [SpacetimeDB.Reducer] public static void insert_pk_i256(ReducerContext ctx, I256 n, int data) { - var row = new PkI256 { n = n, data = data }; - ctx.Db.PkI256.Insert(ref row); + ctx.Db.PkI256.Insert(new PkI256 { n = n, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_i256(ReducerContext ctx, I256 n, int data) { var key = n; - var row = new PkI256 { n = n, data = data }; - ctx.Db.PkI256.UpdateByn(key, ref row); + ctx.Db.PkI256.UpdateByn(key, new PkI256 { n = n, data = data }); } [SpacetimeDB.Reducer] @@ -1619,16 +1509,14 @@ public partial struct PkBool [SpacetimeDB.Reducer] public static void insert_pk_bool(ReducerContext ctx, bool b, int data) { - var row = new PkBool { b = b, data = data }; - ctx.Db.PkBool.Insert(ref row); + ctx.Db.PkBool.Insert(new PkBool { b = b, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_bool(ReducerContext ctx, bool b, int data) { var key = b; - var row = new PkBool { b = b, data = data }; - ctx.Db.PkBool.UpdateByb(key, ref row); + ctx.Db.PkBool.UpdateByb(key, new PkBool { b = b, data = data }); } [SpacetimeDB.Reducer] @@ -1648,16 +1536,14 @@ public partial struct PkString [SpacetimeDB.Reducer] public static void insert_pk_string(ReducerContext ctx, string s, int data) { - var row = new PkString { s = s, data = data }; - ctx.Db.PkString.Insert(ref row); + ctx.Db.PkString.Insert(new PkString { s = s, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_string(ReducerContext ctx, string s, int data) { var key = s; - var row = new PkString { s = s, data = data }; - ctx.Db.PkString.UpdateBys(key, ref row); + ctx.Db.PkString.UpdateBys(key, new PkString { s = s, data = data }); } [SpacetimeDB.Reducer] @@ -1677,16 +1563,14 @@ public partial struct PkIdentity [SpacetimeDB.Reducer] public static void insert_pk_identity(ReducerContext ctx, Identity i, int data) { - var row = new PkIdentity { i = i, data = data }; - ctx.Db.PkIdentity.Insert(ref row); + ctx.Db.PkIdentity.Insert(new PkIdentity { i = i, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_identity(ReducerContext ctx, Identity i, int data) { var key = i; - var row = new PkIdentity { i = i, data = data }; - ctx.Db.PkIdentity.UpdateByi(key, ref row); + ctx.Db.PkIdentity.UpdateByi(key, new PkIdentity { i = i, data = data }); } [SpacetimeDB.Reducer] @@ -1706,16 +1590,14 @@ public partial struct PkAddress [SpacetimeDB.Reducer] public static void insert_pk_address(ReducerContext ctx, Address a, int data) { - var row = new PkAddress { a = a, data = data }; - ctx.Db.PkAddress.Insert(ref row); + ctx.Db.PkAddress.Insert(new PkAddress { a = a, data = data }); } [SpacetimeDB.Reducer] public static void update_pk_address(ReducerContext ctx, Address a, int data) { var key = a; - var row = new PkAddress { a = a, data = data }; - ctx.Db.PkAddress.UpdateBya(key, ref row); + ctx.Db.PkAddress.UpdateBya(key, new PkAddress { a = a, data = data }); } [SpacetimeDB.Reducer] @@ -1727,36 +1609,31 @@ public static void delete_pk_address(ReducerContext ctx, Address a) [SpacetimeDB.Reducer] public static void insert_caller_one_identity(ReducerContext ctx) { - var row = new OneIdentity { i = ctx.Sender }; - ctx.Db.OneIdentity.Insert(ref row); + ctx.Db.OneIdentity.Insert(new OneIdentity { i = ctx.Sender }); } [SpacetimeDB.Reducer] public static void insert_caller_vec_identity(ReducerContext ctx) { - var row = new VecIdentity { i = new List { ctx.Sender } }; - ctx.Db.VecIdentity.Insert(ref row); + ctx.Db.VecIdentity.Insert(new VecIdentity { i = new List { ctx.Sender } }); } [SpacetimeDB.Reducer] public static void insert_caller_unique_identity(ReducerContext ctx, int data) { - var row = new UniqueIdentity { i = ctx.Sender, data = data }; - ctx.Db.UniqueIdentity.Insert(ref row); + ctx.Db.UniqueIdentity.Insert(new UniqueIdentity { i = ctx.Sender, data = data }); } [SpacetimeDB.Reducer] public static void insert_caller_pk_identity(ReducerContext ctx, int data) { - var row = new PkIdentity { i = ctx.Sender, data = data }; - ctx.Db.PkIdentity.Insert(ref row); + ctx.Db.PkIdentity.Insert(new PkIdentity { i = ctx.Sender, data = data }); } [SpacetimeDB.Reducer] public static void insert_caller_one_address(ReducerContext ctx) { - var row = new OneAddress { a = (Address)ctx.Address!, }; - ctx.Db.OneAddress.Insert(ref row); + ctx.Db.OneAddress.Insert(new OneAddress { a = (Address)ctx.Address!, }); } [SpacetimeDB.Reducer] @@ -1773,15 +1650,13 @@ public static void insert_caller_vec_address(ReducerContext ctx) [SpacetimeDB.Reducer] public static void insert_caller_unique_address(ReducerContext ctx, int data) { - var row = new UniqueAddress { a = (Address)ctx.Address!, data = data }; - ctx.Db.UniqueAddress.Insert(ref row); + ctx.Db.UniqueAddress.Insert(new UniqueAddress { a = (Address)ctx.Address!, data = data }); } [SpacetimeDB.Reducer] public static void insert_caller_pk_address(ReducerContext ctx, int data) { - var row = new PkAddress { a = (Address)ctx.Address!, data = data }; - ctx.Db.PkAddress.Insert(ref row); + ctx.Db.PkAddress.Insert(new PkAddress { a = (Address)ctx.Address!, data = data }); } [SpacetimeDB.Table(Public = true)] @@ -1838,7 +1713,7 @@ public static void insert_large_table( EveryVecStruct v ) { - var row = new LargeTable { + ctx.Db.LargeTable.Insert(new LargeTable { a = a, b = b, c = c, @@ -1861,20 +1736,18 @@ EveryVecStruct v t = t, u = u, v = v, - }; - ctx.Db.LargeTable.Insert(ref row); + }); } [SpacetimeDB.Reducer] public static void insert_primitives_as_strings(ReducerContext ctx, EveryPrimitiveStruct s) { - var row = new VecString { + ctx.Db.VecString.Insert(new VecString { s = typeof(EveryPrimitiveStruct) .GetFields() .Select(f => f.GetValue(s)!.ToString()!.ToLowerInvariant()) .ToList() - }; - ctx.Db.VecString.Insert(ref row); + }); } [SpacetimeDB.Table(Public = true)] @@ -1887,8 +1760,7 @@ public partial struct TableHoldsTable [SpacetimeDB.Reducer] public static void insert_table_holds_table(ReducerContext ctx, OneU8 a, VecU8 b) { - var row = new TableHoldsTable { a = a, b = b }; - ctx.Db.TableHoldsTable.Insert(ref row); + ctx.Db.TableHoldsTable.Insert(new TableHoldsTable { a = a, b = b }); } [SpacetimeDB.Reducer] diff --git a/modules/sdk-test-multi-cs/Lib.cs b/modules/sdk-test-multi-cs/Lib.cs index 00112c5d27..5bd34a2807 100644 --- a/modules/sdk-test-multi-cs/Lib.cs +++ b/modules/sdk-test-multi-cs/Lib.cs @@ -12,7 +12,7 @@ partial struct User { public string Name; } -[Table(Name = "MyTable1", Public = true, Index = "Name")] +[Table(Name = "MyTable1", Public = true)] [Table(Name = "MyTable2")] partial struct MyTable { public string Name; @@ -31,12 +31,11 @@ static partial class Module public static void AddUser(ReducerContext ctx, string name) { Runtime.Log($"Hello, {name}"); - var user = new User() { + ctx.Db.User.Insert(new User() { Id = ulong.MaxValue, Owner = ctx.Sender, Name = name, - }; - ctx.Db.User.Insert(ref user); + }); } [Reducer] diff --git a/modules/spacetimedb-quickstart-cs/Lib.cs b/modules/spacetimedb-quickstart-cs/Lib.cs index 7a23263343..e5efa37090 100644 --- a/modules/spacetimedb-quickstart-cs/Lib.cs +++ b/modules/spacetimedb-quickstart-cs/Lib.cs @@ -16,8 +16,7 @@ static partial class Module [Reducer("add")] public static void Add(ReducerContext ctx, string name, byte age) { - var row = new Person { Name = name, Age = age }; - ctx.Db.Person.Insert(ref row); + ctx.Db.Person.Insert(new Person { Name = name, Age = age }); } [Reducer("say_hello")] From 4613e338d62bae7b92c7585b840622e5fee17e62 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Wed, 25 Sep 2024 13:10:43 -0400 Subject: [PATCH 08/27] Rebase fix --- modules/sdk-test-multi-cs/Lib.cs | 4 ++-- modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/modules/sdk-test-multi-cs/Lib.cs b/modules/sdk-test-multi-cs/Lib.cs index 5bd34a2807..467c73b65a 100644 --- a/modules/sdk-test-multi-cs/Lib.cs +++ b/modules/sdk-test-multi-cs/Lib.cs @@ -29,7 +29,7 @@ static partial class Module { [Reducer] public static void AddUser(ReducerContext ctx, string name) { - Runtime.Log($"Hello, {name}"); + Log.Info($"Hello, {name}"); ctx.Db.User.Insert(new User() { Id = ulong.MaxValue, @@ -44,7 +44,7 @@ public static void GreetAllUsers(ReducerContext ctx) Runtime.Log("Hello All"); foreach (var user in ctx.Db.User.Iter()) { - Runtime.Log($"Hello, {user.Name}!"); + Log.Info($"Hello, {user.Name}!"); } } } \ No newline at end of file diff --git a/modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj b/modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj index b32e62e008..8f459333e3 100644 --- a/modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj +++ b/modules/sdk-test-multi-cs/sdk-test-multi-cs.csproj @@ -14,7 +14,7 @@ at least it simplifies workflow for editing and testing C# code itself. --> - + From f18e7e046da326ccd9245c4a930cc1ccb4f94495 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Wed, 25 Sep 2024 13:29:26 -0400 Subject: [PATCH 09/27] Fix --- .../bindings-csharp/Codegen.Tests/fixtures/server/server.csproj | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/server.csproj b/crates/bindings-csharp/Codegen.Tests/fixtures/server/server.csproj index 68c9eadab1..adf6d2cd0b 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/server.csproj +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/server.csproj @@ -12,7 +12,7 @@ - + From 9ed248ed5896ca9a0298c58acec16fe08684dda7 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Wed, 25 Sep 2024 13:35:08 -0400 Subject: [PATCH 10/27] Unfix --- .../bindings-csharp/Codegen.Tests/fixtures/server/server.csproj | 1 - 1 file changed, 1 deletion(-) diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/server.csproj b/crates/bindings-csharp/Codegen.Tests/fixtures/server/server.csproj index adf6d2cd0b..37f8529367 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/server.csproj +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/server.csproj @@ -12,7 +12,6 @@ - From bd46658477ac4c02d85407777fad4e6278db706a Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Wed, 25 Sep 2024 13:40:58 -0400 Subject: [PATCH 11/27] Update --- crates/bindings-csharp/Codegen/Module.cs | 25 ++++++++++++------------ modules/sdk-test-multi-cs/Lib.cs | 2 +- 2 files changed, 14 insertions(+), 13 deletions(-) diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index c87fea2776..8ea4b9a8ea 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -2,6 +2,7 @@ namespace SpacetimeDB.Codegen; using System.Collections.Immutable; using Microsoft.CodeAnalysis; +using Microsoft.CodeAnalysis.CSharp; using Microsoft.CodeAnalysis.CSharp.Syntax; using static Utils; @@ -132,7 +133,7 @@ public TableView(TableDeclaration table, AttributeData data) record TableDeclaration : BaseTypeDeclaration { - public readonly string Visibility; + public readonly Accessibility Visibility; public readonly string? Scheduled; public readonly EquatableArray Views; @@ -157,15 +158,15 @@ public TableDeclaration(GeneratorAttributeSyntaxContext context) throw new InvalidOperationException("Tagged enums cannot be tables."); } - Visibility = context.TargetSymbol.DeclaredAccessibility switch - { - Accessibility.ProtectedAndInternal - or Accessibility.NotApplicable - or Accessibility.Internal => "internal", - Accessibility.Public => "public", - _ => throw new Exception( - "Table row type visibility must be public or internal." - ), + Visibility = context.TargetSymbol.DeclaredAccessibility; + switch (Visibility) { + case Accessibility.ProtectedAndInternal: + case Accessibility.NotApplicable: + case Accessibility.Internal: + case Accessibility.Public: + break; + default: + throw new Exception("Table row type visibility must be public or internal."); }; Views = new(context.Attributes @@ -240,7 +241,7 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) var globalName = $"global::{FullName}"; var iTable = $"SpacetimeDB.Internal.ITableView<{v.Name}, {globalName}>"; yield return new((v.Name, globalName), ($$""" - {{Visibility}} readonly struct {{v.Name}} : {{iTable}} { + {{SyntaxFacts.GetText(Visibility)}} readonly struct {{v.Name}} : {{iTable}} { static {{globalName}} {{iTable}}.ReadGenFields(System.IO.BinaryReader reader, {{globalName}} row) { {{string.Join( "\n", @@ -260,7 +261,7 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) public void Insert({{globalName}} row) => {{iTable}}.Insert(row); {{string.Join("\n", GenerateViewFilters(v.Name, iTable))}} } - """, $"{Visibility} Internal.TableHandles.{v.Name} {v.Name} => new();")); + """, $"{SyntaxFacts.GetText(Visibility)} Internal.TableHandles.{v.Name} {v.Name} => new();")); } } diff --git a/modules/sdk-test-multi-cs/Lib.cs b/modules/sdk-test-multi-cs/Lib.cs index 467c73b65a..5162256f72 100644 --- a/modules/sdk-test-multi-cs/Lib.cs +++ b/modules/sdk-test-multi-cs/Lib.cs @@ -41,7 +41,7 @@ public static void AddUser(ReducerContext ctx, string name) { [Reducer] public static void GreetAllUsers(ReducerContext ctx) { - Runtime.Log("Hello All"); + Log.Info("Hello All"); foreach (var user in ctx.Db.User.Iter()) { Log.Info($"Hello, {user.Name}!"); From d30e38b75cac7aafe33e57440825820280648dc8 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Wed, 25 Sep 2024 14:05:05 -0400 Subject: [PATCH 12/27] Update --- crates/bindings-csharp/BSATN.Runtime/Db.cs | 8 +- .../Codegen.Tests/fixtures/server/Lib.cs | 15 +-- .../snapshots/Module#PublicTable.verified.cs | 127 +++++------------- ...Module#Timers.SendMessageTimer.verified.cs | 21 +-- crates/bindings-csharp/Codegen/Module.cs | 9 +- crates/bindings-csharp/Runtime/Attrs.cs | 6 +- 6 files changed, 50 insertions(+), 136 deletions(-) diff --git a/crates/bindings-csharp/BSATN.Runtime/Db.cs b/crates/bindings-csharp/BSATN.Runtime/Db.cs index a1039d3468..dc2624e4f7 100644 --- a/crates/bindings-csharp/BSATN.Runtime/Db.cs +++ b/crates/bindings-csharp/BSATN.Runtime/Db.cs @@ -1,11 +1,7 @@ namespace SpacetimeDB; -public abstract record DbContext +public abstract record DbContext(DbView Db) where DbView : class, new() { - public readonly DbView Db; - - public DbContext() => Db = new(); - - public DbContext(DbView db) => Db = db; + public DbContext() : this(new DbView()) { } } diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs index df6a40cc5d..ae9ed0632f 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs @@ -17,8 +17,8 @@ public partial class CustomClass { public const int IGNORE_ME = 0; public static readonly string IGNORE_ME_TOO = ""; - public int IntField; - public string StringField; + public int IntField = 0; + public string StringField = ""; } [StructLayout(LayoutKind.Auto)] @@ -84,8 +84,8 @@ public static partial class Reducers [SpacetimeDB.Reducer] public static void InsertData(ReducerContext ctx, PublicTable data) { - ctx.Db.PublicTable.Insert(ref data); - Runtime.Log("New list"); + ctx.Db.PublicTable.Insert(data); + Log.Info("New list"); foreach (var item in ctx.Db.PublicTable.Iter()) { Log.Info($"Item: {item.StringField}"); @@ -108,7 +108,7 @@ public static partial class AndClasses [SpacetimeDB.Reducer("test_custom_name_and_reducer_ctx")] public static void InsertData2(ReducerContext ctx, PublicTable data) { - ctx.Db.PublicTable.Insert(ref data); + ctx.Db.PublicTable.Insert(data); } } } @@ -134,10 +134,9 @@ public static void SendScheduledMessage(ReducerContext ctx, SendMessageTimer arg [SpacetimeDB.Reducer(ReducerKind.Init)] public static void Init(ReducerContext ctx) { - var row = new SendMessageTimer { + ctx.Db.SendMessageTimer.Insert(new SendMessageTimer { Text = "bot sending a message", ScheduledAt = ctx.Time.AddSeconds(10), - }; - ctx.Db.SendMessageTimer.Insert(ref row); + }); } } diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs index 7b24363b14..08d7e77880 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs @@ -197,126 +197,59 @@ SpacetimeDB.BSATN.ITypeRegistrar registrar TableName: nameof(PublicTable), Columns: [ - new(nameof(Id), global::PublicTable.BSATN.Id.GetAlgebraicType(registrar)), - new( - nameof(ByteField), - global::PublicTable.BSATN.ByteField.GetAlgebraicType(registrar) - ), - new( - nameof(UshortField), - global::PublicTable.BSATN.UshortField.GetAlgebraicType(registrar) - ), - new( - nameof(UintField), - global::PublicTable.BSATN.UintField.GetAlgebraicType(registrar) - ), - new( - nameof(UlongField), - global::PublicTable.BSATN.UlongField.GetAlgebraicType(registrar) - ), - new( - nameof(UInt128Field), - global::PublicTable.BSATN.UInt128Field.GetAlgebraicType(registrar) - ), - new( - nameof(U128Field), - global::PublicTable.BSATN.U128Field.GetAlgebraicType(registrar) - ), - new( - nameof(U256Field), - global::PublicTable.BSATN.U256Field.GetAlgebraicType(registrar) - ), - new( - nameof(SbyteField), - global::PublicTable.BSATN.SbyteField.GetAlgebraicType(registrar) - ), - new( - nameof(ShortField), - global::PublicTable.BSATN.ShortField.GetAlgebraicType(registrar) - ), - new( - nameof(IntField), - global::PublicTable.BSATN.IntField.GetAlgebraicType(registrar) - ), - new( - nameof(LongField), - global::PublicTable.BSATN.LongField.GetAlgebraicType(registrar) - ), - new( - nameof(Int128Field), - global::PublicTable.BSATN.Int128Field.GetAlgebraicType(registrar) - ), - new( - nameof(I128Field), - global::PublicTable.BSATN.I128Field.GetAlgebraicType(registrar) - ), - new( - nameof(I256Field), - global::PublicTable.BSATN.I256Field.GetAlgebraicType(registrar) - ), - new( - nameof(BoolField), - global::PublicTable.BSATN.BoolField.GetAlgebraicType(registrar) - ), - new( - nameof(FloatField), - global::PublicTable.BSATN.FloatField.GetAlgebraicType(registrar) - ), - new( - nameof(DoubleField), - global::PublicTable.BSATN.DoubleField.GetAlgebraicType(registrar) - ), - new( - nameof(StringField), - global::PublicTable.BSATN.StringField.GetAlgebraicType(registrar) - ), - new( - nameof(IdentityField), - global::PublicTable.BSATN.IdentityField.GetAlgebraicType(registrar) - ), - new( - nameof(AddressField), - global::PublicTable.BSATN.AddressField.GetAlgebraicType(registrar) - ), + new(nameof(Id), BSATN.Id.GetAlgebraicType(registrar)), + new(nameof(ByteField), BSATN.ByteField.GetAlgebraicType(registrar)), + new(nameof(UshortField), BSATN.UshortField.GetAlgebraicType(registrar)), + new(nameof(UintField), BSATN.UintField.GetAlgebraicType(registrar)), + new(nameof(UlongField), BSATN.UlongField.GetAlgebraicType(registrar)), + new(nameof(UInt128Field), BSATN.UInt128Field.GetAlgebraicType(registrar)), + new(nameof(U128Field), BSATN.U128Field.GetAlgebraicType(registrar)), + new(nameof(U256Field), BSATN.U256Field.GetAlgebraicType(registrar)), + new(nameof(SbyteField), BSATN.SbyteField.GetAlgebraicType(registrar)), + new(nameof(ShortField), BSATN.ShortField.GetAlgebraicType(registrar)), + new(nameof(IntField), BSATN.IntField.GetAlgebraicType(registrar)), + new(nameof(LongField), BSATN.LongField.GetAlgebraicType(registrar)), + new(nameof(Int128Field), BSATN.Int128Field.GetAlgebraicType(registrar)), + new(nameof(I128Field), BSATN.I128Field.GetAlgebraicType(registrar)), + new(nameof(I256Field), BSATN.I256Field.GetAlgebraicType(registrar)), + new(nameof(BoolField), BSATN.BoolField.GetAlgebraicType(registrar)), + new(nameof(FloatField), BSATN.FloatField.GetAlgebraicType(registrar)), + new(nameof(DoubleField), BSATN.DoubleField.GetAlgebraicType(registrar)), + new(nameof(StringField), BSATN.StringField.GetAlgebraicType(registrar)), + new(nameof(IdentityField), BSATN.IdentityField.GetAlgebraicType(registrar)), + new(nameof(AddressField), BSATN.AddressField.GetAlgebraicType(registrar)), new( nameof(CustomStructField), - global::PublicTable.BSATN.CustomStructField.GetAlgebraicType(registrar) + BSATN.CustomStructField.GetAlgebraicType(registrar) ), new( nameof(CustomClassField), - global::PublicTable.BSATN.CustomClassField.GetAlgebraicType(registrar) + BSATN.CustomClassField.GetAlgebraicType(registrar) ), new( nameof(CustomEnumField), - global::PublicTable.BSATN.CustomEnumField.GetAlgebraicType(registrar) + BSATN.CustomEnumField.GetAlgebraicType(registrar) ), new( nameof(CustomTaggedEnumField), - global::PublicTable.BSATN.CustomTaggedEnumField.GetAlgebraicType( - registrar - ) - ), - new( - nameof(ListField), - global::PublicTable.BSATN.ListField.GetAlgebraicType(registrar) + BSATN.CustomTaggedEnumField.GetAlgebraicType(registrar) ), + new(nameof(ListField), BSATN.ListField.GetAlgebraicType(registrar)), new( nameof(DictionaryField), - global::PublicTable.BSATN.DictionaryField.GetAlgebraicType(registrar) + BSATN.DictionaryField.GetAlgebraicType(registrar) ), new( nameof(NullableValueField), - global::PublicTable.BSATN.NullableValueField.GetAlgebraicType(registrar) + BSATN.NullableValueField.GetAlgebraicType(registrar) ), new( nameof(NullableReferenceField), - global::PublicTable.BSATN.NullableReferenceField.GetAlgebraicType( - registrar - ) + BSATN.NullableReferenceField.GetAlgebraicType(registrar) ), new( nameof(ComplexNestedField), - global::PublicTable.BSATN.ComplexNestedField.GetAlgebraicType(registrar) + BSATN.ComplexNestedField.GetAlgebraicType(registrar) ) ], Indexes: [], diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs index 67865ddea2..b83a761968 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs @@ -62,24 +62,9 @@ SpacetimeDB.BSATN.ITypeRegistrar registrar TableName: nameof(SendMessageTimer), Columns: [ - new( - nameof(Text), - global::Timers.SendMessageTimer.BSATN.Text.GetAlgebraicType( - registrar - ) - ), - new( - nameof(ScheduledId), - global::Timers.SendMessageTimer.BSATN.ScheduledId.GetAlgebraicType( - registrar - ) - ), - new( - nameof(ScheduledAt), - global::Timers.SendMessageTimer.BSATN.ScheduledAt.GetAlgebraicType( - registrar - ) - ) + new(nameof(Text), BSATN.Text.GetAlgebraicType(registrar)), + new(nameof(ScheduledId), BSATN.ScheduledId.GetAlgebraicType(registrar)), + new(nameof(ScheduledAt), BSATN.ScheduledAt.GetAlgebraicType(registrar)) ], Indexes: [], Constraints: diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index 8ea4b9a8ea..d22f1cf314 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -105,7 +105,7 @@ public ColumnAttrs GetAttrs(string tableName) => Attrs // For the `TableDesc` constructor. public string GenerateColumnDef() => - $"new (nameof({Name}), global::{FullTableName}.BSATN.{Name}.GetAlgebraicType(registrar))"; + $"new (nameof({Name}), BSATN.{Name}.GetAlgebraicType(registrar))"; // For the `Filter` constructor. public string GenerateFilterEntry() => @@ -387,8 +387,7 @@ public ReducerDeclaration(GeneratorAttributeSyntaxContext context) public KeyValuePair GenerateClass() { - var args = string.Join(", ", Args.Select(a => $"{a.Name}.Read(reader)")); - var argsSep = args == "" ? "" : ", "; + var args = string.Join(", ", Args.Select(a => $"{a.Name}.Read(reader)").Prepend("ctx")); var class_ = $$""" class {{Name}}: SpacetimeDB.Internal.IReducer { {{MemberDeclaration.GenerateBsatnFields(Accessibility.Private, Args)}} @@ -399,7 +398,7 @@ class {{Name}}: SpacetimeDB.Internal.IReducer { ); public void Invoke(BinaryReader reader, SpacetimeDB.Internal.IReducerContext ctx) { - {{FullName}}((SpacetimeDB.ReducerContext)ctx{{argsSep}}{{args}}); + {{FullName}}((SpacetimeDB.ReducerContext){{args}}); } } """; @@ -485,7 +484,9 @@ public void Initialize(IncrementalGeneratorInitializationContext context) var addReducers = tuple.Right.Sort((a, b) => a.Key.CompareTo(b.Key)); // Don't generate the FFI boilerplate if there are no tables or reducers. if (tableViews.IsEmpty && addReducers.IsEmpty) + { return; + } context.AddSource( "FFI.cs", $$""" diff --git a/crates/bindings-csharp/Runtime/Attrs.cs b/crates/bindings-csharp/Runtime/Attrs.cs index 1a05f85bc2..f6ab1fabd2 100644 --- a/crates/bindings-csharp/Runtime/Attrs.cs +++ b/crates/bindings-csharp/Runtime/Attrs.cs @@ -32,14 +32,14 @@ public sealed class TableAttribute : Attribute /// /// Defaults to the nameof of the target type. ///
- public string? Name; + public string? Name { get; init; } /// /// Set to true to make the table visible to everyone. /// /// Defaults to the table only being visible to its owner. /// - public bool Public = false; + public bool Public { get; init; } = false; public string? Scheduled { get; init; } } @@ -47,7 +47,7 @@ public sealed class TableAttribute : Attribute [AttributeUsage(AttributeTargets.Field)] public abstract class ColumnAttribute : Attribute { - public string? Table; + public string? Table { get; init; } } public sealed class AutoIncAttribute : ColumnAttribute { } From 4f47dfe95b4c654337b8b5df7a9525a23b2d7db7 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Wed, 25 Sep 2024 15:13:01 -0400 Subject: [PATCH 13/27] Update + Format --- crates/bindings-csharp/BSATN.Runtime/Attrs.cs | 3 +- crates/bindings-csharp/BSATN.Runtime/Db.cs | 3 +- .../Codegen.Tests/fixtures/server/Lib.cs | 11 +- .../server/snapshots/Module#FFI.verified.cs | 16 +- crates/bindings-csharp/Codegen/Module.cs | 139 +++++++++++------- crates/bindings-csharp/Runtime/Attrs.cs | 2 - .../bindings-csharp/Runtime/Internal/FFI.cs | 2 +- .../Runtime/Internal/Module.cs | 34 +++-- .../bindings-csharp/Runtime/LogStopwatch.cs | 1 + crates/bindings-csharp/Runtime/Runtime.cs | 29 ++-- 10 files changed, 145 insertions(+), 95 deletions(-) diff --git a/crates/bindings-csharp/BSATN.Runtime/Attrs.cs b/crates/bindings-csharp/BSATN.Runtime/Attrs.cs index 840e0aca96..6dc073d987 100644 --- a/crates/bindings-csharp/BSATN.Runtime/Attrs.cs +++ b/crates/bindings-csharp/BSATN.Runtime/Attrs.cs @@ -12,5 +12,4 @@ public sealed class TypeAttribute : Attribute { } // This could be an interface, but using `record` forces C# to check that it can // only be applied on types that are records themselves. public abstract record TaggedEnum - where Variants : struct, ITuple -{ } + where Variants : struct, ITuple { } diff --git a/crates/bindings-csharp/BSATN.Runtime/Db.cs b/crates/bindings-csharp/BSATN.Runtime/Db.cs index dc2624e4f7..7f3e6ebe8f 100644 --- a/crates/bindings-csharp/BSATN.Runtime/Db.cs +++ b/crates/bindings-csharp/BSATN.Runtime/Db.cs @@ -3,5 +3,6 @@ public abstract record DbContext(DbView Db) where DbView : class, new() { - public DbContext() : this(new DbView()) { } + public DbContext() + : this(new DbView()) { } } diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs index ae9ed0632f..a8a2046765 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs @@ -134,9 +134,12 @@ public static void SendScheduledMessage(ReducerContext ctx, SendMessageTimer arg [SpacetimeDB.Reducer(ReducerKind.Init)] public static void Init(ReducerContext ctx) { - ctx.Db.SendMessageTimer.Insert(new SendMessageTimer { - Text = "bot sending a message", - ScheduledAt = ctx.Time.AddSeconds(10), - }); + ctx.Db.SendMessageTimer.Insert( + new SendMessageTimer + { + Text = "bot sending a message", + ScheduledAt = ctx.Time.AddSeconds(10), + } + ); } } diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs index 54ee754738..75e469fab2 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs @@ -8,7 +8,16 @@ namespace SpacetimeDB { - public sealed record ReducerContext : BaseReducerContext { } + public sealed record ReducerContext : BaseReducerContext + { + internal ReducerContext( + Identity identity, + Address? address, + Random random, + DateTimeOffset time + ) + : base(identity, address, random, time) { } + } namespace Internal.TableHandles { @@ -444,7 +453,10 @@ public void Invoke(BinaryReader reader, SpacetimeDB.Internal.IReducerContext ctx #endif public static void Main() { - SpacetimeDB.Internal.Module.Initialize(new SpacetimeDB.ReducerContext()); + SpacetimeDB.Internal.Module.Initialize( + (identity, address, random, time) => + new SpacetimeDB.ReducerContext(identity, address, random, time) + ); SpacetimeDB.Internal.Module.RegisterReducer(); SpacetimeDB.Internal.Module.RegisterReducer(); diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index d22f1cf314..7a49af340b 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -32,19 +32,26 @@ public ColumnDeclaration(string tableName, IFieldSymbol field) { FullTableName = tableName; - Attrs = new(field - .GetAttributes() - .Select(a => (table: a.NamedArguments.FirstOrDefault(a => a.Key == "Table").Value.Value as string, - attr: a.AttributeClass?.ToString() switch - { - "SpacetimeDB.AutoIncAttribute" => ColumnAttrs.AutoInc, - "SpacetimeDB.PrimaryKeyAttribute" => ColumnAttrs.PrimaryKey, - "SpacetimeDB.UniqueAttribute" => ColumnAttrs.Unique, - "SpacetimeDB.IndexedAttribute" => ColumnAttrs.Indexed, - _ => ColumnAttrs.UnSet, - })) - .Where(a => a.attr != ColumnAttrs.UnSet) - .ToImmutableArray()); + Attrs = new( + field + .GetAttributes() + .Select(a => + ( + table: a.NamedArguments.FirstOrDefault(a => a.Key == "Table").Value.Value + as string, + attr: a.AttributeClass?.ToString() switch + { + "SpacetimeDB.AutoIncAttribute" => ColumnAttrs.AutoInc, + "SpacetimeDB.PrimaryKeyAttribute" => ColumnAttrs.PrimaryKey, + "SpacetimeDB.UniqueAttribute" => ColumnAttrs.Unique, + "SpacetimeDB.IndexedAttribute" => ColumnAttrs.Indexed, + _ => ColumnAttrs.UnSet, + } + ) + ) + .Where(a => a.attr != ColumnAttrs.UnSet) + .ToImmutableArray() + ); var type = field.Type; @@ -99,9 +106,10 @@ or SpecialType.System_Int64 } } - public ColumnAttrs GetAttrs(string tableName) => Attrs - .Where(x => x.table == null || x.table == tableName) - .Aggregate(ColumnAttrs.UnSet, (xs, x) => xs | x.mask); + public ColumnAttrs GetAttrs(string tableName) => + Attrs + .Where(x => x.table == null || x.table == tableName) + .Aggregate(ColumnAttrs.UnSet, (xs, x) => xs | x.mask); // For the `TableDesc` constructor. public string GenerateColumnDef() => @@ -120,12 +128,14 @@ record TableView public TableView(TableDeclaration table, AttributeData data) { - Name = data.NamedArguments.FirstOrDefault(x => x.Key == "Name").Value.Value as string ?? table.ShortName; + Name = + data.NamedArguments.FirstOrDefault(x => x.Key == "Name").Value.Value as string + ?? table.ShortName; IsPublic = data.NamedArguments.Any(pair => pair is { Key: "Public", Value.Value: true }); - Scheduled = data.NamedArguments - .Where(pair => pair.Key == "Scheduled") + Scheduled = data + .NamedArguments.Where(pair => pair.Key == "Scheduled") .Select(pair => (string?)pair.Value.Value) .SingleOrDefault(); } @@ -138,17 +148,24 @@ record TableDeclaration : BaseTypeDeclaration public readonly EquatableArray Views; private static ColumnDeclaration[] ScheduledColumns(string tableName) => - [ - new(tableName, "ScheduledId", "ulong", "SpacetimeDB.BSATN.U64", ColumnAttrs.PrimaryKeyAuto, true), - new( - tableName, - "ScheduledAt", - "SpacetimeDB.ScheduleAt", - "SpacetimeDB.ScheduleAt.BSATN", - ColumnAttrs.UnSet, - false - ), - ]; + [ + new( + tableName, + "ScheduledId", + "ulong", + "SpacetimeDB.BSATN.U64", + ColumnAttrs.PrimaryKeyAuto, + true + ), + new( + tableName, + "ScheduledAt", + "SpacetimeDB.ScheduleAt", + "SpacetimeDB.ScheduleAt.BSATN", + ColumnAttrs.UnSet, + false + ), + ]; public TableDeclaration(GeneratorAttributeSyntaxContext context) : base(context) @@ -159,7 +176,8 @@ public TableDeclaration(GeneratorAttributeSyntaxContext context) } Visibility = context.TargetSymbol.DeclaredAccessibility; - switch (Visibility) { + switch (Visibility) + { case Accessibility.ProtectedAndInternal: case Accessibility.NotApplicable: case Accessibility.Internal: @@ -167,11 +185,10 @@ public TableDeclaration(GeneratorAttributeSyntaxContext context) break; default: throw new Exception("Table row type visibility must be public or internal."); - }; + } + ; - Views = new(context.Attributes - .Select(a => new TableView(this, a)) - .ToImmutableArray()); + Views = new(context.Attributes.Select(a => new TableView(this, a)).ToImmutableArray()); var schedules = Views.Select(t => t.Scheduled); var numSchedules = schedules.Count(); @@ -180,7 +197,9 @@ public TableDeclaration(GeneratorAttributeSyntaxContext context) var distinctSchedules = schedules.Distinct(); if (numSchedules != Views.Length || distinctSchedules.Count() != 1) { - throw new Exception("When using multiple [Table] attributes with schedule, all [Table] must have the same schedule."); + throw new Exception( + "When using multiple [Table] attributes with schedule, all [Table] must have the same schedule." + ); } Scheduled = distinctSchedules.First(); @@ -230,7 +249,9 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) } } - public IEnumerable> GenerateViews() + public IEnumerable< + KeyValuePair<(string viewName, string tableName), (string view, string getter)> + > GenerateViews() { foreach (var v in Views) { @@ -240,7 +261,10 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) var globalName = $"global::{FullName}"; var iTable = $"SpacetimeDB.Internal.ITableView<{v.Name}, {globalName}>"; - yield return new((v.Name, globalName), ($$""" + yield return new( + (v.Name, globalName), + ( + $$""" {{SyntaxFacts.GetText(Visibility)}} readonly struct {{v.Name}} : {{iTable}} { static {{globalName}} {{iTable}}.ReadGenFields(System.IO.BinaryReader reader, {{globalName}} row) { {{string.Join( @@ -261,7 +285,10 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) public void Insert({{globalName}} row) => {{iTable}}.Insert(row); {{string.Join("\n", GenerateViewFilters(v.Name, iTable))}} } - """, $"{SyntaxFacts.GetText(Visibility)} Internal.TableHandles.{v.Name} {v.Name} => new();")); + """, + $"{SyntaxFacts.GetText(Visibility)} Internal.TableHandles.{v.Name} {v.Name} => new();" + ) + ); } } @@ -345,20 +372,12 @@ public override Scope.Extensions ToExtensions() } } -record ReducerParamDeclaration : MemberDeclaration -{ - public ReducerParamDeclaration(IParameterSymbol param) - : base(param.Name, param.Type) - { - } -} - record ReducerDeclaration { public readonly string Name; public readonly string ExportName; public readonly string FullName; - public readonly EquatableArray Args; + public readonly EquatableArray Args; public readonly Scope Scope; public ReducerDeclaration(GeneratorAttributeSyntaxContext context) @@ -371,16 +390,24 @@ public ReducerDeclaration(GeneratorAttributeSyntaxContext context) { throw new Exception($"Reducer {method} must return void"); } - if (method.Parameters.FirstOrDefault()?.Type is not INamedTypeSymbol namedType || namedType.Name != "ReducerContext") + if ( + method.Parameters.FirstOrDefault()?.Type is not INamedTypeSymbol namedType + || namedType.Name != "ReducerContext" + ) { - throw new Exception($"Reducer {method} must have a first argument of type ReducerContext"); + throw new Exception( + $"Reducer {method} must have a first argument of type ReducerContext" + ); } Name = method.Name; ExportName = attr.Name ?? Name; FullName = SymbolToName(method); Args = new( - method.Parameters.Skip(1).Select(p => new ReducerParamDeclaration(p)).ToImmutableArray() + method + .Parameters.Skip(1) + .Select(p => new MemberDeclaration(p.Name, p.Type)) + .ToImmutableArray() ); Scope = new Scope(methodSyntax.Parent as MemberDeclarationSyntax); } @@ -480,7 +507,9 @@ public void Initialize(IncrementalGeneratorInitializationContext context) // Not really important outside of testing, but for testing // it matters because we commit module-bindings // so they need to match 1:1 between different langs. - var tableViews = tuple.Left.Sort((a, b) => a.Key.viewName.CompareTo(b.Key.viewName)); + var tableViews = tuple.Left.Sort( + (a, b) => a.Key.viewName.CompareTo(b.Key.viewName) + ); var addReducers = tuple.Right.Sort((a, b) => a.Key.CompareTo(b.Key)); // Don't generate the FFI boilerplate if there are no tables or reducers. if (tableViews.IsEmpty && addReducers.IsEmpty) @@ -498,7 +527,9 @@ public void Initialize(IncrementalGeneratorInitializationContext context) using System.Runtime.InteropServices; namespace SpacetimeDB { - public sealed record ReducerContext : BaseReducerContext {} + public sealed record ReducerContext : BaseReducerContext { + internal ReducerContext(Identity identity, Address? address, Random random, DateTimeOffset time) : base(identity, address, random, time) {} + } namespace Internal.TableHandles { {{string.Join("\n", tableViews.Select(v => v.Value.view))}} @@ -521,7 +552,7 @@ static class ModuleRegistration { [DynamicDependency(DynamicallyAccessedMemberTypes.PublicMethods, typeof(SpacetimeDB.Internal.Module))] #endif public static void Main() { - SpacetimeDB.Internal.Module.Initialize(new SpacetimeDB.ReducerContext()); + SpacetimeDB.Internal.Module.Initialize((identity, address, random, time) => new SpacetimeDB.ReducerContext(identity, address, random, time)); {{string.Join( "\n", diff --git a/crates/bindings-csharp/Runtime/Attrs.cs b/crates/bindings-csharp/Runtime/Attrs.cs index f6ab1fabd2..578d0293d9 100644 --- a/crates/bindings-csharp/Runtime/Attrs.cs +++ b/crates/bindings-csharp/Runtime/Attrs.cs @@ -71,5 +71,3 @@ public sealed class ReducerAttribute(string? name = null) : Attribute { public string? Name => name; } - - diff --git a/crates/bindings-csharp/Runtime/Internal/FFI.cs b/crates/bindings-csharp/Runtime/Internal/FFI.cs index 800ddf4336..444a90b6c2 100644 --- a/crates/bindings-csharp/Runtime/Internal/FFI.cs +++ b/crates/bindings-csharp/Runtime/Internal/FFI.cs @@ -169,7 +169,7 @@ out RowIter out_ [LibraryImport(StdbNamespace)] public static partial Errno _row_iter_bsatn_advance( RowIter iter_handle, - [MarshalUsing(CountElementName = nameof(buffer_len))][Out] byte[] buffer, + [MarshalUsing(CountElementName = nameof(buffer_len))] [Out] byte[] buffer, ref uint buffer_len ); diff --git a/crates/bindings-csharp/Runtime/Internal/Module.cs b/crates/bindings-csharp/Runtime/Internal/Module.cs index dca50f3994..c8d7f60ca7 100644 --- a/crates/bindings-csharp/Runtime/Internal/Module.cs +++ b/crates/bindings-csharp/Runtime/Internal/Module.cs @@ -12,8 +12,7 @@ public RawConstraintDefV8(string tableName, ushort colIndex, string colName, Col ConstraintName: $"ct_{tableName}_{colName}_{attrs}", Constraints: (byte)attrs, Columns: [colIndex] - ) - { } + ) { } } partial class RawModuleDefV8 @@ -54,9 +53,12 @@ public static class Module private static readonly RawModuleDefV8 moduleDef = new(); private static readonly List reducers = []; - private static IReducerContext? context = null; + private static Func? newContext = + null; - public static void Initialize(IReducerContext ctx) => context = ctx; + public static void Initialize( + Func ctor + ) => newContext = ctor; readonly struct TypeRegistrar() : ITypeRegistrar { @@ -190,22 +192,22 @@ public static Errno __call_reducer__( BytesSink error ) { - // Piece together the sender identity. - Runtime.SenderIdentity = Identity.From( - MemoryMarshal.AsBytes([sender_0, sender_1, sender_2, sender_3]).ToArray() - ); - - // Piece together the sender address. - Runtime.SenderAddress = Address.From(MemoryMarshal.AsBytes([address_0, address_1]).ToArray()); - - Runtime.Random = new((int)timestamp.MicrosecondsSinceEpoch); - Runtime.Time = timestamp.ToStd(); - try { + var senderIdentity = Identity.From( + MemoryMarshal.AsBytes([sender_0, sender_1, sender_2, sender_3]).ToArray() + ); + var senderAddress = Address.From( + MemoryMarshal.AsBytes([address_0, address_1]).ToArray() + ); + var random = new Random((int)timestamp.MicrosecondsSinceEpoch); + var time = timestamp.ToStd(); + + var ctx = newContext!(senderIdentity, senderAddress, random, time); + using var stream = new MemoryStream(args.Consume()); using var reader = new BinaryReader(stream); - reducers[(int)id].Invoke(reader, context!); + reducers[(int)id].Invoke(reader, ctx); if (stream.Position != stream.Length) { throw new Exception("Unrecognised extra bytes in the reducer arguments"); diff --git a/crates/bindings-csharp/Runtime/LogStopwatch.cs b/crates/bindings-csharp/Runtime/LogStopwatch.cs index 319ab2574d..effb2d5785 100644 --- a/crates/bindings-csharp/Runtime/LogStopwatch.cs +++ b/crates/bindings-csharp/Runtime/LogStopwatch.cs @@ -1,4 +1,5 @@ namespace SpacetimeDB; + using System.Text; using SpacetimeDB.Internal; diff --git a/crates/bindings-csharp/Runtime/Runtime.cs b/crates/bindings-csharp/Runtime/Runtime.cs index e15cf5c10d..a5a5082cbf 100644 --- a/crates/bindings-csharp/Runtime/Runtime.cs +++ b/crates/bindings-csharp/Runtime/Runtime.cs @@ -61,18 +61,21 @@ public AlgebraicType GetAlgebraicType(ITypeRegistrar registrar) => public abstract record BaseReducerContext : DbContext, IReducerContext where DbView : class, new() { - public Identity Sender => Runtime.SenderIdentity!; - public Address Address => Runtime.SenderAddress!; - public DateTimeOffset Time => Runtime.Time!; -} - -public static class Runtime -{ - public static Random Random { get; internal set; } = new(); - - public static Identity? SenderIdentity { get; internal set; } + public readonly Identity Sender; + public readonly Address? Address; + public readonly Random Random; + public readonly DateTimeOffset Time; - public static Address? SenderAddress { get; internal set; } - - public static DateTimeOffset Time { get; internal set; } + protected BaseReducerContext( + Identity sender, + Address? address, + Random random, + DateTimeOffset time + ) + { + Sender = sender; + Address = address; + Random = random; + Time = time; + } } From 18969142dc457581fdd294ef5fd750cf8008bd07 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Wed, 25 Sep 2024 15:16:08 -0400 Subject: [PATCH 14/27] Format --- crates/bindings-csharp/Codegen/Module.cs | 2 +- modules/sdk-test-connect-disconnect-cs/Lib.cs | 6 ++++-- 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index 7a49af340b..13695758ae 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -117,7 +117,7 @@ public string GenerateColumnDef() => // For the `Filter` constructor. public string GenerateFilterEntry() => - $"new (nameof({Name}), (w, v) => global::{FullTableName}.BSATN.{Name}.Write(w, ({Type}) v!))"; + $"new (nameof({Name}), (w, v) => BSATN.{Name}.Write(w, ({Type}) v!))"; } record TableView diff --git a/modules/sdk-test-connect-disconnect-cs/Lib.cs b/modules/sdk-test-connect-disconnect-cs/Lib.cs index 054906ed9d..542780c653 100644 --- a/modules/sdk-test-connect-disconnect-cs/Lib.cs +++ b/modules/sdk-test-connect-disconnect-cs/Lib.cs @@ -3,12 +3,14 @@ namespace SpacetimeDB.Sdk.Test.ConnectDisconnect; using SpacetimeDB; [SpacetimeDB.Table(Public = true)] -public partial struct Connected { +public partial struct Connected +{ public Identity identity; } [SpacetimeDB.Table(Public = true)] -public partial struct Disconnected { +public partial struct Disconnected +{ public Identity identity; } From 8d02568879dd7e63e8606b4190e285793c34bf60 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 09:52:21 -0400 Subject: [PATCH 15/27] Fix CI --- crates/cli/src/subcommands/generate/csharp.rs | 220 +++++++++--------- .../src/subcommands/project/csharp/Lib._cs | 12 +- 2 files changed, 117 insertions(+), 115 deletions(-) diff --git a/crates/cli/src/subcommands/generate/csharp.rs b/crates/cli/src/subcommands/generate/csharp.rs index ff02a339dc..4244f2a095 100644 --- a/crates/cli/src/subcommands/generate/csharp.rs +++ b/crates/cli/src/subcommands/generate/csharp.rs @@ -516,6 +516,7 @@ fn autogen_csharp_access_funcs_for_struct( pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &str) -> String { let func_name = &*reducer.name; + // let reducer_pascal_name = func_name.to_case(Case::Pascal); let func_name_pascal_case = func_name.to_case(Case::Pascal); let mut output = CsharpAutogen::new(namespace, &[]); @@ -527,46 +528,101 @@ pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &st "public partial class {func_name_pascal_case}ArgsStruct : IReducerArgs" ); + let mut func_params: String = String::new(); + let mut field_inits: String = String::new(); + indented_block(&mut output, |output| { + writeln!( + output, + "ReducerType IReducerArgs.ReducerType => ReducerType.{func_name_pascal_case};" + ); writeln!(output, "string IReducerArgsBase.ReducerName => \"{func_name}\";"); - writeln!(output, "bool IReducerArgs.InvokeHandler(EventContext ctx) => ctx.Reducers.Invoke{func_name_pascal_case}(ctx, this);"); + writeln!(output, "bool IReducerArgs.InvokeHandler(ReducerEvent reducerEvent) => Reducer.On{func_name_pascal_case}(reducerEvent, this);"); if !reducer.args.is_empty() { writeln!(output); } - for arg in reducer.args.iter() { + for (arg_i, arg) in reducer.args.iter().enumerate() { let name = arg .name .as_deref() .unwrap_or_else(|| panic!("reducer args should have names: {func_name}")); - let arg_type_str = ty_fmt(ctx, &arg.algebraic_type, namespace); + let arg_name = name.to_case(Case::Camel); let field_name = name.to_case(Case::Pascal); + let arg_type_str = ty_fmt(ctx, &arg.algebraic_type, namespace); + if arg_i != 0 { + func_params.push_str(", "); + field_inits.push_str(", "); + } write!(output, "public {arg_type_str} {field_name}"); // Skip default initializer if it's the same as the implicit default. if let Some(default) = default_init(ctx, &arg.algebraic_type) { write!(output, " = {default}"); } writeln!(output, ";"); + write!(func_params, "{arg_type_str} {arg_name}").unwrap(); + write!(field_inits, "{field_name} = {arg_name}").unwrap(); } }); + writeln!(output); + + writeln!(output, "public static partial class Reducer"); + indented_block(&mut output, |output| { + let delegate_separator = if !reducer.args.is_empty() { ", " } else { "" }; + writeln!( + output, + "public delegate void {func_name_pascal_case}Handler(ReducerEvent reducerEvent{delegate_separator}{func_params});" + ); + writeln!( + output, + "public static event {func_name_pascal_case}Handler? On{func_name_pascal_case}Event;" + ); + + writeln!(output); + + writeln!(output, "public static void {func_name_pascal_case}({func_params})"); + indented_block(output, |output| { + writeln!( + output, + "SpacetimeDBClient.instance.InternalCallReducer(new {func_name_pascal_case}ArgsStruct {{ {field_inits} }});" + ); + }); + writeln!(output); + + writeln!( + output, + "public static bool On{func_name_pascal_case}(ReducerEvent reducerEvent, {func_name_pascal_case}ArgsStruct args)" + ); + indented_block(output, |output| { + writeln!(output, "if (On{func_name_pascal_case}Event == null) return false;"); + writeln!(output, "On{func_name_pascal_case}Event("); + // Write out arguments one per line + { + indent_scope!(output); + write!(output, "reducerEvent"); + for (i, arg) in reducer.args.iter().enumerate() { + writeln!(output, ","); + let arg_name = arg + .name + .as_deref() + .map_or_else(|| format!("Arg{i}"), |name| name.to_case(Case::Pascal)); + write!(output, "args.{arg_name}"); + } + writeln!(output); + } + writeln!(output, ");"); + writeln!(output, "return true;"); + }); + }); + writeln!(output); + output.into_inner() } pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) -> Vec<(String, String)> { let mut results = Vec::new(); - let tables = items - .iter() - .filter_map(|i| { - if let GenItem::Table(table) = i { - Some(table) - } - else { - None - } - }); - let reducers: Vec<&ReducerDef> = items .iter() .filter_map(|i| { @@ -584,98 +640,23 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) let mut output = CsharpAutogen::new(namespace, &["SpacetimeDB.ClientApi"]); - writeln!(output, "public interface IReducerArgs : IReducerArgsBase"); + writeln!(output, "public enum ReducerType"); indented_block(&mut output, |output| { - writeln!(output, "bool InvokeHandler(EventContext ctx);"); - }); - writeln!(output); - - writeln!(output, "public sealed class RemoteTables"); - indented_block(&mut output, |output| { - for table in tables { - let name = &table.schema.table_name; - writeln!(output, "public readonly RemoteTableHandle {} = new();", name, name); + writeln!(output, "None,"); + for reducer_name in &reducer_names { + writeln!(output, "{reducer_name},"); } }); writeln!(output); - writeln!(output, "public sealed class RemoteReducers : RemoteBase"); + writeln!(output, "public interface IReducerArgs : IReducerArgsBase"); indented_block(&mut output, |output| { - for reducer in &reducers { - let func_name = &*reducer.name; - let func_name_pascal_case = func_name.to_case(Case::Pascal); - let delegate_separator = if !reducer.args.is_empty() { ", " } else { "" }; - - let mut func_params: String = String::new(); - let mut field_inits: String = String::new(); - - for (arg_i, arg) in reducer.args.iter().enumerate() { - if arg_i != 0 { - func_params.push_str(", "); - field_inits.push_str(", "); - } - - let name = arg - .name - .as_deref() - .unwrap_or_else(|| panic!("reducer args should have names: {func_name}")); - let arg_type_str = ty_fmt(ctx, &arg.algebraic_type, namespace); - let arg_name = name.to_case(Case::Camel); - let field_name = name.to_case(Case::Pascal); - - write!(func_params, "{arg_type_str} {arg_name}").unwrap(); - write!(field_inits, "{field_name} = {arg_name}").unwrap(); - } - - writeln!( - output, - "public delegate void {func_name_pascal_case}Handler(EventContext ctx{delegate_separator}{func_params});" - ); - writeln!( - output, - "public event {func_name_pascal_case}Handler? On{func_name_pascal_case};" - ); - writeln!(output); - - - writeln!(output, "public void {func_name_pascal_case}({func_params})"); - indented_block(output, |output| { - writeln!( - output, - "conn.InternalCallReducer(new {func_name_pascal_case}ArgsStruct {{ {field_inits} }});" - ); - }); - writeln!(output); - - writeln!( - output, - "public bool Invoke{func_name_pascal_case}(EventContext ctx, {func_name_pascal_case}ArgsStruct args)" - ); - indented_block(output, |output| { - writeln!(output, "if (On{func_name_pascal_case} == null) return false;"); - writeln!(output, "On{func_name_pascal_case}("); - // Write out arguments one per line - { - indent_scope!(output); - write!(output, "ctx"); - for (i, arg) in reducer.args.iter().enumerate() { - writeln!(output, ","); - let arg_name = arg - .name - .as_deref() - .map_or_else(|| format!("Arg{i}"), |name| name.to_case(Case::Pascal)); - write!(output, "args.{arg_name}"); - } - writeln!(output); - } - writeln!(output, ");"); - writeln!(output, "return true;"); - }); - } + writeln!(output, "ReducerType ReducerType {{ get; }}"); + writeln!(output, "bool InvokeHandler(ReducerEvent reducerEvent);"); }); writeln!(output); - writeln!(output, "public partial class EventContext : EventContextBase"); + writeln!(output, "public partial class ReducerEvent : ReducerEventBase"); indented_block(&mut output, |output| { writeln!(output, "public IReducerArgs? Args {{ get; }}"); writeln!(output); @@ -683,8 +664,33 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) writeln!(output); writeln!( output, - "public EventContext(DbConnection conn, TransactionUpdate update, IReducerArgs? args) : base(conn.RemoteTables, conn.RemoteReducers, update) => Args = args;" + r#"[Obsolete("ReducerType is deprecated, please match directly on type of .Args instead.")]"# ); + writeln!( + output, + "public ReducerType Reducer => Args?.ReducerType ?? ReducerType.None;" + ); + writeln!(output); + writeln!( + output, + "public ReducerEvent(IReducerArgs? args) : base() => Args = args;" + ); + writeln!( + output, + "public ReducerEvent(TransactionUpdate update, IReducerArgs? args) : base(update) => Args = args;" + ); + writeln!(output); + // Properties for reducer args + for reducer_name in &reducer_names { + writeln!( + output, + r#"[Obsolete("Accessors that implicitly cast `Args` are deprecated, please match `Args` against the desired type explicitly instead.")]"# + ); + writeln!( + output, + "public {reducer_name}ArgsStruct {reducer_name}Args => ({reducer_name}ArgsStruct)Args!;" + ); + } writeln!(output); // Event handlers. writeln!( @@ -696,18 +702,11 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) writeln!( output, - "public class DbConnection : DbConnectionBase" + "public class SpacetimeDBClient : SpacetimeDBClientBase" ); indented_block(&mut output, |output| { - writeln!(output, "public readonly RemoteTables RemoteTables = new();"); - writeln!(output, "public readonly RemoteReducers RemoteReducers = new();"); - writeln!(output); - - writeln!(output, "public DbConnection()"); + writeln!(output, "protected SpacetimeDBClient()"); indented_block(output, |output| { - writeln!(output, "RemoteReducers.Init(this);"); - writeln!(output); - for item in items { if let GenItem::Table(table) = item { writeln!( @@ -720,9 +719,12 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) }); writeln!(output); + writeln!(output, "public static readonly SpacetimeDBClient instance = new();"); + writeln!(output); + writeln!( output, - "protected override EventContext ReducerEventFromDbEvent(TransactionUpdate update)" + "protected override ReducerEvent ReducerEventFromDbEvent(TransactionUpdate update)" ); indented_block(output, |output| { writeln!(output, "var encodedArgs = update.ReducerCall.Args;"); @@ -746,7 +748,7 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) ); } writeln!(output, "}};"); - writeln!(output, "return new EventContext(this, update, args);"); + writeln!(output, "return new ReducerEvent(update, args);"); }); }); diff --git a/crates/cli/src/subcommands/project/csharp/Lib._cs b/crates/cli/src/subcommands/project/csharp/Lib._cs index 83f83490ef..197d2dda0c 100644 --- a/crates/cli/src/subcommands/project/csharp/Lib._cs +++ b/crates/cli/src/subcommands/project/csharp/Lib._cs @@ -5,24 +5,24 @@ static partial class Module [SpacetimeDB.Table] public partial struct Person { - [SpacetimeDB.Column(ColumnAttrs.Unique | ColumnAttrs.AutoInc)] + [SpacetimeDB.AutoInc] + [SpacetimeDB.PrimaryKey] public int Id; public string Name; public int Age; } [SpacetimeDB.Reducer] - public static void Add(string name, int age) + public static void Add(ReducerContext ctx, string name, int age) { - var person = new Person { Name = name, Age = age }; - person.Insert(); + var person = ctx.Db.Person.Insert(new Person { Name = name, Age = age }); Log.Info($"Inserted {person.Name} under #{person.Id}"); } [SpacetimeDB.Reducer] - public static void SayHello() + public static void SayHello(ReducerContext ctx) { - foreach (var person in Person.Iter()) + foreach (var person in ctx.Db.Person.Iter()) { Log.Info($"Hello, {person.Name}!"); } From 914fce1754ca0eecb5a6431d9abe0d328a12c29a Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 10:11:31 -0400 Subject: [PATCH 16/27] Review feedback --- crates/bindings-csharp/Codegen/Module.cs | 99 ++++++++++--------- .../Runtime/Internal/Module.cs | 2 +- crates/bindings-csharp/Runtime/Runtime.cs | 22 ----- 3 files changed, 56 insertions(+), 67 deletions(-) diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index 13695758ae..dadc5fef33 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -176,40 +176,44 @@ public TableDeclaration(GeneratorAttributeSyntaxContext context) } Visibility = context.TargetSymbol.DeclaredAccessibility; - switch (Visibility) + + var container = context.TargetSymbol; + while (container != null) { - case Accessibility.ProtectedAndInternal: - case Accessibility.NotApplicable: - case Accessibility.Internal: - case Accessibility.Public: - break; - default: - throw new Exception("Table row type visibility must be public or internal."); + switch (Visibility) + { + case Accessibility.ProtectedAndInternal: + case Accessibility.NotApplicable: + case Accessibility.Internal: + case Accessibility.Public: + break; + default: + throw new Exception( + "Table row type visibility must be public or internal, including containing types." + ); + } + ; + + container = container.ContainingType; } - ; Views = new(context.Attributes.Select(a => new TableView(this, a)).ToImmutableArray()); - var schedules = Views.Select(t => t.Scheduled); - var numSchedules = schedules.Count(); - if (numSchedules > 0) + var schedules = Views.Select(t => t.Scheduled).Distinct(); + if (schedules.Count() != 1) { - var distinctSchedules = schedules.Distinct(); - if (numSchedules != Views.Length || distinctSchedules.Count() != 1) - { - throw new Exception( - "When using multiple [Table] attributes with schedule, all [Table] must have the same schedule." - ); - } + throw new Exception( + "When using multiple [Table] attributes with schedule, all [Table] must have the same schedule." + ); + } - Scheduled = distinctSchedules.First(); - if (Scheduled != null) - { - // For scheduled tables, we append extra fields early in the pipeline, - // both to the type itself and to the BSATN information, as if they - // were part of the original declaration. - Members = new(Members.Concat(ScheduledColumns(FullName)).ToImmutableArray()); - } + Scheduled = schedules.First(); + if (Scheduled != null) + { + // For scheduled tables, we append extra fields early in the pipeline, + // both to the type itself and to the BSATN information, as if they + // were part of the original declaration. + Members = new(Members.Concat(ScheduledColumns(FullName)).ToImmutableArray()); } } @@ -249,9 +253,9 @@ public IEnumerable GenerateViewFilters(string viewName, string iTable) } } - public IEnumerable< - KeyValuePair<(string viewName, string tableName), (string view, string getter)> - > GenerateViews() + public record struct View(string viewName, string tableName, string view, string getter); + + public IEnumerable GenerateViews() { foreach (var v in Views) { @@ -262,9 +266,9 @@ public IEnumerable< var globalName = $"global::{FullName}"; var iTable = $"SpacetimeDB.Internal.ITableView<{v.Name}, {globalName}>"; yield return new( - (v.Name, globalName), - ( - $$""" + v.Name, + globalName, + $$""" {{SyntaxFacts.GetText(Visibility)}} readonly struct {{v.Name}} : {{iTable}} { static {{globalName}} {{iTable}}.ReadGenFields(System.IO.BinaryReader reader, {{globalName}} row) { {{string.Join( @@ -286,8 +290,7 @@ public IEnumerable< {{string.Join("\n", GenerateViewFilters(v.Name, iTable))}} } """, - $"{SyntaxFacts.GetText(Visibility)} Internal.TableHandles.{v.Name} {v.Name} => new();" - ) + $"{SyntaxFacts.GetText(Visibility)} Internal.TableHandles.{v.Name} {v.Name} => new();" ); } } @@ -507,9 +510,7 @@ public void Initialize(IncrementalGeneratorInitializationContext context) // Not really important outside of testing, but for testing // it matters because we commit module-bindings // so they need to match 1:1 between different langs. - var tableViews = tuple.Left.Sort( - (a, b) => a.Key.viewName.CompareTo(b.Key.viewName) - ); + var tableViews = tuple.Left.Sort((a, b) => a.viewName.CompareTo(b.viewName)); var addReducers = tuple.Right.Sort((a, b) => a.Key.CompareTo(b.Key)); // Don't generate the FFI boilerplate if there are no tables or reducers. if (tableViews.IsEmpty && addReducers.IsEmpty) @@ -527,16 +528,26 @@ public void Initialize(IncrementalGeneratorInitializationContext context) using System.Runtime.InteropServices; namespace SpacetimeDB { - public sealed record ReducerContext : BaseReducerContext { - internal ReducerContext(Identity identity, Address? address, Random random, DateTimeOffset time) : base(identity, address, random, time) {} + public sealed record ReducerContext : DbContext, Internal.IReducerContext { + public readonly Identity Sender; + public readonly Address? Address; + public readonly Random Random; + public readonly DateTimeOffset Time; + + internal ReducerContext(Identity sender, Address? address, Random random, DateTimeOffset time) { + Sender = sender; + Address = address; + Random = random; + Time = time; + } } namespace Internal.TableHandles { - {{string.Join("\n", tableViews.Select(v => v.Value.view))}} + {{string.Join("\n", tableViews.Select(v => v.view))}} } public sealed class Local { - {{string.Join("\n", tableViews.Select(v => v.Value.getter))}} + {{string.Join("\n", tableViews.Select(v => v.getter))}} } } @@ -552,7 +563,7 @@ static class ModuleRegistration { [DynamicDependency(DynamicallyAccessedMemberTypes.PublicMethods, typeof(SpacetimeDB.Internal.Module))] #endif public static void Main() { - SpacetimeDB.Internal.Module.Initialize((identity, address, random, time) => new SpacetimeDB.ReducerContext(identity, address, random, time)); + SpacetimeDB.Internal.Module.SetReducerContextConstructor((identity, address, random, time) => new SpacetimeDB.ReducerContext(identity, address, random, time)); {{string.Join( "\n", @@ -562,7 +573,7 @@ public static void Main() { )}} {{string.Join( "\n", - tableViews.Select(t => $"SpacetimeDB.Internal.Module.RegisterTable<{t.Key.tableName}>();") + tableViews.Select(t => $"SpacetimeDB.Internal.Module.RegisterTable<{t.tableName}>();") )}} } diff --git a/crates/bindings-csharp/Runtime/Internal/Module.cs b/crates/bindings-csharp/Runtime/Internal/Module.cs index c8d7f60ca7..5a4452fe60 100644 --- a/crates/bindings-csharp/Runtime/Internal/Module.cs +++ b/crates/bindings-csharp/Runtime/Internal/Module.cs @@ -56,7 +56,7 @@ public static class Module private static Func? newContext = null; - public static void Initialize( + public static void SetReducerContextConstructor( Func ctor ) => newContext = ctor; diff --git a/crates/bindings-csharp/Runtime/Runtime.cs b/crates/bindings-csharp/Runtime/Runtime.cs index a5a5082cbf..badb81a053 100644 --- a/crates/bindings-csharp/Runtime/Runtime.cs +++ b/crates/bindings-csharp/Runtime/Runtime.cs @@ -57,25 +57,3 @@ public AlgebraicType GetAlgebraicType(ITypeRegistrar registrar) => ); } } - -public abstract record BaseReducerContext : DbContext, IReducerContext - where DbView : class, new() -{ - public readonly Identity Sender; - public readonly Address? Address; - public readonly Random Random; - public readonly DateTimeOffset Time; - - protected BaseReducerContext( - Identity sender, - Address? address, - Random random, - DateTimeOffset time - ) - { - Sender = sender; - Address = address; - Random = random; - Time = time; - } -} From d644f2f54be95b62c71722f6070c5644c4dd02d9 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 10:48:43 -0400 Subject: [PATCH 17/27] Revert --- crates/cli/src/subcommands/generate/csharp.rs | 166 ++++++++++-------- 1 file changed, 90 insertions(+), 76 deletions(-) diff --git a/crates/cli/src/subcommands/generate/csharp.rs b/crates/cli/src/subcommands/generate/csharp.rs index 4244f2a095..ab37394a70 100644 --- a/crates/cli/src/subcommands/generate/csharp.rs +++ b/crates/cli/src/subcommands/generate/csharp.rs @@ -1,20 +1,36 @@ // Note: the generated code depends on APIs and interfaces from crates/bindings-csharp/BSATN.Runtime. use super::util::fmt_fn; - use std::fmt::{self, Write}; use std::ops::Deref; use convert_case::{Case, Casing}; use spacetimedb_lib::sats::{AlgebraicType, AlgebraicTypeRef, ArrayType, ProductType, SumType}; -use spacetimedb_lib::ReducerDef; +use spacetimedb_lib::{ReducerDef, TableDesc}; use spacetimedb_primitives::ColList; use spacetimedb_schema::schema::TableSchema; use super::code_indenter::CodeIndenter; -use super::{GenCtx, GenItem, TableDescHack}; +use super::{GenCtx, GenItem}; fn scalar_or_string_name(b: &AlgebraicType) -> Option<&str> { Some(match b { + + + + + + + + Expand Down + + + + + + Expand Up + + @@ -279,17 +279,13 @@ pub fn autogen_csharp_tuple(ctx: &GenCtx, name: &str, tuple: &ProductType, names + AlgebraicType::Bool => "bool", AlgebraicType::I8 => "sbyte", AlgebraicType::U8 => "byte", @@ -38,7 +54,6 @@ fn scalar_or_string_name(b: &AlgebraicType) -> Option<&str> { | AlgebraicType::Map(_) => return None, }) } - fn ty_fmt<'a>(ctx: &'a GenCtx, ty: &'a AlgebraicType, namespace: &'a str) -> impl fmt::Display + 'a { fmt_fn(move |f| match ty { ty if ty.is_identity() => f.write_str("SpacetimeDB.Identity"), @@ -95,7 +110,6 @@ fn ty_fmt<'a>(ctx: &'a GenCtx, ty: &'a AlgebraicType, namespace: &'a str) -> imp ty => f.write_str(scalar_or_string_name(ty).expect("must be a scalar/string type at this point")), }) } - fn default_init(ctx: &GenCtx, ty: &AlgebraicType) -> Option<&'static str> { match ty { // Options have a default value of null which is fine for us, and simple enums have their own default. @@ -115,40 +129,32 @@ fn default_init(ctx: &GenCtx, ty: &AlgebraicType) -> Option<&'static str> { } } } - // can maybe do something fancy with this in the future fn csharp_typename(ctx: &GenCtx, typeref: AlgebraicTypeRef) -> &str { ctx.names[typeref.idx()].as_deref().expect("tuples should have names") } - macro_rules! indent_scope { ($x:ident) => { let mut $x = $x.indented(1); }; } - struct CsharpAutogen { output: CodeIndenter, } - impl std::ops::Deref for CsharpAutogen { type Target = CodeIndenter; - fn deref(&self) -> &Self::Target { &self.output } } - impl std::ops::DerefMut for CsharpAutogen { fn deref_mut(&mut self) -> &mut Self::Target { &mut self.output } } - impl CsharpAutogen { pub fn new(namespace: &str, extra_usings: &[&str]) -> Self { let mut output = CodeIndenter::new(String::new()); - writeln!( output, "// THIS FILE IS AUTOMATICALLY GENERATED BY SPACETIMEDB. EDITS TO THIS FILE" @@ -156,10 +162,8 @@ impl CsharpAutogen { writeln!(output, "// WILL NOT BE SAVED. MODIFY TABLES IN RUST INSTEAD."); writeln!(output, "// "); writeln!(output); - writeln!(output, "#nullable enable"); writeln!(output); - writeln!(output, "using System;"); if namespace != "SpacetimeDB" { writeln!(output, "using SpacetimeDB;"); @@ -168,24 +172,19 @@ impl CsharpAutogen { writeln!(output, "using {extra_using};"); } writeln!(output); - writeln!(output, "namespace {namespace}"); writeln!(output, "{{"); - output.indent(1); Self { output } } - pub fn into_inner(mut self) -> String { self.dedent(1); writeln!(self, "}}"); self.output.into_inner() } } - pub fn autogen_csharp_sum(ctx: &GenCtx, name: &str, sum_type: &SumType, namespace: &str) -> String { let mut output = CsharpAutogen::new(namespace, &[]); - let mut sum_namespace = None; let mut sum_type_name = name.replace("r#", "").to_case(Case::Pascal); if sum_type_name.contains('.') { @@ -193,23 +192,18 @@ pub fn autogen_csharp_sum(ctx: &GenCtx, name: &str, sum_type: &SumType, namespac if split.len() != 2 { panic!("Enum names cannot contain more than one namespace prefix. Example: MyNamespace.MyEnum"); } - sum_namespace = Some(split[0].to_string().to_case(Case::Pascal)); sum_type_name = split[1].to_string().to_case(Case::Pascal); } - if let Some(sum_namespace) = &sum_namespace { writeln!(output, "public partial class {sum_namespace}"); writeln!(output, "{{"); output.indent(1); - writeln!(output, "public partial class Types"); writeln!(output, "{{"); output.indent(1); } - writeln!(output, "[SpacetimeDB.Type]"); - if sum_type.is_simple_enum() { writeln!(output, "public enum {sum_type_name}"); indented_block(&mut output, |output| { @@ -263,33 +257,50 @@ pub fn autogen_csharp_sum(ctx: &GenCtx, name: &str, sum_type: &SumType, namespac writeln!(output); writeln!(output, ")>;"); } - if sum_namespace.is_some() { for _ in 0..2 { output.dedent(1); writeln!(output, "}}"); } } - output.into_inner() } - pub fn autogen_csharp_tuple(ctx: &GenCtx, name: &str, tuple: &ProductType, namespace: &str) -> String { autogen_csharp_product_table_common(ctx, name, tuple, None, namespace) } #[allow(deprecated)] -pub fn autogen_csharp_table(ctx: &GenCtx, table: &TableDescHack, namespace: &str) -> String { +pub fn autogen_csharp_table(ctx: &GenCtx, table: &TableDesc, namespace: &str) -> String { let tuple = ctx.typespace[table.data].as_product().unwrap(); autogen_csharp_product_table_common( ctx, csharp_typename(ctx, table.data), tuple, - Some(table.schema.clone()), + Some( + TableSchema::from_def(0.into(), table.schema.clone()) + .validated() + .expect("Failed to generate table due to validation errors"), + ), namespace, ) } + + + + + + + Expand Down + + + + + + Expand Up + + @@ -317,7 +313,7 @@ fn autogen_csharp_product_table_common( + fn autogen_csharp_product_table_common( ctx: &GenCtx, name: &str, @@ -305,7 +316,6 @@ fn autogen_csharp_product_table_common( "System.Runtime.Serialization", ], ); - writeln!(output, "[SpacetimeDB.Type]"); writeln!(output, "[DataContract]"); write!(output, "public partial class {name}"); @@ -313,10 +323,27 @@ fn autogen_csharp_product_table_common( write!( output, " : SpacetimeDB.{parent}<{name}, {namespace}.ReducerEvent>", - parent = if schema.primary_key.is_some() { + parent = if schema.pk().is_some() { "DatabaseTableWithPrimaryKey" } else { "DatabaseTable" + + + + + + + + Expand Down + + + + + + Expand Up + + @@ -383,7 +379,7 @@ fn autogen_csharp_product_table_common( + } ); } @@ -331,18 +358,13 @@ fn autogen_csharp_product_table_common( .as_ref() .expect("autogen'd tuples should have field names") .replace("r#", ""); - writeln!(output, "[DataMember(Name = \"{orig_name}\")]"); - let field_name = orig_name.to_case(Case::Pascal); let ty = ty_fmt(ctx, &field.algebraic_type, namespace).to_string(); - writeln!(output, "public {ty} {field_name};"); - (field_name, ty) }) .collect::>(); - // Generate fully-parameterized constructor. writeln!(output); writeln!(output, "public {name}("); @@ -363,7 +385,6 @@ fn autogen_csharp_product_table_common( } }); writeln!(output); - // Generate default constructor (if the one above is not already parameterless). if !fields.is_empty() { writeln!(output, "public {name}()"); @@ -379,10 +400,27 @@ fn autogen_csharp_product_table_common( // If this is a table, we want to generate event accessor and indexes if let Some(schema) = &schema { - let constraints = schema.backcompat_column_constraints(); + let constraints = schema.column_constraints(); let mut unique_indexes = Vec::new(); // Declare custom index dictionaries for col in schema.columns() { + + + + + + + + Expand Down + + + + + + Expand Up + + @@ -450,7 +446,7 @@ fn autogen_csharp_access_funcs_for_struct( + let field_name = col.col_name.replace("r#", "").to_case(Case::Pascal); if !constraints[&ColList::new(col.col_pos)].has_unique() { continue; @@ -421,24 +459,20 @@ fn autogen_csharp_product_table_common( }); writeln!(output); } - // If this is a table, we want to include functions for accessing the table data // Insert the funcs for accessing this struct autogen_csharp_access_funcs_for_struct(output, name, product_type, name, schema); writeln!(output); } }); - output.into_inner() } - fn indented_block(output: &mut CodeIndenter, f: impl FnOnce(&mut CodeIndenter) -> R) -> R { writeln!(output, "{{"); let res = f(&mut output.indented(1)); writeln!(output, "}}"); res } - fn autogen_csharp_access_funcs_for_struct( output: &mut CodeIndenter, struct_name_pascal_case: &str, @@ -446,15 +480,25 @@ fn autogen_csharp_access_funcs_for_struct( _table_name: &str, schema: &TableSchema, ) { - let constraints = schema.backcompat_column_constraints(); + let constraints = schema.column_constraints(); for col in schema.columns() { let is_unique = constraints[&ColList::new(col.col_pos)].has_unique(); + + + + + + + + Expand Down + + + let field = &product_type.elements[col.col_pos.idx()]; let field_name = field.name.as_ref().expect("autogen'd tuples should have field names"); let field_type = &field.algebraic_type; let csharp_field_name_pascal = field_name.replace("r#", "").to_case(Case::Pascal); - let csharp_field_type = match field_type { AlgebraicType::Product(product) => { if product.is_identity() { @@ -471,7 +515,6 @@ fn autogen_csharp_access_funcs_for_struct( _ => continue, }, }; - if is_unique { writeln!( output, @@ -486,7 +529,6 @@ fn autogen_csharp_access_funcs_for_struct( }); writeln!(output); } - writeln!( output, "public static IEnumerable<{struct_name_pascal_case}> FilterBy{csharp_field_name_pascal}({csharp_field_type} value)" @@ -504,7 +546,6 @@ fn autogen_csharp_access_funcs_for_struct( }); writeln!(output); } - if let Some(primary_col_index) = schema.pk() { writeln!( output, @@ -513,24 +554,19 @@ fn autogen_csharp_access_funcs_for_struct( ); } } - pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &str) -> String { let func_name = &*reducer.name; // let reducer_pascal_name = func_name.to_case(Case::Pascal); let func_name_pascal_case = func_name.to_case(Case::Pascal); - let mut output = CsharpAutogen::new(namespace, &[]); - //Args struct writeln!(output, "[SpacetimeDB.Type]"); writeln!( output, "public partial class {func_name_pascal_case}ArgsStruct : IReducerArgs" ); - let mut func_params: String = String::new(); let mut field_inits: String = String::new(); - indented_block(&mut output, |output| { writeln!( output, @@ -549,7 +585,6 @@ pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &st let arg_name = name.to_case(Case::Camel); let field_name = name.to_case(Case::Pascal); let arg_type_str = ty_fmt(ctx, &arg.algebraic_type, namespace); - if arg_i != 0 { func_params.push_str(", "); field_inits.push_str(", "); @@ -564,9 +599,7 @@ pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &st write!(field_inits, "{field_name} = {arg_name}").unwrap(); } }); - writeln!(output); - writeln!(output, "public static partial class Reducer"); indented_block(&mut output, |output| { let delegate_separator = if !reducer.args.is_empty() { ", " } else { "" }; @@ -578,9 +611,7 @@ pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &st output, "public static event {func_name_pascal_case}Handler? On{func_name_pascal_case}Event;" ); - writeln!(output); - writeln!(output, "public static void {func_name_pascal_case}({func_params})"); indented_block(output, |output| { writeln!( @@ -589,7 +620,6 @@ pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &st ); }); writeln!(output); - writeln!( output, "public static bool On{func_name_pascal_case}(ReducerEvent reducerEvent, {func_name_pascal_case}ArgsStruct args)" @@ -616,13 +646,10 @@ pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &st }); }); writeln!(output); - output.into_inner() } - pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) -> Vec<(String, String)> { let mut results = Vec::new(); - let reducers: Vec<&ReducerDef> = items .iter() .filter_map(|i| { @@ -637,9 +664,7 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) .iter() .map(|reducer| reducer.name.deref().to_case(Case::Pascal)) .collect(); - let mut output = CsharpAutogen::new(namespace, &["SpacetimeDB.ClientApi"]); - writeln!(output, "public enum ReducerType"); indented_block(&mut output, |output| { writeln!(output, "None,"); @@ -648,14 +673,12 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) } }); writeln!(output); - writeln!(output, "public interface IReducerArgs : IReducerArgsBase"); indented_block(&mut output, |output| { writeln!(output, "ReducerType ReducerType {{ get; }}"); writeln!(output, "bool InvokeHandler(ReducerEvent reducerEvent);"); }); writeln!(output); - writeln!(output, "public partial class ReducerEvent : ReducerEventBase"); indented_block(&mut output, |output| { writeln!(output, "public IReducerArgs? Args {{ get; }}"); @@ -699,7 +722,6 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) ); }); writeln!(output); - writeln!( output, "public class SpacetimeDBClient : SpacetimeDBClientBase" @@ -718,10 +740,8 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) } }); writeln!(output); - writeln!(output, "public static readonly SpacetimeDBClient instance = new();"); writeln!(output); - writeln!( output, "protected override ReducerEvent ReducerEventFromDbEvent(TransactionUpdate update)" @@ -751,14 +771,10 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) writeln!(output, "return new ReducerEvent(update, args);"); }); }); - results.push(("_Globals/SpacetimeDBClient.cs".to_owned(), output.into_inner())); - // Note: Unity requires script classes to have the same name as the file they are in. // That's why we're generating a separate file for Unity-specific code. - let mut output = CsharpAutogen::new(namespace, &[]); - writeln!(output, "// This class is only used in Unity projects."); writeln!( output, @@ -774,8 +790,6 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) writeln!(output, "private void Update() => SpacetimeDBClient.instance.Update();"); }); writeln!(output, "#endif"); - results.push(("_Globals/UnityNetworkManager.cs".to_owned(), output.into_inner())); - results -} +} \ No newline at end of file From 56709dd952ddce20b65673360ad0b3d212d58829 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 11:07:14 -0400 Subject: [PATCH 18/27] Fixme --- crates/cli/src/subcommands/generate/csharp.rs | 148 ++++++++---------- 1 file changed, 69 insertions(+), 79 deletions(-) diff --git a/crates/cli/src/subcommands/generate/csharp.rs b/crates/cli/src/subcommands/generate/csharp.rs index ab37394a70..58f102a1ef 100644 --- a/crates/cli/src/subcommands/generate/csharp.rs +++ b/crates/cli/src/subcommands/generate/csharp.rs @@ -1,5 +1,6 @@ // Note: the generated code depends on APIs and interfaces from crates/bindings-csharp/BSATN.Runtime. use super::util::fmt_fn; + use std::fmt::{self, Write}; use std::ops::Deref; @@ -14,23 +15,6 @@ use super::{GenCtx, GenItem}; fn scalar_or_string_name(b: &AlgebraicType) -> Option<&str> { Some(match b { - - - - - - - - Expand Down - - - - - - Expand Up - - @@ -279,17 +279,13 @@ pub fn autogen_csharp_tuple(ctx: &GenCtx, name: &str, tuple: &ProductType, names - AlgebraicType::Bool => "bool", AlgebraicType::I8 => "sbyte", AlgebraicType::U8 => "byte", @@ -54,6 +38,7 @@ fn scalar_or_string_name(b: &AlgebraicType) -> Option<&str> { | AlgebraicType::Map(_) => return None, }) } + fn ty_fmt<'a>(ctx: &'a GenCtx, ty: &'a AlgebraicType, namespace: &'a str) -> impl fmt::Display + 'a { fmt_fn(move |f| match ty { ty if ty.is_identity() => f.write_str("SpacetimeDB.Identity"), @@ -110,6 +95,7 @@ fn ty_fmt<'a>(ctx: &'a GenCtx, ty: &'a AlgebraicType, namespace: &'a str) -> imp ty => f.write_str(scalar_or_string_name(ty).expect("must be a scalar/string type at this point")), }) } + fn default_init(ctx: &GenCtx, ty: &AlgebraicType) -> Option<&'static str> { match ty { // Options have a default value of null which is fine for us, and simple enums have their own default. @@ -129,32 +115,40 @@ fn default_init(ctx: &GenCtx, ty: &AlgebraicType) -> Option<&'static str> { } } } + // can maybe do something fancy with this in the future fn csharp_typename(ctx: &GenCtx, typeref: AlgebraicTypeRef) -> &str { ctx.names[typeref.idx()].as_deref().expect("tuples should have names") } + macro_rules! indent_scope { ($x:ident) => { let mut $x = $x.indented(1); }; } + struct CsharpAutogen { output: CodeIndenter, } + impl std::ops::Deref for CsharpAutogen { type Target = CodeIndenter; + fn deref(&self) -> &Self::Target { &self.output } } + impl std::ops::DerefMut for CsharpAutogen { fn deref_mut(&mut self) -> &mut Self::Target { &mut self.output } } + impl CsharpAutogen { pub fn new(namespace: &str, extra_usings: &[&str]) -> Self { let mut output = CodeIndenter::new(String::new()); + writeln!( output, "// THIS FILE IS AUTOMATICALLY GENERATED BY SPACETIMEDB. EDITS TO THIS FILE" @@ -162,8 +156,10 @@ impl CsharpAutogen { writeln!(output, "// WILL NOT BE SAVED. MODIFY TABLES IN RUST INSTEAD."); writeln!(output, "// "); writeln!(output); + writeln!(output, "#nullable enable"); writeln!(output); + writeln!(output, "using System;"); if namespace != "SpacetimeDB" { writeln!(output, "using SpacetimeDB;"); @@ -172,19 +168,24 @@ impl CsharpAutogen { writeln!(output, "using {extra_using};"); } writeln!(output); + writeln!(output, "namespace {namespace}"); writeln!(output, "{{"); + output.indent(1); Self { output } } + pub fn into_inner(mut self) -> String { self.dedent(1); writeln!(self, "}}"); self.output.into_inner() } } + pub fn autogen_csharp_sum(ctx: &GenCtx, name: &str, sum_type: &SumType, namespace: &str) -> String { let mut output = CsharpAutogen::new(namespace, &[]); + let mut sum_namespace = None; let mut sum_type_name = name.replace("r#", "").to_case(Case::Pascal); if sum_type_name.contains('.') { @@ -192,18 +193,23 @@ pub fn autogen_csharp_sum(ctx: &GenCtx, name: &str, sum_type: &SumType, namespac if split.len() != 2 { panic!("Enum names cannot contain more than one namespace prefix. Example: MyNamespace.MyEnum"); } + sum_namespace = Some(split[0].to_string().to_case(Case::Pascal)); sum_type_name = split[1].to_string().to_case(Case::Pascal); } + if let Some(sum_namespace) = &sum_namespace { writeln!(output, "public partial class {sum_namespace}"); writeln!(output, "{{"); output.indent(1); + writeln!(output, "public partial class Types"); writeln!(output, "{{"); output.indent(1); } + writeln!(output, "[SpacetimeDB.Type]"); + if sum_type.is_simple_enum() { writeln!(output, "public enum {sum_type_name}"); indented_block(&mut output, |output| { @@ -257,14 +263,17 @@ pub fn autogen_csharp_sum(ctx: &GenCtx, name: &str, sum_type: &SumType, namespac writeln!(output); writeln!(output, ")>;"); } + if sum_namespace.is_some() { for _ in 0..2 { output.dedent(1); writeln!(output, "}}"); } } + output.into_inner() } + pub fn autogen_csharp_tuple(ctx: &GenCtx, name: &str, tuple: &ProductType, namespace: &str) -> String { autogen_csharp_product_table_common(ctx, name, tuple, None, namespace) } @@ -285,22 +294,6 @@ pub fn autogen_csharp_table(ctx: &GenCtx, table: &TableDesc, namespace: &str) -> ) } - - - - - - - Expand Down - - - - - - Expand Up - - @@ -317,7 +313,7 @@ fn autogen_csharp_product_table_common( - fn autogen_csharp_product_table_common( ctx: &GenCtx, name: &str, @@ -316,6 +309,7 @@ fn autogen_csharp_product_table_common( "System.Runtime.Serialization", ], ); + writeln!(output, "[SpacetimeDB.Type]"); writeln!(output, "[DataContract]"); write!(output, "public partial class {name}"); @@ -327,23 +321,6 @@ fn autogen_csharp_product_table_common( "DatabaseTableWithPrimaryKey" } else { "DatabaseTable" - - - - - - - - Expand Down - - - - - - Expand Up - - @@ -383,7 +379,7 @@ fn autogen_csharp_product_table_common( - } ); } @@ -358,13 +335,18 @@ fn autogen_csharp_product_table_common( .as_ref() .expect("autogen'd tuples should have field names") .replace("r#", ""); + writeln!(output, "[DataMember(Name = \"{orig_name}\")]"); + let field_name = orig_name.to_case(Case::Pascal); let ty = ty_fmt(ctx, &field.algebraic_type, namespace).to_string(); + writeln!(output, "public {ty} {field_name};"); + (field_name, ty) }) .collect::>(); + // Generate fully-parameterized constructor. writeln!(output); writeln!(output, "public {name}("); @@ -385,6 +367,7 @@ fn autogen_csharp_product_table_common( } }); writeln!(output); + // Generate default constructor (if the one above is not already parameterless). if !fields.is_empty() { writeln!(output, "public {name}()"); @@ -404,23 +387,6 @@ fn autogen_csharp_product_table_common( let mut unique_indexes = Vec::new(); // Declare custom index dictionaries for col in schema.columns() { - - - - - - - - Expand Down - - - - - - Expand Up - - @@ -450,7 +446,7 @@ fn autogen_csharp_access_funcs_for_struct( - let field_name = col.col_name.replace("r#", "").to_case(Case::Pascal); if !constraints[&ColList::new(col.col_pos)].has_unique() { continue; @@ -459,20 +425,24 @@ fn autogen_csharp_product_table_common( }); writeln!(output); } + // If this is a table, we want to include functions for accessing the table data // Insert the funcs for accessing this struct autogen_csharp_access_funcs_for_struct(output, name, product_type, name, schema); writeln!(output); } }); + output.into_inner() } + fn indented_block(output: &mut CodeIndenter, f: impl FnOnce(&mut CodeIndenter) -> R) -> R { writeln!(output, "{{"); let res = f(&mut output.indented(1)); writeln!(output, "}}"); res } + fn autogen_csharp_access_funcs_for_struct( output: &mut CodeIndenter, struct_name_pascal_case: &str, @@ -484,21 +454,11 @@ fn autogen_csharp_access_funcs_for_struct( for col in schema.columns() { let is_unique = constraints[&ColList::new(col.col_pos)].has_unique(); - - - - - - - - Expand Down - - - let field = &product_type.elements[col.col_pos.idx()]; let field_name = field.name.as_ref().expect("autogen'd tuples should have field names"); let field_type = &field.algebraic_type; let csharp_field_name_pascal = field_name.replace("r#", "").to_case(Case::Pascal); + let csharp_field_type = match field_type { AlgebraicType::Product(product) => { if product.is_identity() { @@ -515,6 +475,7 @@ fn autogen_csharp_access_funcs_for_struct( _ => continue, }, }; + if is_unique { writeln!( output, @@ -529,6 +490,7 @@ fn autogen_csharp_access_funcs_for_struct( }); writeln!(output); } + writeln!( output, "public static IEnumerable<{struct_name_pascal_case}> FilterBy{csharp_field_name_pascal}({csharp_field_type} value)" @@ -546,6 +508,7 @@ fn autogen_csharp_access_funcs_for_struct( }); writeln!(output); } + if let Some(primary_col_index) = schema.pk() { writeln!( output, @@ -554,19 +517,24 @@ fn autogen_csharp_access_funcs_for_struct( ); } } + pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &str) -> String { let func_name = &*reducer.name; // let reducer_pascal_name = func_name.to_case(Case::Pascal); let func_name_pascal_case = func_name.to_case(Case::Pascal); + let mut output = CsharpAutogen::new(namespace, &[]); + //Args struct writeln!(output, "[SpacetimeDB.Type]"); writeln!( output, "public partial class {func_name_pascal_case}ArgsStruct : IReducerArgs" ); + let mut func_params: String = String::new(); let mut field_inits: String = String::new(); + indented_block(&mut output, |output| { writeln!( output, @@ -585,6 +553,7 @@ pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &st let arg_name = name.to_case(Case::Camel); let field_name = name.to_case(Case::Pascal); let arg_type_str = ty_fmt(ctx, &arg.algebraic_type, namespace); + if arg_i != 0 { func_params.push_str(", "); field_inits.push_str(", "); @@ -599,7 +568,9 @@ pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &st write!(field_inits, "{field_name} = {arg_name}").unwrap(); } }); + writeln!(output); + writeln!(output, "public static partial class Reducer"); indented_block(&mut output, |output| { let delegate_separator = if !reducer.args.is_empty() { ", " } else { "" }; @@ -611,7 +582,9 @@ pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &st output, "public static event {func_name_pascal_case}Handler? On{func_name_pascal_case}Event;" ); + writeln!(output); + writeln!(output, "public static void {func_name_pascal_case}({func_params})"); indented_block(output, |output| { writeln!( @@ -620,6 +593,7 @@ pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &st ); }); writeln!(output); + writeln!( output, "public static bool On{func_name_pascal_case}(ReducerEvent reducerEvent, {func_name_pascal_case}ArgsStruct args)" @@ -646,10 +620,13 @@ pub fn autogen_csharp_reducer(ctx: &GenCtx, reducer: &ReducerDef, namespace: &st }); }); writeln!(output); + output.into_inner() } + pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) -> Vec<(String, String)> { let mut results = Vec::new(); + let reducers: Vec<&ReducerDef> = items .iter() .filter_map(|i| { @@ -664,7 +641,9 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) .iter() .map(|reducer| reducer.name.deref().to_case(Case::Pascal)) .collect(); + let mut output = CsharpAutogen::new(namespace, &["SpacetimeDB.ClientApi"]); + writeln!(output, "public enum ReducerType"); indented_block(&mut output, |output| { writeln!(output, "None,"); @@ -673,12 +652,14 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) } }); writeln!(output); + writeln!(output, "public interface IReducerArgs : IReducerArgsBase"); indented_block(&mut output, |output| { writeln!(output, "ReducerType ReducerType {{ get; }}"); writeln!(output, "bool InvokeHandler(ReducerEvent reducerEvent);"); }); writeln!(output); + writeln!(output, "public partial class ReducerEvent : ReducerEventBase"); indented_block(&mut output, |output| { writeln!(output, "public IReducerArgs? Args {{ get; }}"); @@ -722,6 +703,7 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) ); }); writeln!(output); + writeln!( output, "public class SpacetimeDBClient : SpacetimeDBClientBase" @@ -740,8 +722,10 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) } }); writeln!(output); + writeln!(output, "public static readonly SpacetimeDBClient instance = new();"); writeln!(output); + writeln!( output, "protected override ReducerEvent ReducerEventFromDbEvent(TransactionUpdate update)" @@ -771,10 +755,14 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) writeln!(output, "return new ReducerEvent(update, args);"); }); }); + results.push(("_Globals/SpacetimeDBClient.cs".to_owned(), output.into_inner())); + // Note: Unity requires script classes to have the same name as the file they are in. // That's why we're generating a separate file for Unity-specific code. + let mut output = CsharpAutogen::new(namespace, &[]); + writeln!(output, "// This class is only used in Unity projects."); writeln!( output, @@ -790,6 +778,8 @@ pub fn autogen_csharp_globals(ctx: &GenCtx, items: &[GenItem], namespace: &str) writeln!(output, "private void Update() => SpacetimeDBClient.instance.Update();"); }); writeln!(output, "#endif"); + results.push(("_Globals/UnityNetworkManager.cs".to_owned(), output.into_inner())); + results -} \ No newline at end of file +} From 7af0869408b6c1954f6af82a3601a50e26ebc8bc Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 11:28:23 -0400 Subject: [PATCH 19/27] autogen files --- .../src/module_bindings/mod.rs | 20 +------------------ 1 file changed, 1 insertion(+), 19 deletions(-) diff --git a/crates/sdk/tests/connect_disconnect_client/src/module_bindings/mod.rs b/crates/sdk/tests/connect_disconnect_client/src/module_bindings/mod.rs index 94ec48f210..4721e2a8f9 100644 --- a/crates/sdk/tests/connect_disconnect_client/src/module_bindings/mod.rs +++ b/crates/sdk/tests/connect_disconnect_client/src/module_bindings/mod.rs @@ -22,20 +22,13 @@ use std::sync::Arc; pub mod connected; pub mod disconnected; -pub mod on_connect_reducer; -pub mod on_disconnect_reducer; pub use connected::*; pub use disconnected::*; -pub use on_connect_reducer::*; -pub use on_disconnect_reducer::*; #[allow(unused)] #[derive(Serialize, Deserialize, Clone, PartialEq, Debug)] -pub enum ReducerEvent { - OnConnect(on_connect_reducer::OnConnectArgs), - OnDisconnect(on_disconnect_reducer::OnDisconnectArgs), -} +pub enum ReducerEvent {} #[allow(unused)] pub struct Module; @@ -76,17 +69,6 @@ impl SpacetimeModule for Module { let reducer_call = &event.reducer_call; #[allow(clippy::match_single_binding)] match &reducer_call.reducer_name[..] { - "OnConnect" => _reducer_callbacks.handle_event_of_type::( - event, - _state, - ReducerEvent::OnConnect, - ), - "OnDisconnect" => _reducer_callbacks - .handle_event_of_type::( - event, - _state, - ReducerEvent::OnDisconnect, - ), unknown => { spacetimedb_sdk::log::error!("Event on an unknown reducer: {:?}", unknown); None From 4393546193b8ab28073a61acf070197ae73ba470 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 11:46:05 -0400 Subject: [PATCH 20/27] verified --- .../server/snapshots/Module#FFI.verified.cs | 16 ++- .../snapshots/Module#PublicTable.verified.cs | 121 +++++------------- ...Module#Timers.SendMessageTimer.verified.cs | 17 +-- 3 files changed, 46 insertions(+), 108 deletions(-) diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs index 75e469fab2..09a9df1b9d 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs @@ -8,15 +8,25 @@ namespace SpacetimeDB { - public sealed record ReducerContext : BaseReducerContext + public sealed record ReducerContext : DbContext, Internal.IReducerContext { + public readonly Identity Sender; + public readonly Address? Address; + public readonly Random Random; + public readonly DateTimeOffset Time; + internal ReducerContext( - Identity identity, + Identity sender, Address? address, Random random, DateTimeOffset time ) - : base(identity, address, random, time) { } + { + Sender = sender; + Address = address; + Random = random; + Time = time; + } } namespace Internal.TableHandles diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs index 08d7e77880..7a1e03c156 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PublicTable.verified.cs @@ -274,137 +274,76 @@ SpacetimeDB.BSATN.ITypeRegistrar registrar static SpacetimeDB.Internal.Filter SpacetimeDB.Internal.ITable.CreateFilter() => new( [ - new(nameof(Id), (w, v) => global::PublicTable.BSATN.Id.Write(w, (int)v!)), - new( - nameof(ByteField), - (w, v) => global::PublicTable.BSATN.ByteField.Write(w, (byte)v!) - ), - new( - nameof(UshortField), - (w, v) => global::PublicTable.BSATN.UshortField.Write(w, (ushort)v!) - ), - new( - nameof(UintField), - (w, v) => global::PublicTable.BSATN.UintField.Write(w, (uint)v!) - ), - new( - nameof(UlongField), - (w, v) => global::PublicTable.BSATN.UlongField.Write(w, (ulong)v!) - ), + new(nameof(Id), (w, v) => BSATN.Id.Write(w, (int)v!)), + new(nameof(ByteField), (w, v) => BSATN.ByteField.Write(w, (byte)v!)), + new(nameof(UshortField), (w, v) => BSATN.UshortField.Write(w, (ushort)v!)), + new(nameof(UintField), (w, v) => BSATN.UintField.Write(w, (uint)v!)), + new(nameof(UlongField), (w, v) => BSATN.UlongField.Write(w, (ulong)v!)), new( nameof(UInt128Field), - (w, v) => global::PublicTable.BSATN.UInt128Field.Write(w, (System.UInt128)v!) - ), - new( - nameof(U128Field), - (w, v) => global::PublicTable.BSATN.U128Field.Write(w, (SpacetimeDB.U128)v!) - ), - new( - nameof(U256Field), - (w, v) => global::PublicTable.BSATN.U256Field.Write(w, (SpacetimeDB.U256)v!) - ), - new( - nameof(SbyteField), - (w, v) => global::PublicTable.BSATN.SbyteField.Write(w, (sbyte)v!) - ), - new( - nameof(ShortField), - (w, v) => global::PublicTable.BSATN.ShortField.Write(w, (short)v!) - ), - new( - nameof(IntField), - (w, v) => global::PublicTable.BSATN.IntField.Write(w, (int)v!) - ), - new( - nameof(LongField), - (w, v) => global::PublicTable.BSATN.LongField.Write(w, (long)v!) - ), - new( - nameof(Int128Field), - (w, v) => global::PublicTable.BSATN.Int128Field.Write(w, (System.Int128)v!) - ), - new( - nameof(I128Field), - (w, v) => global::PublicTable.BSATN.I128Field.Write(w, (SpacetimeDB.I128)v!) - ), - new( - nameof(I256Field), - (w, v) => global::PublicTable.BSATN.I256Field.Write(w, (SpacetimeDB.I256)v!) - ), - new( - nameof(BoolField), - (w, v) => global::PublicTable.BSATN.BoolField.Write(w, (bool)v!) - ), - new( - nameof(FloatField), - (w, v) => global::PublicTable.BSATN.FloatField.Write(w, (float)v!) - ), - new( - nameof(DoubleField), - (w, v) => global::PublicTable.BSATN.DoubleField.Write(w, (double)v!) - ), - new( - nameof(StringField), - (w, v) => global::PublicTable.BSATN.StringField.Write(w, (string)v!) + (w, v) => BSATN.UInt128Field.Write(w, (System.UInt128)v!) ), + new(nameof(U128Field), (w, v) => BSATN.U128Field.Write(w, (SpacetimeDB.U128)v!)), + new(nameof(U256Field), (w, v) => BSATN.U256Field.Write(w, (SpacetimeDB.U256)v!)), + new(nameof(SbyteField), (w, v) => BSATN.SbyteField.Write(w, (sbyte)v!)), + new(nameof(ShortField), (w, v) => BSATN.ShortField.Write(w, (short)v!)), + new(nameof(IntField), (w, v) => BSATN.IntField.Write(w, (int)v!)), + new(nameof(LongField), (w, v) => BSATN.LongField.Write(w, (long)v!)), + new(nameof(Int128Field), (w, v) => BSATN.Int128Field.Write(w, (System.Int128)v!)), + new(nameof(I128Field), (w, v) => BSATN.I128Field.Write(w, (SpacetimeDB.I128)v!)), + new(nameof(I256Field), (w, v) => BSATN.I256Field.Write(w, (SpacetimeDB.I256)v!)), + new(nameof(BoolField), (w, v) => BSATN.BoolField.Write(w, (bool)v!)), + new(nameof(FloatField), (w, v) => BSATN.FloatField.Write(w, (float)v!)), + new(nameof(DoubleField), (w, v) => BSATN.DoubleField.Write(w, (double)v!)), + new(nameof(StringField), (w, v) => BSATN.StringField.Write(w, (string)v!)), new( nameof(IdentityField), - (w, v) => - global::PublicTable.BSATN.IdentityField.Write(w, (SpacetimeDB.Identity)v!) + (w, v) => BSATN.IdentityField.Write(w, (SpacetimeDB.Identity)v!) ), new( nameof(AddressField), - (w, v) => - global::PublicTable.BSATN.AddressField.Write(w, (SpacetimeDB.Address)v!) + (w, v) => BSATN.AddressField.Write(w, (SpacetimeDB.Address)v!) ), new( nameof(CustomStructField), - (w, v) => global::PublicTable.BSATN.CustomStructField.Write(w, (CustomStruct)v!) + (w, v) => BSATN.CustomStructField.Write(w, (CustomStruct)v!) ), new( nameof(CustomClassField), - (w, v) => global::PublicTable.BSATN.CustomClassField.Write(w, (CustomClass)v!) + (w, v) => BSATN.CustomClassField.Write(w, (CustomClass)v!) ), new( nameof(CustomEnumField), - (w, v) => global::PublicTable.BSATN.CustomEnumField.Write(w, (CustomEnum)v!) + (w, v) => BSATN.CustomEnumField.Write(w, (CustomEnum)v!) ), new( nameof(CustomTaggedEnumField), - (w, v) => - global::PublicTable.BSATN.CustomTaggedEnumField.Write( - w, - (CustomTaggedEnum)v! - ) + (w, v) => BSATN.CustomTaggedEnumField.Write(w, (CustomTaggedEnum)v!) ), new( nameof(ListField), - (w, v) => - global::PublicTable.BSATN.ListField.Write( - w, - (System.Collections.Generic.List)v! - ) + (w, v) => BSATN.ListField.Write(w, (System.Collections.Generic.List)v!) ), new( nameof(DictionaryField), (w, v) => - global::PublicTable.BSATN.DictionaryField.Write( + BSATN.DictionaryField.Write( w, (System.Collections.Generic.Dictionary)v! ) ), new( nameof(NullableValueField), - (w, v) => global::PublicTable.BSATN.NullableValueField.Write(w, (int?)v!) + (w, v) => BSATN.NullableValueField.Write(w, (int?)v!) ), new( nameof(NullableReferenceField), - (w, v) => global::PublicTable.BSATN.NullableReferenceField.Write(w, (string?)v!) + (w, v) => BSATN.NullableReferenceField.Write(w, (string?)v!) ), new( nameof(ComplexNestedField), (w, v) => - global::PublicTable.BSATN.ComplexNestedField.Write( + BSATN.ComplexNestedField.Write( w, (System.Collections.Generic.Dictionary< CustomEnum, diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs index b83a761968..26f8b11a88 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#Timers.SendMessageTimer.verified.cs @@ -94,22 +94,11 @@ SpacetimeDB.BSATN.ITypeRegistrar registrar static SpacetimeDB.Internal.Filter SpacetimeDB.Internal.ITable.CreateFilter() => new( [ - new( - nameof(Text), - (w, v) => global::Timers.SendMessageTimer.BSATN.Text.Write(w, (string)v!) - ), - new( - nameof(ScheduledId), - (w, v) => - global::Timers.SendMessageTimer.BSATN.ScheduledId.Write(w, (ulong)v!) - ), + new(nameof(Text), (w, v) => BSATN.Text.Write(w, (string)v!)), + new(nameof(ScheduledId), (w, v) => BSATN.ScheduledId.Write(w, (ulong)v!)), new( nameof(ScheduledAt), - (w, v) => - global::Timers.SendMessageTimer.BSATN.ScheduledAt.Write( - w, - (SpacetimeDB.ScheduleAt)v! - ) + (w, v) => BSATN.ScheduledAt.Write(w, (SpacetimeDB.ScheduleAt)v!) ) ] ); From d25639823b43bb5611ea04d4d169fd88b069bfaf Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 12:01:12 -0400 Subject: [PATCH 21/27] oops --- .../fixtures/server/snapshots/Module#FFI.verified.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs index 09a9df1b9d..cb2fb1d8a9 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs @@ -463,7 +463,7 @@ public void Invoke(BinaryReader reader, SpacetimeDB.Internal.IReducerContext ctx #endif public static void Main() { - SpacetimeDB.Internal.Module.Initialize( + SpacetimeDB.Internal.Module.SetReducerContextConstructor( (identity, address, random, time) => new SpacetimeDB.ReducerContext(identity, address, random, time) ); From e768556f153328dc70f2f714fa7606acbb556bc3 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 12:19:12 -0400 Subject: [PATCH 22/27] public project Module --- crates/cli/src/subcommands/project/csharp/Lib._cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/cli/src/subcommands/project/csharp/Lib._cs b/crates/cli/src/subcommands/project/csharp/Lib._cs index 197d2dda0c..c52974c229 100644 --- a/crates/cli/src/subcommands/project/csharp/Lib._cs +++ b/crates/cli/src/subcommands/project/csharp/Lib._cs @@ -1,6 +1,6 @@ using SpacetimeDB; -static partial class Module +public static partial class Module { [SpacetimeDB.Table] public partial struct Person From 509bbeb5cc6c7ced0c8a83bc15d90bc917ee69fc Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 12:35:48 -0400 Subject: [PATCH 23/27] codegen insert return --- crates/bindings-csharp/Codegen/Module.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index dadc5fef33..783bd541ca 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -286,7 +286,7 @@ public IEnumerable GenerateViews() } public IEnumerable<{{globalName}}> Iter() => {{iTable}}.Iter(); public IEnumerable<{{globalName}}> Query(System.Linq.Expressions.Expression> predicate) => {{iTable}}.Query(predicate); - public void Insert({{globalName}} row) => {{iTable}}.Insert(row); + public {{globalName}} Insert({{globalName}} row) => {{iTable}}.Insert(row); {{string.Join("\n", GenerateViewFilters(v.Name, iTable))}} } """, From b2a60696c0f79da02fd9208fecdfdb4e86feb89e Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 12:59:14 -0400 Subject: [PATCH 24/27] verified --- .../fixtures/server/snapshots/Module#FFI.verified.cs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs index cb2fb1d8a9..275b221fc9 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#FFI.verified.cs @@ -52,7 +52,7 @@ public readonly struct PrivateTable predicate ); - public void Insert(global::PrivateTable row) => + public global::PrivateTable Insert(global::PrivateTable row) => SpacetimeDB.Internal.ITableView.Insert(row); } @@ -78,7 +78,7 @@ public readonly struct PublicTable System.Linq.Expressions.Expression> predicate ) => SpacetimeDB.Internal.ITableView.Query(predicate); - public void Insert(global::PublicTable row) => + public global::PublicTable Insert(global::PublicTable row) => SpacetimeDB.Internal.ITableView.Insert(row); public IEnumerable FilterById(int Id) => @@ -315,7 +315,7 @@ public readonly struct SendMessageTimer global::Timers.SendMessageTimer >.Query(predicate); - public void Insert(global::Timers.SendMessageTimer row) => + public global::Timers.SendMessageTimer Insert(global::Timers.SendMessageTimer row) => SpacetimeDB.Internal.ITableView< SendMessageTimer, global::Timers.SendMessageTimer From fcff0decbc9dcc648a8e0ca141d3fba1ba33121d Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 14:14:59 -0400 Subject: [PATCH 25/27] update --- crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs | 2 +- .../fixtures/server/snapshots/Module#PrivateTable.verified.cs | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs index a8a2046765..98f2c3816e 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/Lib.cs @@ -39,7 +39,7 @@ public partial record CustomTaggedEnum : SpacetimeDB.TaggedEnum<(int IntVariant, string StringVariant)>; [SpacetimeDB.Table] -public partial struct PrivateTable { } +public partial class PrivateTable { } [SpacetimeDB.Table] public partial struct PublicTable diff --git a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PrivateTable.verified.cs b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PrivateTable.verified.cs index 5b43bd94b3..915464b0ef 100644 --- a/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PrivateTable.verified.cs +++ b/crates/bindings-csharp/Codegen.Tests/fixtures/server/snapshots/Module#PrivateTable.verified.cs @@ -2,7 +2,7 @@ // #nullable enable -partial struct PrivateTable : SpacetimeDB.Internal.ITable +partial class PrivateTable : SpacetimeDB.Internal.ITable { public void ReadFields(System.IO.BinaryReader reader) { } From b5dfac7b9b4ddc765098ad73699ec067e9ef13ee Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 18:02:20 -0400 Subject: [PATCH 26/27] update --- crates/bindings-csharp/Codegen/Module.cs | 7 +++++-- crates/cli/src/subcommands/project/csharp/Lib._cs | 2 +- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/crates/bindings-csharp/Codegen/Module.cs b/crates/bindings-csharp/Codegen/Module.cs index 783bd541ca..264e0380d9 100644 --- a/crates/bindings-csharp/Codegen/Module.cs +++ b/crates/bindings-csharp/Codegen/Module.cs @@ -417,7 +417,10 @@ public ReducerDeclaration(GeneratorAttributeSyntaxContext context) public KeyValuePair GenerateClass() { - var args = string.Join(", ", Args.Select(a => $"{a.Name}.Read(reader)").Prepend("ctx")); + var args = string.Join( + ", ", + Args.Select(a => $"{a.Name}.Read(reader)").Prepend("(SpacetimeDB.ReducerContext)ctx") + ); var class_ = $$""" class {{Name}}: SpacetimeDB.Internal.IReducer { {{MemberDeclaration.GenerateBsatnFields(Accessibility.Private, Args)}} @@ -428,7 +431,7 @@ class {{Name}}: SpacetimeDB.Internal.IReducer { ); public void Invoke(BinaryReader reader, SpacetimeDB.Internal.IReducerContext ctx) { - {{FullName}}((SpacetimeDB.ReducerContext){{args}}); + {{FullName}}({{args}}); } } """; diff --git a/crates/cli/src/subcommands/project/csharp/Lib._cs b/crates/cli/src/subcommands/project/csharp/Lib._cs index c52974c229..98a85f15a4 100644 --- a/crates/cli/src/subcommands/project/csharp/Lib._cs +++ b/crates/cli/src/subcommands/project/csharp/Lib._cs @@ -5,7 +5,7 @@ public static partial class Module [SpacetimeDB.Table] public partial struct Person { - [SpacetimeDB.AutoInc] + [SpacetimeDB.AutoInc] [SpacetimeDB.PrimaryKey] public int Id; public string Name; From fc5f3b896e6cf3849c2924b45814552b00f4bb81 Mon Sep 17 00:00:00 2001 From: Jeremie Pelletier Date: Thu, 26 Sep 2024 23:14:13 -0400 Subject: [PATCH 27/27] undo --- crates/cli/src/subcommands/generate/csharp.rs | 18 +++++++----------- 1 file changed, 7 insertions(+), 11 deletions(-) diff --git a/crates/cli/src/subcommands/generate/csharp.rs b/crates/cli/src/subcommands/generate/csharp.rs index 58f102a1ef..4244f2a095 100644 --- a/crates/cli/src/subcommands/generate/csharp.rs +++ b/crates/cli/src/subcommands/generate/csharp.rs @@ -6,12 +6,12 @@ use std::ops::Deref; use convert_case::{Case, Casing}; use spacetimedb_lib::sats::{AlgebraicType, AlgebraicTypeRef, ArrayType, ProductType, SumType}; -use spacetimedb_lib::{ReducerDef, TableDesc}; +use spacetimedb_lib::ReducerDef; use spacetimedb_primitives::ColList; use spacetimedb_schema::schema::TableSchema; use super::code_indenter::CodeIndenter; -use super::{GenCtx, GenItem}; +use super::{GenCtx, GenItem, TableDescHack}; fn scalar_or_string_name(b: &AlgebraicType) -> Option<&str> { Some(match b { @@ -279,17 +279,13 @@ pub fn autogen_csharp_tuple(ctx: &GenCtx, name: &str, tuple: &ProductType, names } #[allow(deprecated)] -pub fn autogen_csharp_table(ctx: &GenCtx, table: &TableDesc, namespace: &str) -> String { +pub fn autogen_csharp_table(ctx: &GenCtx, table: &TableDescHack, namespace: &str) -> String { let tuple = ctx.typespace[table.data].as_product().unwrap(); autogen_csharp_product_table_common( ctx, csharp_typename(ctx, table.data), tuple, - Some( - TableSchema::from_def(0.into(), table.schema.clone()) - .validated() - .expect("Failed to generate table due to validation errors"), - ), + Some(table.schema.clone()), namespace, ) } @@ -317,7 +313,7 @@ fn autogen_csharp_product_table_common( write!( output, " : SpacetimeDB.{parent}<{name}, {namespace}.ReducerEvent>", - parent = if schema.pk().is_some() { + parent = if schema.primary_key.is_some() { "DatabaseTableWithPrimaryKey" } else { "DatabaseTable" @@ -383,7 +379,7 @@ fn autogen_csharp_product_table_common( // If this is a table, we want to generate event accessor and indexes if let Some(schema) = &schema { - let constraints = schema.column_constraints(); + let constraints = schema.backcompat_column_constraints(); let mut unique_indexes = Vec::new(); // Declare custom index dictionaries for col in schema.columns() { @@ -450,7 +446,7 @@ fn autogen_csharp_access_funcs_for_struct( _table_name: &str, schema: &TableSchema, ) { - let constraints = schema.column_constraints(); + let constraints = schema.backcompat_column_constraints(); for col in schema.columns() { let is_unique = constraints[&ColList::new(col.col_pos)].has_unique();