From 98dfbcc1e0f079713f294b45b1df8d4f7c771b9f Mon Sep 17 00:00:00 2001 From: Ilan Uzan Date: Fri, 3 Oct 2025 18:40:29 +0200 Subject: [PATCH 1/6] feat: enable override timestamp to NodaTime.Instant --- CodeGenerator/Generators/CsprojGen.cs | 1 + Drivers/ColumnMapping.cs | 4 +- Drivers/DbDriver.cs | 69 +++++-- Drivers/Generators/CommonGen.cs | 21 -- Drivers/Generators/ExecDeclareGen.cs | 4 +- Drivers/Generators/ExecLastIdDeclareGen.cs | 4 +- Drivers/Generators/ExecRowsDeclareGen.cs | 4 +- Drivers/Generators/ManyDeclareGen.cs | 4 +- Drivers/Generators/OneDeclareGen.cs | 4 +- Drivers/MySqlConnectorDriver.cs | 24 +-- Drivers/NpgsqlDriver.cs | 186 +++++++++++------- PluginOptions/Options.cs | 5 +- PluginOptions/RawOptions.cs | 3 + end2end/EndToEndScaffold/Program.cs | 1 + .../Templates/PostgresTests.cs | 39 +++- .../MySqlConnectorDapperTester.generated.cs | 1 + .../MySqlConnectorTester.generated.cs | 1 + .../NpgsqlDapperTester.generated.cs | 21 +- .../EndToEndTests/NpgsqlTester.generated.cs | 21 +- .../SqliteDapperTester.generated.cs | 1 + .../EndToEndTests/SqliteTester.generated.cs | 1 + .../MySqlConnectorDapperTester.generated.cs | 1 + .../MySqlConnectorTester.generated.cs | 1 + .../NpgsqlDapperTester.generated.cs | 21 +- .../NpgsqlTester.generated.cs | 21 +- .../SqliteDapperTester.generated.cs | 1 + .../SqliteTester.generated.cs | 1 + .../MySqlConnectorDapperExample.csproj | 1 + .../MySqlConnectorDapperExample/request.json | 2 +- .../request.message | Bin 25750 -> 25770 bytes .../MySqlConnectorDapperLegacyExample.csproj | 1 + .../request.json | 2 +- .../request.message | Bin 25784 -> 25804 bytes .../MySqlConnectorExample.csproj | 1 + examples/MySqlConnectorExample/request.json | 2 +- .../MySqlConnectorExample/request.message | Bin 25734 -> 25754 bytes .../MySqlConnectorLegacyExample.csproj | 1 + .../MySqlConnectorLegacyExample/request.json | 2 +- .../request.message | Bin 25768 -> 25788 bytes examples/NpgsqlDapperExample/Models.cs | 3 + .../NpgsqlDapperExample.csproj | 1 + examples/NpgsqlDapperExample/QuerySql.cs | 13 +- examples/NpgsqlDapperExample/Utils.cs | 19 ++ examples/NpgsqlDapperExample/request.json | 46 ++++- examples/NpgsqlDapperExample/request.message | 34 ++-- examples/NpgsqlDapperLegacyExample/Models.cs | 3 + .../NpgsqlDapperLegacyExample.csproj | 1 + .../NpgsqlDapperLegacyExample/QuerySql.cs | 13 +- examples/NpgsqlDapperLegacyExample/Utils.cs | 19 ++ .../NpgsqlDapperLegacyExample/request.json | 46 ++++- .../NpgsqlDapperLegacyExample/request.message | 34 ++-- examples/NpgsqlExample/Models.cs | 4 +- examples/NpgsqlExample/NpgsqlExample.csproj | 1 + examples/NpgsqlExample/QuerySql.cs | 66 ++++--- examples/NpgsqlExample/request.json | 46 ++++- examples/NpgsqlExample/request.message | 34 ++-- examples/NpgsqlLegacyExample/Models.cs | 3 + .../NpgsqlLegacyExample.csproj | 1 + examples/NpgsqlLegacyExample/QuerySql.cs | 64 +++--- examples/NpgsqlLegacyExample/request.json | 46 ++++- examples/NpgsqlLegacyExample/request.message | 34 ++-- .../SqliteDapperExample.csproj | 1 + examples/SqliteDapperExample/request.json | 2 +- examples/SqliteDapperExample/request.message | Bin 9792 -> 9812 bytes .../SqliteDapperLegacyExample.csproj | 1 + .../SqliteDapperLegacyExample/request.json | 2 +- .../SqliteDapperLegacyExample/request.message | Bin 9826 -> 9846 bytes examples/SqliteExample/SqliteExample.csproj | 1 + examples/SqliteExample/request.json | 2 +- examples/SqliteExample/request.message | Bin 9776 -> 9796 bytes .../SqliteLegacyExample.csproj | 1 + examples/SqliteLegacyExample/request.json | 2 +- examples/SqliteLegacyExample/request.message | Bin 9810 -> 9830 bytes examples/config/postgresql/types/query.sql | 5 +- examples/config/postgresql/types/schema.sql | 3 +- sqlc.ci.yaml | 16 ++ sqlc.local.generated.yaml | 16 ++ sqlc.request.generated.yaml | 16 ++ .../DefaultSchemaEnum/request.json | 2 +- .../DefaultSchemaEnum/request.message | 2 +- .../SchemaScopedEnum/request.json | 2 +- .../SchemaScopedEnum/request.message | 2 +- 82 files changed, 778 insertions(+), 306 deletions(-) diff --git a/CodeGenerator/Generators/CsprojGen.cs b/CodeGenerator/Generators/CsprojGen.cs index f41319e9..99a1c9a4 100644 --- a/CodeGenerator/Generators/CsprojGen.cs +++ b/CodeGenerator/Generators/CsprojGen.cs @@ -60,6 +60,7 @@ string GetPackageReferences() return $""" {optionalDapperPackageReference}{optionalCsvHelper}{optionalSystemTextJson} + """; } diff --git a/Drivers/ColumnMapping.cs b/Drivers/ColumnMapping.cs index 8878043c..df38edda 100644 --- a/Drivers/ColumnMapping.cs +++ b/Drivers/ColumnMapping.cs @@ -16,7 +16,7 @@ public class ColumnMapping( Dictionary dbTypes, ReaderFn readerFn, ReaderFn? readerArrayFn = null, - string? usingDirective = null, + string[]? usingDirectives = null, WriterFn? writerFn = null, ConvertFunc? convertFunc = null, string? sqlMapper = null, @@ -25,7 +25,7 @@ public class ColumnMapping( public Dictionary DbTypes { get; } = dbTypes; public ReaderFn ReaderFn { get; } = readerFn; public ReaderFn? ReaderArrayFn { get; } = readerArrayFn; - public string? UsingDirective { get; } = usingDirective; + public string[]? UsingDirectives { get; } = usingDirectives; public WriterFn? WriterFn { get; } = writerFn; public ConvertFunc? ConvertFunc { get; } = convertFunc; public string? SqlMapper { get; } = sqlMapper; diff --git a/Drivers/DbDriver.cs b/Drivers/DbDriver.cs index 6a359104..91e23b56 100644 --- a/Drivers/DbDriver.cs +++ b/Drivers/DbDriver.cs @@ -51,6 +51,7 @@ public abstract class DbDriver "NpgsqlCircle", "JsonElement", "NpgsqlCidr", + "Instant" ]; protected abstract Dictionary ColumnMappings { get; } @@ -68,6 +69,23 @@ public static string TransformQueryForSliceArgs(string originalSql, int sliceSiz throw new InvalidOperationException("Transaction is provided, but its connection is null."); """; + protected static readonly SqlMapperImplFunc NodaInstantTypeHandler = _ => $$""" + private class NodaInstantTypeHandler : SqlMapper.TypeHandler + { + public override Instant Parse(object value) + { + if (value is DateTime dt) + return dt.ToInstant(); + throw new DataException($"Cannot convert {value?.GetType()} to Instant"); + } + + public override void SetValue(IDbDataParameter parameter, Instant value) + { + parameter.Value = value; + } + } + """; + protected DbDriver( Options options, Catalog catalog, @@ -118,17 +136,16 @@ public virtual ISet GetUsingDirectivesForQueries() private ISet GetUsingDirectivesForColumnMappings() { var usingDirectives = new HashSet(); - foreach (var schemaTables in Tables.Values) - foreach (var table in schemaTables.Values) - foreach (var column in table.Columns) - { - var csharpType = GetCsharpTypeWithoutNullableSuffix(column, null); - if (!ColumnMappings.ContainsKey(csharpType)) - continue; - - var columnMapping = ColumnMappings[csharpType]; - usingDirectives.AddRangeExcludeNulls([columnMapping.UsingDirective]); - } + foreach (var query in Queries) + foreach (var column in query.Columns) + { + var csharpType = GetCsharpTypeWithoutNullableSuffix(column, query); + if (!ColumnMappings.ContainsKey(csharpType)) + continue; + + var columnMapping = ColumnMappings[csharpType]; + usingDirectives.AddRangeIf(columnMapping.UsingDirectives!, columnMapping.UsingDirectives is not null); + } return usingDirectives; } @@ -223,6 +240,32 @@ public virtual string[] GetLastIdStatement(Query query) ]; } + public virtual string AddParametersToCommand(Query query) + { + return query.Params.Select(p => + { + var commandVar = Variable.Command.AsVarName(); + var param = $"{Variable.Args.AsVarName()}.{p.Column.Name.ToPascalCase()}"; + var columnMapping = GetCsharpTypeWithoutNullableSuffix(p.Column, query); + + if (p.Column.IsSqlcSlice) + return $$""" + for (int i = 0; i < {{param}}.Length; i++) + {{commandVar}}.Parameters.AddWithValue($"@{{p.Column.Name}}Arg{i}", {{param}}[i]); + """; + + var writerFn = GetWriterFn(p.Column, query); + var paramToWrite = writerFn is null ? param : writerFn( + param, + p.Column.Type.Name, + IsColumnNotNull(p.Column, query), + Options.UseDapper, + Options.DotnetFramework.IsDotnetLegacy()); + var addParamToCommand = $"""{commandVar}.Parameters.AddWithValue("@{p.Column.Name}", {paramToWrite});"""; + return addParamToCommand; + }).JoinByNewLine(); + } + public Column GetColumnFromParam(Parameter queryParam, Query query) { if (string.IsNullOrEmpty(queryParam.Column.Name)) @@ -287,13 +330,15 @@ public string AddNullableSuffixIfNeeded(string csharpType, bool notNull) protected string? GetColumnDbTypeOverride(Column column) { + if (column.IsArray) + return null; var columnType = column.Type.Name.ToLower(); foreach (var columnMapping in ColumnMappings.Values) { if (columnMapping.DbTypes.TryGetValue(columnType, out var dbTypeOverride)) return dbTypeOverride.NpgsqlTypeOverride; } - throw new NotSupportedException($"Column {column.Name} has unsupported column type: {column.Type.Name}"); + return null; } public bool IsTypeNullable(string csharpType) diff --git a/Drivers/Generators/CommonGen.cs b/Drivers/Generators/CommonGen.cs index 71c22265..f330b24e 100644 --- a/Drivers/Generators/CommonGen.cs +++ b/Drivers/Generators/CommonGen.cs @@ -13,27 +13,6 @@ public static string GetMethodParameterList(string argInterface, IEnumerable - { - var commandVar = Variable.Command.AsVarName(); - var param = $"{Variable.Args.AsVarName()}.{p.Column.Name.ToPascalCase()}"; - if (p.Column.IsSqlcSlice) - return $$""" - for (int i = 0; i < {{param}}.Length; i++) - {{commandVar}}.Parameters.AddWithValue($"@{{p.Column.Name}}Arg{i}", {{param}}[i]); - """; - - var notNull = dbDriver.IsColumnNotNull(p.Column, query); - var writerFn = dbDriver.GetWriterFn(p.Column, query); - var paramToWrite = writerFn is null ? param : writerFn(param, p.Column.Type.Name, notNull, dbDriver.Options.UseDapper, dbDriver.Options.DotnetFramework.IsDotnetLegacy()); - var addParamToCommand = $"""{commandVar}.Parameters.AddWithValue("@{p.Column.Name}", {paramToWrite});"""; - return addParamToCommand; - }).JoinByNewLine(); - } - public string ConstructDapperParamsDict(Query query) { if (!query.Params.Any()) return string.Empty; diff --git a/Drivers/Generators/ExecDeclareGen.cs b/Drivers/Generators/ExecDeclareGen.cs index 2470457d..e2b6bb38 100644 --- a/Drivers/Generators/ExecDeclareGen.cs +++ b/Drivers/Generators/ExecDeclareGen.cs @@ -70,7 +70,7 @@ private string GetDriverNoTxBody(string sqlVar, Query query) { var (establishConnection, connectionOpen) = dbDriver.EstablishConnection(query); var createSqlCommand = dbDriver.CreateSqlCommand(sqlVar); - var commandParameters = CommonGen.AddParametersToCommand(query); + var commandParameters = dbDriver.AddParametersToCommand(query); return $$""" using ({{establishConnection}}) { @@ -89,7 +89,7 @@ private string GetDriverWithTxBody(string sqlVar, Query query) { var transactionProperty = Variable.Transaction.AsPropertyName(); var commandVar = Variable.Command.AsVarName(); - var commandParameters = CommonGen.AddParametersToCommand(query); + var commandParameters = dbDriver.AddParametersToCommand(query); return $$""" {{dbDriver.TransactionConnectionNullExcetionThrow}} diff --git a/Drivers/Generators/ExecLastIdDeclareGen.cs b/Drivers/Generators/ExecLastIdDeclareGen.cs index 48c9a231..7493bda8 100644 --- a/Drivers/Generators/ExecLastIdDeclareGen.cs +++ b/Drivers/Generators/ExecLastIdDeclareGen.cs @@ -67,7 +67,7 @@ private string GetDriverNoTxBody(string sqlVar, Query query) { var (establishConnection, connectionOpen) = dbDriver.EstablishConnection(query); var createSqlCommand = dbDriver.CreateSqlCommand(sqlVar); - var commandParameters = CommonGen.AddParametersToCommand(query); + var commandParameters = dbDriver.AddParametersToCommand(query); var returnLastId = ((IExecLastId)dbDriver).GetLastIdStatement(query).JoinByNewLine(); return $$""" using ({{establishConnection}}) @@ -86,7 +86,7 @@ private string GetDriverWithTxBody(string sqlVar, Query query) { var transactionProperty = Variable.Transaction.AsPropertyName(); var commandVar = Variable.Command.AsVarName(); - var commandParameters = CommonGen.AddParametersToCommand(query); + var commandParameters = dbDriver.AddParametersToCommand(query); var returnLastId = ((IExecLastId)dbDriver).GetLastIdStatement(query).JoinByNewLine(); return $$""" diff --git a/Drivers/Generators/ExecRowsDeclareGen.cs b/Drivers/Generators/ExecRowsDeclareGen.cs index 7acdc8c4..c5711e8b 100644 --- a/Drivers/Generators/ExecRowsDeclareGen.cs +++ b/Drivers/Generators/ExecRowsDeclareGen.cs @@ -69,7 +69,7 @@ private string GetDriverNoTxBody(string sqlVar, Query query) { var (establishConnection, connectionOpen) = dbDriver.EstablishConnection(query); var createSqlCommand = dbDriver.CreateSqlCommand(sqlVar); - var commandParameters = CommonGen.AddParametersToCommand(query); + var commandParameters = dbDriver.AddParametersToCommand(query); return $$""" using ({{establishConnection}}) { @@ -87,7 +87,7 @@ private string GetDriverWithTxBody(string sqlVar, Query query) { var transactionProperty = Variable.Transaction.AsPropertyName(); var commandVar = Variable.Command.AsVarName(); - var commandParameters = CommonGen.AddParametersToCommand(query); + var commandParameters = dbDriver.AddParametersToCommand(query); return $$""" {{dbDriver.TransactionConnectionNullExcetionThrow}} diff --git a/Drivers/Generators/ManyDeclareGen.cs b/Drivers/Generators/ManyDeclareGen.cs index 73a13547..a9096d32 100644 --- a/Drivers/Generators/ManyDeclareGen.cs +++ b/Drivers/Generators/ManyDeclareGen.cs @@ -79,7 +79,7 @@ private string GetDriverNoTxBody(string sqlVar, string returnInterface, Query qu { var (establishConnection, connectionOpen) = dbDriver.EstablishConnection(query); var createSqlCommand = dbDriver.CreateSqlCommand(sqlVar); - var commandParameters = CommonGen.AddParametersToCommand(query); + var commandParameters = dbDriver.AddParametersToCommand(query); var initDataReader = CommonGen.InitDataReader(); var awaitReaderRow = CommonGen.AwaitReaderRow(); var dataclassInit = CommonGen.InstantiateDataclass(query.Columns.ToArray(), returnInterface, query); @@ -111,7 +111,7 @@ private string GetDriverWithTxBody(string sqlVar, string returnInterface, Query { var transactionProperty = Variable.Transaction.AsPropertyName(); var commandVar = Variable.Command.AsVarName(); - var commandParameters = CommonGen.AddParametersToCommand(query); + var commandParameters = dbDriver.AddParametersToCommand(query); var initDataReader = CommonGen.InitDataReader(); var awaitReaderRow = CommonGen.AwaitReaderRow(); var dataclassInit = CommonGen.InstantiateDataclass(query.Columns.ToArray(), returnInterface, query); diff --git a/Drivers/Generators/OneDeclareGen.cs b/Drivers/Generators/OneDeclareGen.cs index c35d4d52..c0715ba8 100644 --- a/Drivers/Generators/OneDeclareGen.cs +++ b/Drivers/Generators/OneDeclareGen.cs @@ -79,7 +79,7 @@ private string GetDriverNoTxBody(string sqlVar, string returnInterface, Query qu { var (establishConnection, connectionOpen) = dbDriver.EstablishConnection(query); var createSqlCommand = dbDriver.CreateSqlCommand(sqlVar); - var commandParameters = CommonGen.AddParametersToCommand(query); + var commandParameters = dbDriver.AddParametersToCommand(query); var initDataReader = CommonGen.InitDataReader(); var awaitReaderRow = CommonGen.AwaitReaderRow(); var returnDataclass = CommonGen.InstantiateDataclass(query.Columns.ToArray(), returnInterface, query); @@ -108,7 +108,7 @@ private string GetDriverWithTxBody(string sqlVar, string returnInterface, Query { var transactionProperty = Variable.Transaction.AsPropertyName(); var commandVar = Variable.Command.AsVarName(); - var commandParameters = CommonGen.AddParametersToCommand(query); + var commandParameters = dbDriver.AddParametersToCommand(query); var initDataReader = CommonGen.InitDataReader(); var awaitReaderRow = CommonGen.AwaitReaderRow(); var returnDataclass = CommonGen.InstantiateDataclass(query.Columns.ToArray(), returnInterface, query); diff --git a/Drivers/MySqlConnectorDriver.cs b/Drivers/MySqlConnectorDriver.cs index 2c05cb63..9dd89272 100644 --- a/Drivers/MySqlConnectorDriver.cs +++ b/Drivers/MySqlConnectorDriver.cs @@ -26,7 +26,7 @@ public sealed partial class MySqlConnectorDriver( { { "tinyint", new(Length: 1) } }, - readerFn: (ordinal, _) => $"reader.GetBoolean({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetBoolean({ordinal})" ), ["short"] = new( new() @@ -35,7 +35,7 @@ public sealed partial class MySqlConnectorDriver( { "smallint", new() }, { "year", new() } }, - readerFn: (ordinal, _) => $"reader.GetInt16({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetInt16({ordinal})" ), ["int"] = new( new() @@ -44,7 +44,7 @@ public sealed partial class MySqlConnectorDriver( { "integer", new() }, { "mediumint", new() } }, - readerFn: (ordinal, _) => $"reader.GetInt32({ordinal})", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetInt32({ordinal})", convertFunc: x => $"Convert.ToInt32{x}" ), ["long"] = new( @@ -52,7 +52,7 @@ public sealed partial class MySqlConnectorDriver( { { "bigint", new() } }, - readerFn: (ordinal, _) => $"reader.GetInt64({ordinal})", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetInt64({ordinal})", convertFunc: x => $"Convert.ToInt64{x}" ), ["double"] = new( @@ -61,14 +61,14 @@ public sealed partial class MySqlConnectorDriver( { "double", new() }, { "float", new() } }, - readerFn: (ordinal, _) => $"reader.GetDouble({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetDouble({ordinal})" ), ["decimal"] = new( new() { { "decimal", new() } }, - readerFn: (ordinal, _) => $"reader.GetDecimal({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetDecimal({ordinal})" ), /* Binary data types */ @@ -77,7 +77,7 @@ public sealed partial class MySqlConnectorDriver( { { "bit", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})" ), ["byte[]"] = new( new() @@ -89,7 +89,7 @@ public sealed partial class MySqlConnectorDriver( { "tinyblob", new() }, { "varbinary", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})" ), /* String data types */ @@ -104,7 +104,7 @@ public sealed partial class MySqlConnectorDriver( { "varchar", new() }, { "var_string", new() }, }, - readerFn: (ordinal, _) => $"reader.GetString({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetString({ordinal})" ), /* Date and time data types */ @@ -115,14 +115,14 @@ public sealed partial class MySqlConnectorDriver( { "datetime", new() }, { "timestamp", new() } }, - readerFn: (ordinal, _) => $"reader.GetDateTime({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetDateTime({ordinal})" ), ["TimeSpan"] = new( new() { { "time", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})" ), /* Unstructured data types */ @@ -139,7 +139,7 @@ public sealed partial class MySqlConnectorDriver( var nullValue = isDapper ? "null" : "(object)DBNull.Value"; return $"{el}?.GetRawText() ?? {nullValue}"; }, - usingDirective: "System.Text.Json", + usingDirectives: ["System.Text.Json"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(JsonElement), new JsonElementTypeHandler());", sqlMapperImpl: JsonElementTypeHandler ), diff --git a/Drivers/NpgsqlDriver.cs b/Drivers/NpgsqlDriver.cs index ba01c162..3403e858 100644 --- a/Drivers/NpgsqlDriver.cs +++ b/Drivers/NpgsqlDriver.cs @@ -37,16 +37,16 @@ public NpgsqlDriver( { "bool", new() }, { "boolean", new() } }, - readerFn: (ordinal, _) => $"reader.GetBoolean({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetBoolean({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})" ), ["short"] = new( new() { { "int2", new() } }, - readerFn: (ordinal, _) => $"reader.GetInt16({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetInt16({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", convertFunc: x => $"Convert.ToInt16({x})" ), ["int"] = new( @@ -57,8 +57,8 @@ public NpgsqlDriver( { "int4", new() }, { "serial", new() } }, - readerFn: (ordinal, _) => $"reader.GetInt32({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetInt32({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", convertFunc: x => $"Convert.ToInt32({x})" ), ["long"] = new( @@ -68,8 +68,8 @@ public NpgsqlDriver( { "bigint", new() }, { "bigserial", new() } }, - readerFn: (ordinal, _) => $"reader.GetInt64({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetInt64({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", convertFunc: x => $"Convert.ToInt64({x})" ), ["float"] = new( @@ -78,8 +78,8 @@ public NpgsqlDriver( { "float4", new() }, { "real", new() } }, - readerFn: (ordinal, _) => $"reader.GetFloat({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFloat({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})" ), ["decimal"] = new( new() @@ -88,16 +88,16 @@ public NpgsqlDriver( { "decimal", new() }, { "money", new(NpgsqlTypeOverride: "NpgsqlDbType.Money") } }, - readerFn: (ordinal, _) => $"reader.GetDecimal({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetDecimal({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})" ), ["double"] = new( new() { { "float8", new() } }, - readerFn: (ordinal, _) => $"reader.GetDouble({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetDouble({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})" ), /* String data types */ @@ -113,8 +113,8 @@ public NpgsqlDriver( { "jsonpath", new() }, { "macaddr8", new() } }, - readerFn: (ordinal, _) => $"reader.GetString({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetString({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})" ), /* Date and time data types */ @@ -124,18 +124,32 @@ public NpgsqlDriver( { "time", new(NpgsqlTypeOverride: "NpgsqlDbType.Time") }, { "interval", new(NpgsqlTypeOverride: "NpgsqlDbType.Interval") } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})" ), ["DateTime"] = new( new() { { "date", new(NpgsqlTypeOverride: "NpgsqlDbType.Date") }, - { "timestamp", new() }, - { "timestamptz", new() } + { "timestamp", new(NpgsqlTypeOverride: "NpgsqlDbType.Timestamp") }, + { "timestamptz", new(NpgsqlTypeOverride: "NpgsqlDbType.TimestampTz") } }, - readerFn: (ordinal, _) => $"reader.GetDateTime({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetDateTime({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})" + ), + ["Instant"] = new( + [], + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetDateTime({ordinal}).ToInstant()", + writerFn: (el, _, notNull, isDapper, isLegacy) => + { + if (notNull) + return $"{el}.ToDateTimeUtc().ToLocalTime()"; + var nullValue = isDapper ? "null" : "(object)DBNull.Value"; + return $"{el}?.ToDateTimeUtc().ToLocalTime() ?? {nullValue}"; + }, + usingDirectives: ["System", "NodaTime", "NodaTime.Extensions"], + sqlMapper: "SqlMapper.AddTypeHandler(typeof(Instant), new NodaInstantTypeHandler());", + sqlMapperImpl: NodaInstantTypeHandler ), /* Unstructured data types */ @@ -153,7 +167,7 @@ public NpgsqlDriver( var nullValue = isDapper ? "null" : "(object)DBNull.Value"; return $"{el}.HasValue ? (object) {el}.Value : {nullValue}"; }, - usingDirective: "System.Text.Json", + usingDirectives: ["System.Text.Json"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(JsonElement), new JsonElementTypeHandler());", sqlMapperImpl: JsonElementTypeHandler ), @@ -177,7 +191,7 @@ public NpgsqlDriver( var nullValue = isDapper ? "null" : "(object)DBNull.Value"; return $"{el} != null ? {el}.OuterXml : {nullValue}"; }, - usingDirective: "System.Xml", + usingDirectives: ["System.Xml"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(XmlDocument), new XmlDocumentTypeHandler());", sqlMapperImpl: XmlDocumentTypeHandler ), @@ -188,9 +202,9 @@ public NpgsqlDriver( { { "point", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - usingDirective: "NpgsqlTypes", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + usingDirectives: ["NpgsqlTypes"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(NpgsqlPoint), new NpgsqlTypeHandler());" ), ["NpgsqlLine"] = new( @@ -198,9 +212,9 @@ public NpgsqlDriver( { { "line", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - usingDirective: "NpgsqlTypes", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + usingDirectives: ["NpgsqlTypes"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(NpgsqlLine), new NpgsqlTypeHandler());" ), ["NpgsqlLSeg"] = new( @@ -208,9 +222,9 @@ public NpgsqlDriver( { { "lseg", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - usingDirective: "NpgsqlTypes", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + usingDirectives: ["NpgsqlTypes"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(NpgsqlLSeg), new NpgsqlTypeHandler());" ), ["NpgsqlBox"] = new( @@ -218,9 +232,9 @@ public NpgsqlDriver( { { "box", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - usingDirective: "NpgsqlTypes", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + usingDirectives: ["NpgsqlTypes"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(NpgsqlBox), new NpgsqlTypeHandler());" ), ["NpgsqlPath"] = new( @@ -228,9 +242,9 @@ public NpgsqlDriver( { { "path", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - usingDirective: "NpgsqlTypes", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + usingDirectives: ["NpgsqlTypes"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(NpgsqlPath), new NpgsqlTypeHandler());" ), ["NpgsqlPolygon"] = new( @@ -238,9 +252,9 @@ public NpgsqlDriver( { { "polygon", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - usingDirective: "NpgsqlTypes", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + usingDirectives: ["NpgsqlTypes"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(NpgsqlPolygon), new NpgsqlTypeHandler());" ), ["NpgsqlCircle"] = new( @@ -248,9 +262,9 @@ public NpgsqlDriver( { { "circle", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - usingDirective: "NpgsqlTypes", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + usingDirectives: ["NpgsqlTypes"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(NpgsqlCircle), new NpgsqlTypeHandler());" ), @@ -260,9 +274,9 @@ public NpgsqlDriver( { { "cidr", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - usingDirective: "NpgsqlTypes", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + usingDirectives: ["NpgsqlTypes"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(NpgsqlCidr), new NpgsqlTypeHandler());" ), ["IPAddress"] = new( @@ -270,9 +284,9 @@ public NpgsqlDriver( { { "inet", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - usingDirective: "System.Net", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + usingDirectives: ["System.Net"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(IPAddress), new NpgsqlTypeHandler());" ), ["PhysicalAddress"] = new( @@ -280,9 +294,9 @@ public NpgsqlDriver( { { "macaddr", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - usingDirective: "System.Net.NetworkInformation", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + usingDirectives: ["System.Net.NetworkInformation"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(PhysicalAddress), new NpgsqlTypeHandler());" ), @@ -292,9 +306,9 @@ public NpgsqlDriver( { { "tsquery", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - usingDirective: "NpgsqlTypes", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + usingDirectives: ["NpgsqlTypes"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(NpgsqlTsQuery), new NpgsqlTypeHandler());" ), ["NpgsqlTsVector"] = new( @@ -302,9 +316,9 @@ public NpgsqlDriver( { { "tsvector", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - usingDirective: "NpgsqlTypes", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + usingDirectives: ["NpgsqlTypes"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(NpgsqlTsVector), new NpgsqlTypeHandler());" ), @@ -314,8 +328,8 @@ public NpgsqlDriver( { { "uuid", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", convertFunc: x => $"Guid.Parse({x}?.ToString())" ), ["byte[]"] = new( @@ -330,15 +344,15 @@ public NpgsqlDriver( { "tinyblob", new() }, { "varbinary", new() } }, - readerFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})", - readerArrayFn: (ordinal, _) => $"reader.GetFieldValue({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})", + readerArrayFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})" ), ["object"] = new( new() { { "anyarray", new() } }, - readerFn: (ordinal, _) => $"reader.GetValue({ordinal})" + readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetValue({ordinal})" ) }; @@ -576,11 +590,17 @@ string AddRowsToCopyCommand() var constructRowFields = query.Params .Select(p => { - var typeOverride = GetColumnDbTypeOverride(p.Column); var param = $"{rowVar}.{p.Column.Name.ToPascalCase()}"; var writerFn = GetWriterFn(p.Column, query); - var paramToWrite = writerFn is null ? param : writerFn(param, p.Column.Type.Name, p.Column.NotNull, false, !Options.DotnetFramework.IsDotnetLegacy()); + var paramToWrite = writerFn is null ? param : writerFn( + param, + p.Column.Type.Name, + IsColumnNotNull(p.Column, query), + false, + Options.DotnetFramework.IsDotnetLegacy()); + var partialStmt = $"await {writerVar}.WriteAsync({paramToWrite}"; + var typeOverride = GetColumnDbTypeOverride(p.Column); return typeOverride is null ? $"{partialStmt});" : $"{partialStmt}, {typeOverride});"; @@ -618,6 +638,38 @@ string AddRowsToCopyCommand() return Options.UseDapper ? null : DefaultWriterFn; } + public override string AddParametersToCommand(Query query) + { + return query.Params.Select(p => + { + var commandVar = Variable.Command.AsVarName(); + var param = $"{Variable.Args.AsVarName()}.{p.Column.Name.ToPascalCase()}"; + + if (p.Column.IsSqlcSlice) + return $$""" + for (int i = 0; i < {{param}}.Length; i++) + {{commandVar}}.Parameters.AddWithValue($"@{{p.Column.Name}}Arg{i}", {{param}}[i]); + """; + + var writerFn = GetWriterFn(p.Column, query); + var paramToWrite = writerFn is null + ? param + : writerFn( + param, + p.Column.Type.Name, + IsColumnNotNull(p.Column, query), + Options.UseDapper, + Options.DotnetFramework.IsDotnetLegacy()); + + var typeOverride = GetColumnDbTypeOverride(p.Column); + var optionalNpgsqlTypeOverride = typeOverride is null + ? string.Empty + : $"{typeOverride}, "; + var addParamToCommand = $"""{commandVar}.Parameters.AddWithValue("@{p.Column.Name}", {optionalNpgsqlTypeOverride}{paramToWrite});"""; + return addParamToCommand; + }).JoinByNewLine(); + } + private static (string, string) GetEnumSchemaAndName(Column column) { var schemaName = column.Type.Schema; diff --git a/PluginOptions/Options.cs b/PluginOptions/Options.cs index 77da0dce..1336065b 100644 --- a/PluginOptions/Options.cs +++ b/PluginOptions/Options.cs @@ -19,6 +19,7 @@ public Options(GenerateRequest generateRequest) UseDapper = rawOptions.UseDapper; OverrideDapperVersion = rawOptions.OverrideDapperVersion; NamespaceName = rawOptions.NamespaceName; + UseNodaTime = rawOptions.UseNodaTime; DotnetFramework = DotnetFrameworkExtensions.ParseName(rawOptions.TargetFramework); Overrides = rawOptions.Overrides ?? []; @@ -39,9 +40,9 @@ public Options(GenerateRequest generateRequest) public string OverrideDapperVersion { get; } - public string NamespaceName { get; } + public bool UseNodaTime { get; } - public bool NotNull { get; } + public string NamespaceName { get; } public List Overrides { get; } diff --git a/PluginOptions/RawOptions.cs b/PluginOptions/RawOptions.cs index 52ebb113..b9b2d2f4 100644 --- a/PluginOptions/RawOptions.cs +++ b/PluginOptions/RawOptions.cs @@ -23,6 +23,9 @@ public record RawOptions [JsonPropertyName("overrideDapperVersion")] public string OverrideDapperVersion { get; init; } = string.Empty; + [JsonPropertyName("useNodaTime")] + public bool UseNodaTime { get; init; } + [JsonPropertyName("overrides")] public List? Overrides { get; init; } diff --git a/end2end/EndToEndScaffold/Program.cs b/end2end/EndToEndScaffold/Program.cs index 1e3c3d1a..68e857fd 100644 --- a/end2end/EndToEndScaffold/Program.cs +++ b/end2end/EndToEndScaffold/Program.cs @@ -54,6 +54,7 @@ private static string GetFileContents(string testClassName, bool isLegacyDotnet) {{optionalUsingSystemNetNetworkInformation}} {{optionalUsingSystemTextJson}} {{optionalUsingSystemXml}} + using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; diff --git a/end2end/EndToEndScaffold/Templates/PostgresTests.cs b/end2end/EndToEndScaffold/Templates/PostgresTests.cs index 01f8f2a6..8c25925e 100644 --- a/end2end/EndToEndScaffold/Templates/PostgresTests.cs +++ b/end2end/EndToEndScaffold/Templates/PostgresTests.cs @@ -138,15 +138,39 @@ void AssertSingularEquals(QuerySql.GetPostgresNumericTypesRow x, QuerySql.GetPos [KnownTestType.PostgresDateTimeDataTypes] = new TestImpl { Impl = $$""" + + private static IEnumerable PostgresDateTimeTypesTestCases + { + get + { + yield return new TestCaseData( + DateTime.Parse("2000-1-30"), + TimeSpan.Parse("12:13:14"), + DateTime.Parse("1983-11-3 02:01:22"), + DateTime.Parse("2022-10-2 15:44:01+09:00").ToUniversalTime(), + TimeSpan.Parse("02:03:04"), + Instant.FromUtc(2022, 10, 2, 15, 44, 1) + ).SetName("DateTimeTypes with values"); + yield return new TestCaseData( + null, + null, + null, + null, + null, + null + ).SetName("DateTimeTypes with null values"); + } + } + [Test] - [TestCase("2000-1-30", "12:13:14", "1983-11-3 02:01:22", "2022-10-2 15:44:01+09:00", "02:03:04")] - [TestCase(null, null, null, null, null)] + [TestCaseSource(nameof(PostgresDateTimeTypesTestCases))] public async Task TestPostgresDateTimeTypes( DateTime? cDate, TimeSpan? cTime, DateTime? cTimestamp, DateTime? cTimestampWithTz, - TimeSpan? cInterval) + TimeSpan? cInterval, + Instant? cTimestampNodaInstantOverride) { await QuerySql.InsertPostgresDateTimeTypes(new QuerySql.InsertPostgresDateTimeTypesArgs { @@ -154,7 +178,8 @@ await QuerySql.InsertPostgresDateTimeTypes(new QuerySql.InsertPostgresDateTimeTy CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, - CInterval = cInterval + CInterval = cInterval, + CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }); var expected = new QuerySql.GetPostgresDateTimeTypesRow @@ -163,7 +188,8 @@ await QuerySql.InsertPostgresDateTimeTypes(new QuerySql.InsertPostgresDateTimeTy CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, - CInterval = cInterval + CInterval = cInterval, + CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }; var actual = await QuerySql.GetPostgresDateTimeTypes(); AssertSingularEquals(expected, actual{{Consts.UnknownRecordValuePlaceholder}}); @@ -175,7 +201,8 @@ void AssertSingularEquals(QuerySql.GetPostgresDateTimeTypesRow x, QuerySql.GetPo Assert.That(x.CTimestamp, Is.EqualTo(y.CTimestamp)); Assert.That(x.CTimestampWithTz, Is.EqualTo(y.CTimestampWithTz)); Assert.That(x.CInterval, Is.EqualTo(y.CInterval)); - } + Assert.That(x.CTimestampNodaInstantOverride, Is.EqualTo(y.CTimestampNodaInstantOverride)); + } } """ }, diff --git a/end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs b/end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs index 50f7a0c3..21d365d1 100644 --- a/end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs +++ b/end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs @@ -1,5 +1,6 @@ using MySqlConnectorDapperExampleGen; using System.Text.Json; +using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; diff --git a/end2end/EndToEndTests/MySqlConnectorTester.generated.cs b/end2end/EndToEndTests/MySqlConnectorTester.generated.cs index d51787d7..bc1cddfc 100644 --- a/end2end/EndToEndTests/MySqlConnectorTester.generated.cs +++ b/end2end/EndToEndTests/MySqlConnectorTester.generated.cs @@ -1,5 +1,6 @@ using MySqlConnectorExampleGen; using System.Text.Json; +using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; diff --git a/end2end/EndToEndTests/NpgsqlDapperTester.generated.cs b/end2end/EndToEndTests/NpgsqlDapperTester.generated.cs index 4d667348..09e84696 100644 --- a/end2end/EndToEndTests/NpgsqlDapperTester.generated.cs +++ b/end2end/EndToEndTests/NpgsqlDapperTester.generated.cs @@ -4,6 +4,7 @@ using System.Net.NetworkInformation; using System.Text.Json; using System.Xml; +using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; @@ -486,19 +487,28 @@ void AssertSingularEquals(QuerySql.GetPostgresNumericTypesRow x, QuerySql.GetPos } } + private static IEnumerable PostgresDateTimeTypesTestCases + { + get + { + yield return new TestCaseData(DateTime.Parse("2000-1-30"), TimeSpan.Parse("12:13:14"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2022-10-2 15:44:01+09:00").ToUniversalTime(), TimeSpan.Parse("02:03:04"), Instant.FromUtc(2022, 10, 2, 15, 44, 1)).SetName("DateTimeTypes with values"); + yield return new TestCaseData(null, null, null, null, null, null).SetName("DateTimeTypes with null values"); + } + } + [Test] - [TestCase("2000-1-30", "12:13:14", "1983-11-3 02:01:22", "2022-10-2 15:44:01+09:00", "02:03:04")] - [TestCase(null, null, null, null, null)] - public async Task TestPostgresDateTimeTypes(DateTime? cDate, TimeSpan? cTime, DateTime? cTimestamp, DateTime? cTimestampWithTz, TimeSpan? cInterval) + [TestCaseSource(nameof(PostgresDateTimeTypesTestCases))] + public async Task TestPostgresDateTimeTypes(DateTime? cDate, TimeSpan? cTime, DateTime? cTimestamp, DateTime? cTimestampWithTz, TimeSpan? cInterval, Instant? cTimestampNodaInstantOverride) { - await QuerySql.InsertPostgresDateTimeTypes(new QuerySql.InsertPostgresDateTimeTypesArgs { CDate = cDate, CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, CInterval = cInterval }); + await QuerySql.InsertPostgresDateTimeTypes(new QuerySql.InsertPostgresDateTimeTypesArgs { CDate = cDate, CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, CInterval = cInterval, CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }); var expected = new QuerySql.GetPostgresDateTimeTypesRow { CDate = cDate, CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, - CInterval = cInterval + CInterval = cInterval, + CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }; var actual = await QuerySql.GetPostgresDateTimeTypes(); AssertSingularEquals(expected, actual); @@ -509,6 +519,7 @@ void AssertSingularEquals(QuerySql.GetPostgresDateTimeTypesRow x, QuerySql.GetPo Assert.That(x.CTimestamp, Is.EqualTo(y.CTimestamp)); Assert.That(x.CTimestampWithTz, Is.EqualTo(y.CTimestampWithTz)); Assert.That(x.CInterval, Is.EqualTo(y.CInterval)); + Assert.That(x.CTimestampNodaInstantOverride, Is.EqualTo(y.CTimestampNodaInstantOverride)); } } diff --git a/end2end/EndToEndTests/NpgsqlTester.generated.cs b/end2end/EndToEndTests/NpgsqlTester.generated.cs index 1a467a17..18bb50c4 100644 --- a/end2end/EndToEndTests/NpgsqlTester.generated.cs +++ b/end2end/EndToEndTests/NpgsqlTester.generated.cs @@ -4,6 +4,7 @@ using System.Net.NetworkInformation; using System.Text.Json; using System.Xml; +using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; @@ -486,19 +487,28 @@ void AssertSingularEquals(QuerySql.GetPostgresNumericTypesRow x, QuerySql.GetPos } } + private static IEnumerable PostgresDateTimeTypesTestCases + { + get + { + yield return new TestCaseData(DateTime.Parse("2000-1-30"), TimeSpan.Parse("12:13:14"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2022-10-2 15:44:01+09:00").ToUniversalTime(), TimeSpan.Parse("02:03:04"), Instant.FromUtc(2022, 10, 2, 15, 44, 1)).SetName("DateTimeTypes with values"); + yield return new TestCaseData(null, null, null, null, null, null).SetName("DateTimeTypes with null values"); + } + } + [Test] - [TestCase("2000-1-30", "12:13:14", "1983-11-3 02:01:22", "2022-10-2 15:44:01+09:00", "02:03:04")] - [TestCase(null, null, null, null, null)] - public async Task TestPostgresDateTimeTypes(DateTime? cDate, TimeSpan? cTime, DateTime? cTimestamp, DateTime? cTimestampWithTz, TimeSpan? cInterval) + [TestCaseSource(nameof(PostgresDateTimeTypesTestCases))] + public async Task TestPostgresDateTimeTypes(DateTime? cDate, TimeSpan? cTime, DateTime? cTimestamp, DateTime? cTimestampWithTz, TimeSpan? cInterval, Instant? cTimestampNodaInstantOverride) { - await QuerySql.InsertPostgresDateTimeTypes(new QuerySql.InsertPostgresDateTimeTypesArgs { CDate = cDate, CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, CInterval = cInterval }); + await QuerySql.InsertPostgresDateTimeTypes(new QuerySql.InsertPostgresDateTimeTypesArgs { CDate = cDate, CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, CInterval = cInterval, CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }); var expected = new QuerySql.GetPostgresDateTimeTypesRow { CDate = cDate, CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, - CInterval = cInterval + CInterval = cInterval, + CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }; var actual = await QuerySql.GetPostgresDateTimeTypes(); AssertSingularEquals(expected, actual.Value); @@ -509,6 +519,7 @@ void AssertSingularEquals(QuerySql.GetPostgresDateTimeTypesRow x, QuerySql.GetPo Assert.That(x.CTimestamp, Is.EqualTo(y.CTimestamp)); Assert.That(x.CTimestampWithTz, Is.EqualTo(y.CTimestampWithTz)); Assert.That(x.CInterval, Is.EqualTo(y.CInterval)); + Assert.That(x.CTimestampNodaInstantOverride, Is.EqualTo(y.CTimestampNodaInstantOverride)); } } diff --git a/end2end/EndToEndTests/SqliteDapperTester.generated.cs b/end2end/EndToEndTests/SqliteDapperTester.generated.cs index 6c300290..7011e8e5 100644 --- a/end2end/EndToEndTests/SqliteDapperTester.generated.cs +++ b/end2end/EndToEndTests/SqliteDapperTester.generated.cs @@ -1,4 +1,5 @@ using SqliteDapperExampleGen; +using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; diff --git a/end2end/EndToEndTests/SqliteTester.generated.cs b/end2end/EndToEndTests/SqliteTester.generated.cs index f3cc01ba..d90f1896 100644 --- a/end2end/EndToEndTests/SqliteTester.generated.cs +++ b/end2end/EndToEndTests/SqliteTester.generated.cs @@ -1,4 +1,5 @@ using SqliteExampleGen; +using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; diff --git a/end2end/EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs b/end2end/EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs index b0ad64cd..876c7e31 100644 --- a/end2end/EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs @@ -1,5 +1,6 @@ using MySqlConnectorDapperLegacyExampleGen; using System.Text.Json; +using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; diff --git a/end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs b/end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs index 3402c78d..944bda04 100644 --- a/end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs @@ -1,5 +1,6 @@ using MySqlConnectorLegacyExampleGen; using System.Text.Json; +using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; diff --git a/end2end/EndToEndTestsLegacy/NpgsqlDapperTester.generated.cs b/end2end/EndToEndTestsLegacy/NpgsqlDapperTester.generated.cs index 9138efad..deb3d279 100644 --- a/end2end/EndToEndTestsLegacy/NpgsqlDapperTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/NpgsqlDapperTester.generated.cs @@ -4,6 +4,7 @@ using System.Net.NetworkInformation; using System.Text.Json; using System.Xml; +using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; @@ -486,19 +487,28 @@ void AssertSingularEquals(QuerySql.GetPostgresNumericTypesRow x, QuerySql.GetPos } } + private static IEnumerable PostgresDateTimeTypesTestCases + { + get + { + yield return new TestCaseData(DateTime.Parse("2000-1-30"), TimeSpan.Parse("12:13:14"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2022-10-2 15:44:01+09:00").ToUniversalTime(), TimeSpan.Parse("02:03:04"), Instant.FromUtc(2022, 10, 2, 15, 44, 1)).SetName("DateTimeTypes with values"); + yield return new TestCaseData(null, null, null, null, null, null).SetName("DateTimeTypes with null values"); + } + } + [Test] - [TestCase("2000-1-30", "12:13:14", "1983-11-3 02:01:22", "2022-10-2 15:44:01+09:00", "02:03:04")] - [TestCase(null, null, null, null, null)] - public async Task TestPostgresDateTimeTypes(DateTime? cDate, TimeSpan? cTime, DateTime? cTimestamp, DateTime? cTimestampWithTz, TimeSpan? cInterval) + [TestCaseSource(nameof(PostgresDateTimeTypesTestCases))] + public async Task TestPostgresDateTimeTypes(DateTime? cDate, TimeSpan? cTime, DateTime? cTimestamp, DateTime? cTimestampWithTz, TimeSpan? cInterval, Instant? cTimestampNodaInstantOverride) { - await QuerySql.InsertPostgresDateTimeTypes(new QuerySql.InsertPostgresDateTimeTypesArgs { CDate = cDate, CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, CInterval = cInterval }); + await QuerySql.InsertPostgresDateTimeTypes(new QuerySql.InsertPostgresDateTimeTypesArgs { CDate = cDate, CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, CInterval = cInterval, CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }); var expected = new QuerySql.GetPostgresDateTimeTypesRow { CDate = cDate, CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, - CInterval = cInterval + CInterval = cInterval, + CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }; var actual = await QuerySql.GetPostgresDateTimeTypes(); AssertSingularEquals(expected, actual); @@ -509,6 +519,7 @@ void AssertSingularEquals(QuerySql.GetPostgresDateTimeTypesRow x, QuerySql.GetPo Assert.That(x.CTimestamp, Is.EqualTo(y.CTimestamp)); Assert.That(x.CTimestampWithTz, Is.EqualTo(y.CTimestampWithTz)); Assert.That(x.CInterval, Is.EqualTo(y.CInterval)); + Assert.That(x.CTimestampNodaInstantOverride, Is.EqualTo(y.CTimestampNodaInstantOverride)); } } diff --git a/end2end/EndToEndTestsLegacy/NpgsqlTester.generated.cs b/end2end/EndToEndTestsLegacy/NpgsqlTester.generated.cs index e40e92e5..fb05b00d 100644 --- a/end2end/EndToEndTestsLegacy/NpgsqlTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/NpgsqlTester.generated.cs @@ -4,6 +4,7 @@ using System.Net.NetworkInformation; using System.Text.Json; using System.Xml; +using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; @@ -486,19 +487,28 @@ void AssertSingularEquals(QuerySql.GetPostgresNumericTypesRow x, QuerySql.GetPos } } + private static IEnumerable PostgresDateTimeTypesTestCases + { + get + { + yield return new TestCaseData(DateTime.Parse("2000-1-30"), TimeSpan.Parse("12:13:14"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2022-10-2 15:44:01+09:00").ToUniversalTime(), TimeSpan.Parse("02:03:04"), Instant.FromUtc(2022, 10, 2, 15, 44, 1)).SetName("DateTimeTypes with values"); + yield return new TestCaseData(null, null, null, null, null, null).SetName("DateTimeTypes with null values"); + } + } + [Test] - [TestCase("2000-1-30", "12:13:14", "1983-11-3 02:01:22", "2022-10-2 15:44:01+09:00", "02:03:04")] - [TestCase(null, null, null, null, null)] - public async Task TestPostgresDateTimeTypes(DateTime? cDate, TimeSpan? cTime, DateTime? cTimestamp, DateTime? cTimestampWithTz, TimeSpan? cInterval) + [TestCaseSource(nameof(PostgresDateTimeTypesTestCases))] + public async Task TestPostgresDateTimeTypes(DateTime? cDate, TimeSpan? cTime, DateTime? cTimestamp, DateTime? cTimestampWithTz, TimeSpan? cInterval, Instant? cTimestampNodaInstantOverride) { - await QuerySql.InsertPostgresDateTimeTypes(new QuerySql.InsertPostgresDateTimeTypesArgs { CDate = cDate, CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, CInterval = cInterval }); + await QuerySql.InsertPostgresDateTimeTypes(new QuerySql.InsertPostgresDateTimeTypesArgs { CDate = cDate, CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, CInterval = cInterval, CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }); var expected = new QuerySql.GetPostgresDateTimeTypesRow { CDate = cDate, CTime = cTime, CTimestamp = cTimestamp, CTimestampWithTz = cTimestampWithTz, - CInterval = cInterval + CInterval = cInterval, + CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }; var actual = await QuerySql.GetPostgresDateTimeTypes(); AssertSingularEquals(expected, actual); @@ -509,6 +519,7 @@ void AssertSingularEquals(QuerySql.GetPostgresDateTimeTypesRow x, QuerySql.GetPo Assert.That(x.CTimestamp, Is.EqualTo(y.CTimestamp)); Assert.That(x.CTimestampWithTz, Is.EqualTo(y.CTimestampWithTz)); Assert.That(x.CInterval, Is.EqualTo(y.CInterval)); + Assert.That(x.CTimestampNodaInstantOverride, Is.EqualTo(y.CTimestampNodaInstantOverride)); } } diff --git a/end2end/EndToEndTestsLegacy/SqliteDapperTester.generated.cs b/end2end/EndToEndTestsLegacy/SqliteDapperTester.generated.cs index b0956df6..9a1bea7a 100644 --- a/end2end/EndToEndTestsLegacy/SqliteDapperTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/SqliteDapperTester.generated.cs @@ -1,4 +1,5 @@ using SqliteDapperLegacyExampleGen; +using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; diff --git a/end2end/EndToEndTestsLegacy/SqliteTester.generated.cs b/end2end/EndToEndTestsLegacy/SqliteTester.generated.cs index c50edf9f..27113668 100644 --- a/end2end/EndToEndTestsLegacy/SqliteTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/SqliteTester.generated.cs @@ -1,4 +1,5 @@ using SqliteLegacyExampleGen; +using NodaTime; using NUnit.Framework; using NUnit.Framework.Legacy; using System; diff --git a/examples/MySqlConnectorDapperExample/MySqlConnectorDapperExample.csproj b/examples/MySqlConnectorDapperExample/MySqlConnectorDapperExample.csproj index 7ee3921e..78b428c8 100644 --- a/examples/MySqlConnectorDapperExample/MySqlConnectorDapperExample.csproj +++ b/examples/MySqlConnectorDapperExample/MySqlConnectorDapperExample.csproj @@ -15,6 +15,7 @@ + \ No newline at end of file diff --git a/examples/MySqlConnectorDapperExample/request.json b/examples/MySqlConnectorDapperExample/request.json index 19472626..09a43ac1 100644 --- a/examples/MySqlConnectorDapperExample/request.json +++ b/examples/MySqlConnectorDapperExample/request.json @@ -3771,5 +3771,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6Ik15U3FsQ29ubmVjdG9yRGFwcGVyRXhhbXBsZUdlbiIsInVzZURhcHBlciI6dHJ1ZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOnRydWV9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19XSwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6Ik15U3FsQ29ubmVjdG9yRGFwcGVyRXhhbXBsZUdlbiIsInVzZURhcHBlciI6dHJ1ZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwidXNlTm9kYVRpbWUiOmZhbHNlLCJvdmVycmlkZXMiOlt7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF9pbnQiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdGltZXN0YW1wIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6dHJ1ZX19LHsiY29sdW1uIjoiKjpjX2pzb25fc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" } \ No newline at end of file diff --git a/examples/MySqlConnectorDapperExample/request.message b/examples/MySqlConnectorDapperExample/request.message index 7390bc73850bac3a407464746205a41c872f074f..7a9cb19ed8ddf920aa92411285d549f0bf249dcd 100644 GIT binary patch delta 39 vcmbPsl5y2Z#tkV+j7KJ?Can=FEl%~zPe}~P%uQ9YN=wWsPTkC(+|CF9PG%39 delta 28 kcmZ2=l5yHe#tkV+j2kAWCasz5!00r2e=_^#ykr|j0Jbj+l>h($ diff --git a/examples/MySqlConnectorDapperLegacyExample/MySqlConnectorDapperLegacyExample.csproj b/examples/MySqlConnectorDapperLegacyExample/MySqlConnectorDapperLegacyExample.csproj index 7acee930..6d3f7908 100644 --- a/examples/MySqlConnectorDapperLegacyExample/MySqlConnectorDapperLegacyExample.csproj +++ b/examples/MySqlConnectorDapperLegacyExample/MySqlConnectorDapperLegacyExample.csproj @@ -15,6 +15,7 @@ + \ No newline at end of file diff --git a/examples/MySqlConnectorDapperLegacyExample/request.json b/examples/MySqlConnectorDapperLegacyExample/request.json index 337b546b..aff66a41 100644 --- a/examples/MySqlConnectorDapperLegacyExample/request.json +++ b/examples/MySqlConnectorDapperLegacyExample/request.json @@ -3771,5 +3771,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JEYXBwZXJMZWdhY3lFeGFtcGxlR2VuIiwidXNlRGFwcGVyIjp0cnVlLCJvdmVycmlkZURhcHBlclZlcnNpb24iOiIiLCJvdmVycmlkZXMiOlt7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF9pbnQiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdGltZXN0YW1wIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6dHJ1ZX19LHsiY29sdW1uIjoiKjpjX2pzb25fc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JEYXBwZXJMZWdhY3lFeGFtcGxlR2VuIiwidXNlRGFwcGVyIjp0cnVlLCJvdmVycmlkZURhcHBlclZlcnNpb24iOiIiLCJ1c2VOb2RhVGltZSI6ZmFsc2UsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X2ludCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJpbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3ZhcmNoYXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF90aW1lc3RhbXAiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjp0cnVlfX0seyJjb2x1bW4iOiIqOmNfanNvbl9zdHJpbmdfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fV0sImRlYnVnUmVxdWVzdCI6ZmFsc2V9" } \ No newline at end of file diff --git a/examples/MySqlConnectorDapperLegacyExample/request.message b/examples/MySqlConnectorDapperLegacyExample/request.message index 3aa6a63e050a2c057d673b39eadb421db72f7725..d507c9657a385a5e38d608ff501371f7871fa6d3 100644 GIT binary patch delta 39 vcmdmSlJU$*#tjuojF%=?ChZa`El%~zPe}~P%uQ9YN=wWsPTg#n+|CF9U~~{f delta 28 kcmX?el5xjL#tjuojQb{6CheN+!{{{GE`@#bgk&2=0KW7K%K!iX diff --git a/examples/MySqlConnectorExample/MySqlConnectorExample.csproj b/examples/MySqlConnectorExample/MySqlConnectorExample.csproj index 6762e189..1c4d75ff 100644 --- a/examples/MySqlConnectorExample/MySqlConnectorExample.csproj +++ b/examples/MySqlConnectorExample/MySqlConnectorExample.csproj @@ -14,6 +14,7 @@ + \ No newline at end of file diff --git a/examples/MySqlConnectorExample/request.json b/examples/MySqlConnectorExample/request.json index b024268c..38d6d266 100644 --- a/examples/MySqlConnectorExample/request.json +++ b/examples/MySqlConnectorExample/request.json @@ -3771,5 +3771,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6Ik15U3FsQ29ubmVjdG9yRXhhbXBsZUdlbiIsInVzZURhcHBlciI6ZmFsc2UsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X2ludCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJpbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3ZhcmNoYXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF90aW1lc3RhbXAiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjp0cnVlfX0seyJjb2x1bW4iOiIqOmNfanNvbl9zdHJpbmdfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fV0sImRlYnVnUmVxdWVzdCI6ZmFsc2V9" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6Ik15U3FsQ29ubmVjdG9yRXhhbXBsZUdlbiIsInVzZURhcHBlciI6ZmFsc2UsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsInVzZU5vZGFUaW1lIjpmYWxzZSwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOnRydWV9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19XSwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" } \ No newline at end of file diff --git a/examples/MySqlConnectorExample/request.message b/examples/MySqlConnectorExample/request.message index 7e0add10a3f0fb5e2d6edfe1760eacd341097180..216298c63c4aaeb8656122bf8601e819cc1405b5 100644 GIT binary patch delta 39 vcmZoW$vEpI + \ No newline at end of file diff --git a/examples/MySqlConnectorLegacyExample/request.json b/examples/MySqlConnectorLegacyExample/request.json index 9407eaa2..24f79ce3 100644 --- a/examples/MySqlConnectorLegacyExample/request.json +++ b/examples/MySqlConnectorLegacyExample/request.json @@ -3771,5 +3771,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JMZWdhY3lFeGFtcGxlR2VuIiwidXNlRGFwcGVyIjpmYWxzZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOnRydWV9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19XSwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JMZWdhY3lFeGFtcGxlR2VuIiwidXNlRGFwcGVyIjpmYWxzZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwidXNlTm9kYVRpbWUiOmZhbHNlLCJvdmVycmlkZXMiOlt7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF9pbnQiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdGltZXN0YW1wIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6dHJ1ZX19LHsiY29sdW1uIjoiKjpjX2pzb25fc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" } \ No newline at end of file diff --git a/examples/MySqlConnectorLegacyExample/request.message b/examples/MySqlConnectorLegacyExample/request.message index 2356033c8c07bde20d374fa3b750af6e808bb4c8..5301c5388af3c3aabd1079bab02ab5e2bc9040e6 100644 GIT binary patch delta 39 vcmZ2+l5x*T#tpeijAtk3C2bWdEl%~zPe}~P%uQ9YN=wWsPTj1S+|CF9SM3k< delta 28 kcmdmUl5xdJ#tpeij5{aiC2gJT!00qtFNJ+`L$VDc0Jt3sUjP6A diff --git a/examples/NpgsqlDapperExample/Models.cs b/examples/NpgsqlDapperExample/Models.cs index 1be88179..c04761d9 100644 --- a/examples/NpgsqlDapperExample/Models.cs +++ b/examples/NpgsqlDapperExample/Models.cs @@ -1,4 +1,6 @@ // auto-generated by sqlc - do not edit +using NodaTime; +using NodaTime.Extensions; using NpgsqlTypes; using System; using System.Collections.Generic; @@ -50,6 +52,7 @@ public class PostgresDatetimeType public DateTime? CTimestamp { get; init; } public DateTime? CTimestampWithTz { get; init; } public TimeSpan? CInterval { get; init; } + public DateTime? CTimestampNodaInstantOverride { get; init; } }; public class PostgresNetworkType { diff --git a/examples/NpgsqlDapperExample/NpgsqlDapperExample.csproj b/examples/NpgsqlDapperExample/NpgsqlDapperExample.csproj index 63b32191..19743a10 100644 --- a/examples/NpgsqlDapperExample/NpgsqlDapperExample.csproj +++ b/examples/NpgsqlDapperExample/NpgsqlDapperExample.csproj @@ -14,6 +14,7 @@ + \ No newline at end of file diff --git a/examples/NpgsqlDapperExample/QuerySql.cs b/examples/NpgsqlDapperExample/QuerySql.cs index c3577ca0..59f993bb 100644 --- a/examples/NpgsqlDapperExample/QuerySql.cs +++ b/examples/NpgsqlDapperExample/QuerySql.cs @@ -5,6 +5,8 @@ // ReSharper disable NotAccessedPositionalProperty.Global // ReSharper disable UnusedAutoPropertyAccessor.Global using Dapper; +using NodaTime; +using NodaTime.Extensions; using Npgsql; using NpgsqlTypes; using System; @@ -901,7 +903,7 @@ public class GetPostgresStringTypesTextSearchArgs return await this.Transaction.Connection.QueryFirstOrDefaultAsync(GetPostgresStringTypesTextSearchSql, queryParams, transaction: this.Transaction); } - private const string InsertPostgresDateTimeTypesSql = " INSERT INTO postgres_datetime_types ( c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval ) VALUES (@c_date, @c_time, @c_timestamp, @c_timestamp_with_tz, @c_interval)"; + private const string InsertPostgresDateTimeTypesSql = " INSERT INTO postgres_datetime_types ( c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override ) VALUES (@c_date, @c_time, @c_timestamp, @c_timestamp_with_tz, @c_interval, @c_timestamp_noda_instant_override)"; public class InsertPostgresDateTimeTypesArgs { public DateTime? CDate { get; init; } @@ -909,6 +911,7 @@ public class InsertPostgresDateTimeTypesArgs public DateTime? CTimestamp { get; init; } public DateTime? CTimestampWithTz { get; init; } public TimeSpan? CInterval { get; init; } + public Instant? CTimestampNodaInstantOverride { get; init; } }; public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs args) { @@ -918,6 +921,7 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar queryParams.Add("c_timestamp", args.CTimestamp); queryParams.Add("c_timestamp_with_tz", args.CTimestampWithTz); queryParams.Add("c_interval", args.CInterval); + queryParams.Add("c_timestamp_noda_instant_override", args.CTimestampNodaInstantOverride?.ToDateTimeUtc().ToLocalTime() ?? null); if (this.Transaction == null) { using (var connection = new NpgsqlConnection(ConnectionString)) @@ -930,7 +934,7 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar await this.Transaction.Connection.ExecuteAsync(InsertPostgresDateTimeTypesSql, queryParams, transaction: this.Transaction); } - private const string GetPostgresDateTimeTypesSql = "SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval FROM postgres_datetime_types LIMIT 1"; + private const string GetPostgresDateTimeTypesSql = "SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override FROM postgres_datetime_types LIMIT 1"; public class GetPostgresDateTimeTypesRow { public DateTime? CDate { get; init; } @@ -938,6 +942,7 @@ public class GetPostgresDateTimeTypesRow public DateTime? CTimestamp { get; init; } public DateTime? CTimestampWithTz { get; init; } public TimeSpan? CInterval { get; init; } + public Instant? CTimestampNodaInstantOverride { get; init; } }; public async Task GetPostgresDateTimeTypes() { @@ -1017,8 +1022,8 @@ public async Task InsertPostgresDateTimeTypesBatch(List + { + public override Instant Parse(object value) + { + if (value is DateTime dt) + return dt.ToInstant(); + throw new DataException($"Cannot convert {value?.GetType()} to Instant"); + } + + public override void SetValue(IDbDataParameter parameter, Instant value) + { + parameter.Value = value; + } + } + private class JsonElementTypeHandler : SqlMapper.TypeHandler { public override JsonElement Parse(object value) @@ -50,6 +68,7 @@ public override void SetValue(IDbDataParameter parameter, XmlDocument? value) public static void ConfigureSqlMapper() { + SqlMapper.AddTypeHandler(typeof(Instant), new NodaInstantTypeHandler()); SqlMapper.AddTypeHandler(typeof(JsonElement), new JsonElementTypeHandler()); SqlMapper.AddTypeHandler(typeof(XmlDocument), new XmlDocumentTypeHandler()); SqlMapper.AddTypeHandler(typeof(NpgsqlPoint), new NpgsqlTypeHandler()); diff --git a/examples/NpgsqlDapperExample/request.json b/examples/NpgsqlDapperExample/request.json index 6d9405cf..3f21284f 100644 --- a/examples/NpgsqlDapperExample/request.json +++ b/examples/NpgsqlDapperExample/request.json @@ -13,7 +13,7 @@ "codegen": { "out": "examples/NpgsqlDapperExample", "plugin": "csharp", - "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiTnBnc3FsRGFwcGVyRXhhbXBsZUdlbiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0UG9zdGdyZXNGdW5jdGlvbnM6bWF4X2ludGVnZXIiLCJjc2hhcnBfdHlwZSI6eyJub3ROdWxsIjpmYWxzZSwidHlwZSI6ImludCJ9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiJHZXRQb3N0Z3Jlc0Z1bmN0aW9uczptYXhfdGltZXN0YW1wIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6dHJ1ZSwidHlwZSI6IkRhdGVUaW1lIn19LHsiY29sdW1uIjoiR2V0UG9zdGdyZXNTcGVjaWFsVHlwZXNDbnQ6Y19qc29uIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJKc29uRWxlbWVudCJ9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzU3BlY2lhbFR5cGVzQ250OmNfanNvbmIiLCJjc2hhcnBfdHlwZSI6eyJub3ROdWxsIjpmYWxzZSwidHlwZSI6Ikpzb25FbGVtZW50In19LHsiY29sdW1uIjoiKjpjX2pzb25fc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiIqOmNfeG1sX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiKjpjX21hY2FkZHI4IiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJzdHJpbmcifX1dLCJ0YXJnZXRGcmFtZXdvcmsiOiJuZXQ4LjAiLCJ1c2VEYXBwZXIiOnRydWV9", + "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiTnBnc3FsRGFwcGVyRXhhbXBsZUdlbiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0UG9zdGdyZXNGdW5jdGlvbnM6bWF4X2ludGVnZXIiLCJjc2hhcnBfdHlwZSI6eyJub3ROdWxsIjpmYWxzZSwidHlwZSI6ImludCJ9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiJHZXRQb3N0Z3Jlc0Z1bmN0aW9uczptYXhfdGltZXN0YW1wIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6dHJ1ZSwidHlwZSI6IkRhdGVUaW1lIn19LHsiY29sdW1uIjoiR2V0UG9zdGdyZXNTcGVjaWFsVHlwZXNDbnQ6Y19qc29uIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJKc29uRWxlbWVudCJ9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzU3BlY2lhbFR5cGVzQ250OmNfanNvbmIiLCJjc2hhcnBfdHlwZSI6eyJub3ROdWxsIjpmYWxzZSwidHlwZSI6Ikpzb25FbGVtZW50In19LHsiY29sdW1uIjoiKjpjX2pzb25fc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiIqOmNfeG1sX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiKjpjX21hY2FkZHI4IiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiIqOmNfdGltZXN0YW1wX25vZGFfaW5zdGFudF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoiSW5zdGFudCJ9fV0sInRhcmdldEZyYW1ld29yayI6Im5ldDguMCIsInVzZURhcHBlciI6dHJ1ZX0=", "process": { "cmd": "./dist/LocalRunner" } @@ -349,6 +349,17 @@ "schema": "pg_catalog", "name": "interval" } + }, + { + "name": "c_timestamp_noda_instant_override", + "length": -1, + "table": { + "name": "postgres_datetime_types" + }, + "type": { + "schema": "pg_catalog", + "name": "timestamp" + } } ] }, @@ -34495,7 +34506,7 @@ "filename": "query.sql" }, { - "text": "\nINSERT INTO postgres_datetime_types\n(\n c_date,\n c_time,\n c_timestamp,\n c_timestamp_with_tz,\n c_interval\n) VALUES ($1, $2, $3, $4, $5)", + "text": "\nINSERT INTO postgres_datetime_types\n(\n c_date,\n c_time,\n c_timestamp,\n c_timestamp_with_tz,\n c_interval,\n c_timestamp_noda_instant_override\n) VALUES ($1, $2, $3, $4, $5, $6)", "name": "InsertPostgresDateTimeTypes", "cmd": ":exec", "parameters": [ @@ -34573,6 +34584,21 @@ }, "originalName": "c_interval" } + }, + { + "number": 6, + "column": { + "name": "c_timestamp_noda_instant_override", + "length": -1, + "table": { + "schema": "public", + "name": "postgres_datetime_types" + }, + "type": { + "name": "pg_catalog.timestamp" + }, + "originalName": "c_timestamp_noda_instant_override" + } } ], "comments": [ @@ -34584,7 +34610,7 @@ } }, { - "text": "SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval FROM postgres_datetime_types LIMIT 1", + "text": "SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override FROM postgres_datetime_types LIMIT 1", "name": "GetPostgresDateTimeTypes", "cmd": ":one", "columns": [ @@ -34646,6 +34672,18 @@ "name": "interval" }, "originalName": "c_interval" + }, + { + "name": "c_timestamp_noda_instant_override", + "length": -1, + "table": { + "name": "postgres_datetime_types" + }, + "type": { + "schema": "pg_catalog", + "name": "timestamp" + }, + "originalName": "c_timestamp_noda_instant_override" } ], "filename": "query.sql" @@ -36194,5 +36232,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6Ik5wZ3NxbERhcHBlckV4YW1wbGVHZW4iLCJ1c2VEYXBwZXIiOnRydWUsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0UG9zdGdyZXNGdW5jdGlvbnM6bWF4X2ludGVnZXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRQb3N0Z3Jlc0Z1bmN0aW9uczptYXhfdGltZXN0YW1wIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6dHJ1ZX19LHsiY29sdW1uIjoiR2V0UG9zdGdyZXNTcGVjaWFsVHlwZXNDbnQ6Y19qc29uIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6Ikpzb25FbGVtZW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzU3BlY2lhbFR5cGVzQ250OmNfanNvbmIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSnNvbkVsZW1lbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2pzb25fc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfeG1sX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX21hY2FkZHI4IiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6Ik5wZ3NxbERhcHBlckV4YW1wbGVHZW4iLCJ1c2VEYXBwZXIiOnRydWUsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsInVzZU5vZGFUaW1lIjpmYWxzZSwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRQb3N0Z3Jlc0Z1bmN0aW9uczptYXhfaW50ZWdlciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJpbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0UG9zdGdyZXNGdW5jdGlvbnM6bWF4X3ZhcmNoYXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzRnVuY3Rpb25zOm1heF90aW1lc3RhbXAiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjp0cnVlfX0seyJjb2x1bW4iOiJHZXRQb3N0Z3Jlc1NwZWNpYWxUeXBlc0NudDpjX2pzb24iLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSnNvbkVsZW1lbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0UG9zdGdyZXNTcGVjaWFsVHlwZXNDbnQ6Y19qc29uYiIsImNzaGFycF90eXBlIjp7InR5cGUiOiJKc29uRWxlbWVudCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfanNvbl9zdHJpbmdfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y194bWxfc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfbWFjYWRkcjgiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190aW1lc3RhbXBfbm9kYV9pbnN0YW50X292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6Ikluc3RhbnQiLCJub3ROdWxsIjpmYWxzZX19XSwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" } \ No newline at end of file diff --git a/examples/NpgsqlDapperExample/request.message b/examples/NpgsqlDapperExample/request.message index f88a261e..5f433518 100644 --- a/examples/NpgsqlDapperExample/request.message +++ b/examples/NpgsqlDapperExample/request.message @@ -1,9 +1,9 @@ - + 2 -postgresql-examples/config/postgresql/authors/schema.sql+examples/config/postgresql/types/schema.sql",examples/config/postgresql/authors/query.sql"*examples/config/postgresql/types/query.sqlb -examples/NpgsqlDapperExamplecsharp{"debugRequest":true,"generateCsproj":true,"namespaceName":"NpgsqlDapperExampleGen","overrides":[{"column":"GetPostgresFunctions:max_integer","csharp_type":{"notNull":false,"type":"int"}},{"column":"GetPostgresFunctions:max_varchar","csharp_type":{"notNull":false,"type":"string"}},{"column":"GetPostgresFunctions:max_timestamp","csharp_type":{"notNull":true,"type":"DateTime"}},{"column":"GetPostgresSpecialTypesCnt:c_json","csharp_type":{"notNull":false,"type":"JsonElement"}},{"column":"GetPostgresSpecialTypesCnt:c_jsonb","csharp_type":{"notNull":false,"type":"JsonElement"}},{"column":"*:c_json_string_override","csharp_type":{"notNull":false,"type":"string"}},{"column":"*:c_xml_string_override","csharp_type":{"notNull":false,"type":"string"}},{"column":"*:c_macaddr8","csharp_type":{"notNull":false,"type":"string"}}],"targetFramework":"net8.0","useDapper":true}* -./dist/LocalRunner public"public +postgresql-examples/config/postgresql/authors/schema.sql+examples/config/postgresql/types/schema.sql",examples/config/postgresql/authors/query.sql"*examples/config/postgresql/types/query.sqlb +examples/NpgsqlDapperExamplecsharp{"debugRequest":true,"generateCsproj":true,"namespaceName":"NpgsqlDapperExampleGen","overrides":[{"column":"GetPostgresFunctions:max_integer","csharp_type":{"notNull":false,"type":"int"}},{"column":"GetPostgresFunctions:max_varchar","csharp_type":{"notNull":false,"type":"string"}},{"column":"GetPostgresFunctions:max_timestamp","csharp_type":{"notNull":true,"type":"DateTime"}},{"column":"GetPostgresSpecialTypesCnt:c_json","csharp_type":{"notNull":false,"type":"JsonElement"}},{"column":"GetPostgresSpecialTypesCnt:c_jsonb","csharp_type":{"notNull":false,"type":"JsonElement"}},{"column":"*:c_json_string_override","csharp_type":{"notNull":false,"type":"string"}},{"column":"*:c_xml_string_override","csharp_type":{"notNull":false,"type":"string"}},{"column":"*:c_macaddr8","csharp_type":{"notNull":false,"type":"string"}},{"column":"*:c_timestamp_noda_instant_override","csharp_type":{"notNull":false,"type":"Instant"}}],"targetFramework":"net8.0","useDapper":true}* +./dist/LocalRunner public"public authors) id0R authorsb  bigserial& name0R authorsbtext# @@ -43,7 +43,7 @@ pg_catalogvarcharP c_character_varying0Rpostgres_string_typesb pg_catalogvarchar8 c_bpchar0Rpostgres_string_typesbbpchar4 -c_text0Rpostgres_string_typesbtext +c_text0Rpostgres_string_typesbtext postgres_datetime_types6 c_date0Rpostgres_datetime_typesbdateB c_time0Rpostgres_datetime_typesb @@ -54,7 +54,9 @@ pg_catalog timestampV pg_catalog timestamptzJ c_interval0Rpostgres_datetime_typesb -pg_cataloginterval +pg_catalogintervalb +!c_timestamp_noda_instant_override0Rpostgres_datetime_typesb +pg_catalog timestamp postgres_network_types5 c_cidr0Rpostgres_network_typesbcidr5 c_inet0Rpostgres_network_typesbinet; @@ -10547,24 +10549,26 @@ LIMIT 1 GetPostgresStringTypesTextSearch:one"0 tsvectorztsv" rnk0@breal*%! -to_tsquery0btext: query.sql - +to_tsquery0btext: query.sql + INSERT INTO postgres_datetime_types ( c_date, c_time, c_timestamp, c_timestamp_with_tz, - c_interval -) VALUES ($1, $2, $3, $4, $5)InsertPostgresDateTimeTypes:exec*JF + c_interval, + c_timestamp_noda_instant_override +) VALUES ($1, $2, $3, $4, $5, $6)InsertPostgresDateTimeTypes:exec*JF c_date0R!publicpostgres_datetime_typesbdatezc_date*UQ c_time0R!publicpostgres_datetime_typesbpg_catalog.timezc_time*d` c_timestamp0R!publicpostgres_datetime_typesbpg_catalog.timestampz c_timestamp*vr c_timestamp_with_tz0R!publicpostgres_datetime_typesbpg_catalog.timestamptzzc_timestamp_with_tz*a] c_interval0R!publicpostgres_datetime_typesbpg_catalog.intervalz -c_interval2 DateTime types : query.sqlBpostgres_datetime_types -hSELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval FROM postgres_datetime_types LIMIT 1GetPostgresDateTimeTypes:one"> +c_interval* +!c_timestamp_noda_instant_override0R!publicpostgres_datetime_typesbpg_catalog.timestampz!c_timestamp_noda_instant_override2 DateTime types : query.sqlBpostgres_datetime_types +SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override FROM postgres_datetime_types LIMIT 1GetPostgresDateTimeTypes:one"> c_date0Rpostgres_datetime_typesbdatezc_date"J c_time0Rpostgres_datetime_typesb pg_catalogtimezc_time"Y @@ -10575,7 +10579,9 @@ pg_catalog timestamptzzc_timestamp_with_tz"V c_interval0Rpostgres_datetime_typesb pg_catalogintervalz -c_interval: query.sqlY +c_interval" +!c_timestamp_noda_instant_override0Rpostgres_datetime_typesb +pg_catalog timestampz!c_timestamp_noda_instant_override: query.sqlY &TRUNCATE TABLE postgres_datetime_typesTruncatePostgresDateTimeTypes:exec: query.sql SELECT c_date, @@ -10911,4 +10917,4 @@ hSELECT c_point, c_line, c_lseg, c_box, c_path, c_polygon, c_circle FROM postgre c_path0Rpostgres_geometric_typesbpathzc_path"H c_polygon0Rpostgres_geometric_typesb polygonz c_polygon"E c_circle0Rpostgres_geometric_typesbcirclezc_circle: query.sqlU -'TRUNCATE TABLE postgres_geometric_typesTruncatePostgresGeoTypes:exec: query.sql"v1.30.0*{"overrideDriverVersion":"","generateCsproj":true,"targetFramework":"net8.0","namespaceName":"NpgsqlDapperExampleGen","useDapper":true,"overrideDapperVersion":"","overrides":[{"column":"GetPostgresFunctions:max_integer","csharp_type":{"type":"int","notNull":false}},{"column":"GetPostgresFunctions:max_varchar","csharp_type":{"type":"string","notNull":false}},{"column":"GetPostgresFunctions:max_timestamp","csharp_type":{"type":"DateTime","notNull":true}},{"column":"GetPostgresSpecialTypesCnt:c_json","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"GetPostgresSpecialTypesCnt:c_jsonb","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"*:c_json_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_xml_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_macaddr8","csharp_type":{"type":"string","notNull":false}}],"debugRequest":false} \ No newline at end of file +'TRUNCATE TABLE postgres_geometric_typesTruncatePostgresGeoTypes:exec: query.sql"v1.30.0*{"overrideDriverVersion":"","generateCsproj":true,"targetFramework":"net8.0","namespaceName":"NpgsqlDapperExampleGen","useDapper":true,"overrideDapperVersion":"","useNodaTime":false,"overrides":[{"column":"GetPostgresFunctions:max_integer","csharp_type":{"type":"int","notNull":false}},{"column":"GetPostgresFunctions:max_varchar","csharp_type":{"type":"string","notNull":false}},{"column":"GetPostgresFunctions:max_timestamp","csharp_type":{"type":"DateTime","notNull":true}},{"column":"GetPostgresSpecialTypesCnt:c_json","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"GetPostgresSpecialTypesCnt:c_jsonb","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"*:c_json_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_xml_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_macaddr8","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_timestamp_noda_instant_override","csharp_type":{"type":"Instant","notNull":false}}],"debugRequest":false} \ No newline at end of file diff --git a/examples/NpgsqlDapperLegacyExample/Models.cs b/examples/NpgsqlDapperLegacyExample/Models.cs index aa6d7b9f..879d51d1 100644 --- a/examples/NpgsqlDapperLegacyExample/Models.cs +++ b/examples/NpgsqlDapperLegacyExample/Models.cs @@ -1,6 +1,8 @@ // auto-generated by sqlc - do not edit namespace NpgsqlDapperLegacyExampleGen { + using NodaTime; + using NodaTime.Extensions; using NpgsqlTypes; using System; using System.Collections.Generic; @@ -51,6 +53,7 @@ public class PostgresDatetimeType public DateTime? CTimestamp { get; set; } public DateTime? CTimestampWithTz { get; set; } public TimeSpan? CInterval { get; set; } + public DateTime? CTimestampNodaInstantOverride { get; set; } }; public class PostgresNetworkType { diff --git a/examples/NpgsqlDapperLegacyExample/NpgsqlDapperLegacyExample.csproj b/examples/NpgsqlDapperLegacyExample/NpgsqlDapperLegacyExample.csproj index 9fc4df6b..fd6d29c5 100644 --- a/examples/NpgsqlDapperLegacyExample/NpgsqlDapperLegacyExample.csproj +++ b/examples/NpgsqlDapperLegacyExample/NpgsqlDapperLegacyExample.csproj @@ -14,6 +14,7 @@ + \ No newline at end of file diff --git a/examples/NpgsqlDapperLegacyExample/QuerySql.cs b/examples/NpgsqlDapperLegacyExample/QuerySql.cs index 4f076194..8e9327d0 100644 --- a/examples/NpgsqlDapperLegacyExample/QuerySql.cs +++ b/examples/NpgsqlDapperLegacyExample/QuerySql.cs @@ -7,6 +7,8 @@ namespace NpgsqlDapperLegacyExampleGen { using Dapper; + using NodaTime; + using NodaTime.Extensions; using Npgsql; using NpgsqlTypes; using System; @@ -902,7 +904,7 @@ public async Task GetPostgresStringTypesTex return await this.Transaction.Connection.QueryFirstOrDefaultAsync(GetPostgresStringTypesTextSearchSql, queryParams, transaction: this.Transaction); } - private const string InsertPostgresDateTimeTypesSql = " INSERT INTO postgres_datetime_types ( c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval ) VALUES (@c_date, @c_time, @c_timestamp, @c_timestamp_with_tz, @c_interval)"; + private const string InsertPostgresDateTimeTypesSql = " INSERT INTO postgres_datetime_types ( c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override ) VALUES (@c_date, @c_time, @c_timestamp, @c_timestamp_with_tz, @c_interval, @c_timestamp_noda_instant_override)"; public class InsertPostgresDateTimeTypesArgs { public DateTime? CDate { get; set; } @@ -910,6 +912,7 @@ public class InsertPostgresDateTimeTypesArgs public DateTime? CTimestamp { get; set; } public DateTime? CTimestampWithTz { get; set; } public TimeSpan? CInterval { get; set; } + public Instant? CTimestampNodaInstantOverride { get; set; } }; public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs args) { @@ -919,6 +922,7 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar queryParams.Add("c_timestamp", args.CTimestamp); queryParams.Add("c_timestamp_with_tz", args.CTimestampWithTz); queryParams.Add("c_interval", args.CInterval); + queryParams.Add("c_timestamp_noda_instant_override", args.CTimestampNodaInstantOverride?.ToDateTimeUtc().ToLocalTime() ?? null); if (this.Transaction == null) { using (var connection = new NpgsqlConnection(ConnectionString)) @@ -931,7 +935,7 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar await this.Transaction.Connection.ExecuteAsync(InsertPostgresDateTimeTypesSql, queryParams, transaction: this.Transaction); } - private const string GetPostgresDateTimeTypesSql = "SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval FROM postgres_datetime_types LIMIT 1"; + private const string GetPostgresDateTimeTypesSql = "SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override FROM postgres_datetime_types LIMIT 1"; public class GetPostgresDateTimeTypesRow { public DateTime? CDate { get; set; } @@ -939,6 +943,7 @@ public class GetPostgresDateTimeTypesRow public DateTime? CTimestamp { get; set; } public DateTime? CTimestampWithTz { get; set; } public TimeSpan? CInterval { get; set; } + public Instant? CTimestampNodaInstantOverride { get; set; } }; public async Task GetPostgresDateTimeTypes() { @@ -1018,8 +1023,8 @@ public async Task InsertPostgresDateTimeTypesBatch(List + { + public override Instant Parse(object value) + { + if (value is DateTime dt) + return dt.ToInstant(); + throw new DataException($"Cannot convert {value?.GetType()} to Instant"); + } + + public override void SetValue(IDbDataParameter parameter, Instant value) + { + parameter.Value = value; + } + } + private class JsonElementTypeHandler : SqlMapper.TypeHandler { public override JsonElement Parse(object value) @@ -51,6 +69,7 @@ public override void SetValue(IDbDataParameter parameter, XmlDocument value) public static void ConfigureSqlMapper() { + SqlMapper.AddTypeHandler(typeof(Instant), new NodaInstantTypeHandler()); SqlMapper.AddTypeHandler(typeof(JsonElement), new JsonElementTypeHandler()); SqlMapper.AddTypeHandler(typeof(XmlDocument), new XmlDocumentTypeHandler()); SqlMapper.AddTypeHandler(typeof(NpgsqlPoint), new NpgsqlTypeHandler()); diff --git a/examples/NpgsqlDapperLegacyExample/request.json b/examples/NpgsqlDapperLegacyExample/request.json index a0ee73f5..db01be80 100644 --- a/examples/NpgsqlDapperLegacyExample/request.json +++ b/examples/NpgsqlDapperLegacyExample/request.json @@ -13,7 +13,7 @@ "codegen": { "out": "examples/NpgsqlDapperLegacyExample", "plugin": "csharp", - "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiTnBnc3FsRGFwcGVyTGVnYWN5RXhhbXBsZUdlbiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0UG9zdGdyZXNGdW5jdGlvbnM6bWF4X2ludGVnZXIiLCJjc2hhcnBfdHlwZSI6eyJub3ROdWxsIjpmYWxzZSwidHlwZSI6ImludCJ9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiJHZXRQb3N0Z3Jlc0Z1bmN0aW9uczptYXhfdGltZXN0YW1wIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6dHJ1ZSwidHlwZSI6IkRhdGVUaW1lIn19LHsiY29sdW1uIjoiR2V0UG9zdGdyZXNTcGVjaWFsVHlwZXNDbnQ6Y19qc29uIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJKc29uRWxlbWVudCJ9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzU3BlY2lhbFR5cGVzQ250OmNfanNvbmIiLCJjc2hhcnBfdHlwZSI6eyJub3ROdWxsIjpmYWxzZSwidHlwZSI6Ikpzb25FbGVtZW50In19LHsiY29sdW1uIjoiKjpjX2pzb25fc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiIqOmNfeG1sX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiKjpjX21hY2FkZHI4IiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJzdHJpbmcifX1dLCJ0YXJnZXRGcmFtZXdvcmsiOiJuZXRzdGFuZGFyZDIuMCIsInVzZURhcHBlciI6dHJ1ZX0=", + "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiTnBnc3FsRGFwcGVyTGVnYWN5RXhhbXBsZUdlbiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0UG9zdGdyZXNGdW5jdGlvbnM6bWF4X2ludGVnZXIiLCJjc2hhcnBfdHlwZSI6eyJub3ROdWxsIjpmYWxzZSwidHlwZSI6ImludCJ9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiJHZXRQb3N0Z3Jlc0Z1bmN0aW9uczptYXhfdGltZXN0YW1wIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6dHJ1ZSwidHlwZSI6IkRhdGVUaW1lIn19LHsiY29sdW1uIjoiR2V0UG9zdGdyZXNTcGVjaWFsVHlwZXNDbnQ6Y19qc29uIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJKc29uRWxlbWVudCJ9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzU3BlY2lhbFR5cGVzQ250OmNfanNvbmIiLCJjc2hhcnBfdHlwZSI6eyJub3ROdWxsIjpmYWxzZSwidHlwZSI6Ikpzb25FbGVtZW50In19LHsiY29sdW1uIjoiKjpjX2pzb25fc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiIqOmNfeG1sX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiKjpjX21hY2FkZHI4IiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiIqOmNfdGltZXN0YW1wX25vZGFfaW5zdGFudF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoiSW5zdGFudCJ9fV0sInRhcmdldEZyYW1ld29yayI6Im5ldHN0YW5kYXJkMi4wIiwidXNlRGFwcGVyIjp0cnVlfQ==", "process": { "cmd": "./dist/LocalRunner" } @@ -349,6 +349,17 @@ "schema": "pg_catalog", "name": "interval" } + }, + { + "name": "c_timestamp_noda_instant_override", + "length": -1, + "table": { + "name": "postgres_datetime_types" + }, + "type": { + "schema": "pg_catalog", + "name": "timestamp" + } } ] }, @@ -34495,7 +34506,7 @@ "filename": "query.sql" }, { - "text": "\nINSERT INTO postgres_datetime_types\n(\n c_date,\n c_time,\n c_timestamp,\n c_timestamp_with_tz,\n c_interval\n) VALUES ($1, $2, $3, $4, $5)", + "text": "\nINSERT INTO postgres_datetime_types\n(\n c_date,\n c_time,\n c_timestamp,\n c_timestamp_with_tz,\n c_interval,\n c_timestamp_noda_instant_override\n) VALUES ($1, $2, $3, $4, $5, $6)", "name": "InsertPostgresDateTimeTypes", "cmd": ":exec", "parameters": [ @@ -34573,6 +34584,21 @@ }, "originalName": "c_interval" } + }, + { + "number": 6, + "column": { + "name": "c_timestamp_noda_instant_override", + "length": -1, + "table": { + "schema": "public", + "name": "postgres_datetime_types" + }, + "type": { + "name": "pg_catalog.timestamp" + }, + "originalName": "c_timestamp_noda_instant_override" + } } ], "comments": [ @@ -34584,7 +34610,7 @@ } }, { - "text": "SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval FROM postgres_datetime_types LIMIT 1", + "text": "SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override FROM postgres_datetime_types LIMIT 1", "name": "GetPostgresDateTimeTypes", "cmd": ":one", "columns": [ @@ -34646,6 +34672,18 @@ "name": "interval" }, "originalName": "c_interval" + }, + { + "name": "c_timestamp_noda_instant_override", + "length": -1, + "table": { + "name": "postgres_datetime_types" + }, + "type": { + "schema": "pg_catalog", + "name": "timestamp" + }, + "originalName": "c_timestamp_noda_instant_override" } ], "filename": "query.sql" @@ -36194,5 +36232,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiTnBnc3FsRGFwcGVyTGVnYWN5RXhhbXBsZUdlbiIsInVzZURhcHBlciI6dHJ1ZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRQb3N0Z3Jlc0Z1bmN0aW9uczptYXhfaW50ZWdlciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJpbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0UG9zdGdyZXNGdW5jdGlvbnM6bWF4X3ZhcmNoYXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzRnVuY3Rpb25zOm1heF90aW1lc3RhbXAiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjp0cnVlfX0seyJjb2x1bW4iOiJHZXRQb3N0Z3Jlc1NwZWNpYWxUeXBlc0NudDpjX2pzb24iLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSnNvbkVsZW1lbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0UG9zdGdyZXNTcGVjaWFsVHlwZXNDbnQ6Y19qc29uYiIsImNzaGFycF90eXBlIjp7InR5cGUiOiJKc29uRWxlbWVudCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfanNvbl9zdHJpbmdfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y194bWxfc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfbWFjYWRkcjgiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fV0sImRlYnVnUmVxdWVzdCI6ZmFsc2V9" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiTnBnc3FsRGFwcGVyTGVnYWN5RXhhbXBsZUdlbiIsInVzZURhcHBlciI6dHJ1ZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwidXNlTm9kYVRpbWUiOmZhbHNlLCJvdmVycmlkZXMiOlt7ImNvbHVtbiI6IkdldFBvc3RncmVzRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRQb3N0Z3Jlc0Z1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0UG9zdGdyZXNGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOnRydWV9fSx7ImNvbHVtbiI6IkdldFBvc3RncmVzU3BlY2lhbFR5cGVzQ250OmNfanNvbiIsImNzaGFycF90eXBlIjp7InR5cGUiOiJKc29uRWxlbWVudCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRQb3N0Z3Jlc1NwZWNpYWxUeXBlc0NudDpjX2pzb25iIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6Ikpzb25FbGVtZW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3htbF9zdHJpbmdfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19tYWNhZGRyOCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RpbWVzdGFtcF9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSW5zdGFudCIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" } \ No newline at end of file diff --git a/examples/NpgsqlDapperLegacyExample/request.message b/examples/NpgsqlDapperLegacyExample/request.message index 39b9ff61..3fa46318 100644 --- a/examples/NpgsqlDapperLegacyExample/request.message +++ b/examples/NpgsqlDapperLegacyExample/request.message @@ -1,9 +1,9 @@ - + 2 -postgresql-examples/config/postgresql/authors/schema.sql+examples/config/postgresql/types/schema.sql",examples/config/postgresql/authors/query.sql"*examples/config/postgresql/types/query.sqlb -"examples/NpgsqlDapperLegacyExamplecsharp{"debugRequest":true,"generateCsproj":true,"namespaceName":"NpgsqlDapperLegacyExampleGen","overrides":[{"column":"GetPostgresFunctions:max_integer","csharp_type":{"notNull":false,"type":"int"}},{"column":"GetPostgresFunctions:max_varchar","csharp_type":{"notNull":false,"type":"string"}},{"column":"GetPostgresFunctions:max_timestamp","csharp_type":{"notNull":true,"type":"DateTime"}},{"column":"GetPostgresSpecialTypesCnt:c_json","csharp_type":{"notNull":false,"type":"JsonElement"}},{"column":"GetPostgresSpecialTypesCnt:c_jsonb","csharp_type":{"notNull":false,"type":"JsonElement"}},{"column":"*:c_json_string_override","csharp_type":{"notNull":false,"type":"string"}},{"column":"*:c_xml_string_override","csharp_type":{"notNull":false,"type":"string"}},{"column":"*:c_macaddr8","csharp_type":{"notNull":false,"type":"string"}}],"targetFramework":"netstandard2.0","useDapper":true}* -./dist/LocalRunner public"public +postgresql-examples/config/postgresql/authors/schema.sql+examples/config/postgresql/types/schema.sql",examples/config/postgresql/authors/query.sql"*examples/config/postgresql/types/query.sqlb +"examples/NpgsqlDapperLegacyExamplecsharp{"debugRequest":true,"generateCsproj":true,"namespaceName":"NpgsqlDapperLegacyExampleGen","overrides":[{"column":"GetPostgresFunctions:max_integer","csharp_type":{"notNull":false,"type":"int"}},{"column":"GetPostgresFunctions:max_varchar","csharp_type":{"notNull":false,"type":"string"}},{"column":"GetPostgresFunctions:max_timestamp","csharp_type":{"notNull":true,"type":"DateTime"}},{"column":"GetPostgresSpecialTypesCnt:c_json","csharp_type":{"notNull":false,"type":"JsonElement"}},{"column":"GetPostgresSpecialTypesCnt:c_jsonb","csharp_type":{"notNull":false,"type":"JsonElement"}},{"column":"*:c_json_string_override","csharp_type":{"notNull":false,"type":"string"}},{"column":"*:c_xml_string_override","csharp_type":{"notNull":false,"type":"string"}},{"column":"*:c_macaddr8","csharp_type":{"notNull":false,"type":"string"}},{"column":"*:c_timestamp_noda_instant_override","csharp_type":{"notNull":false,"type":"Instant"}}],"targetFramework":"netstandard2.0","useDapper":true}* +./dist/LocalRunner public"public authors) id0R authorsb  bigserial& name0R authorsbtext# @@ -43,7 +43,7 @@ pg_catalogvarcharP c_character_varying0Rpostgres_string_typesb pg_catalogvarchar8 c_bpchar0Rpostgres_string_typesbbpchar4 -c_text0Rpostgres_string_typesbtext +c_text0Rpostgres_string_typesbtext postgres_datetime_types6 c_date0Rpostgres_datetime_typesbdateB c_time0Rpostgres_datetime_typesb @@ -54,7 +54,9 @@ pg_catalog timestampV pg_catalog timestamptzJ c_interval0Rpostgres_datetime_typesb -pg_cataloginterval +pg_catalogintervalb +!c_timestamp_noda_instant_override0Rpostgres_datetime_typesb +pg_catalog timestamp postgres_network_types5 c_cidr0Rpostgres_network_typesbcidr5 c_inet0Rpostgres_network_typesbinet; @@ -10547,24 +10549,26 @@ LIMIT 1 GetPostgresStringTypesTextSearch:one"0 tsvectorztsv" rnk0@breal*%! -to_tsquery0btext: query.sql - +to_tsquery0btext: query.sql + INSERT INTO postgres_datetime_types ( c_date, c_time, c_timestamp, c_timestamp_with_tz, - c_interval -) VALUES ($1, $2, $3, $4, $5)InsertPostgresDateTimeTypes:exec*JF + c_interval, + c_timestamp_noda_instant_override +) VALUES ($1, $2, $3, $4, $5, $6)InsertPostgresDateTimeTypes:exec*JF c_date0R!publicpostgres_datetime_typesbdatezc_date*UQ c_time0R!publicpostgres_datetime_typesbpg_catalog.timezc_time*d` c_timestamp0R!publicpostgres_datetime_typesbpg_catalog.timestampz c_timestamp*vr c_timestamp_with_tz0R!publicpostgres_datetime_typesbpg_catalog.timestamptzzc_timestamp_with_tz*a] c_interval0R!publicpostgres_datetime_typesbpg_catalog.intervalz -c_interval2 DateTime types : query.sqlBpostgres_datetime_types -hSELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval FROM postgres_datetime_types LIMIT 1GetPostgresDateTimeTypes:one"> +c_interval* +!c_timestamp_noda_instant_override0R!publicpostgres_datetime_typesbpg_catalog.timestampz!c_timestamp_noda_instant_override2 DateTime types : query.sqlBpostgres_datetime_types +SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override FROM postgres_datetime_types LIMIT 1GetPostgresDateTimeTypes:one"> c_date0Rpostgres_datetime_typesbdatezc_date"J c_time0Rpostgres_datetime_typesb pg_catalogtimezc_time"Y @@ -10575,7 +10579,9 @@ pg_catalog timestamptzzc_timestamp_with_tz"V c_interval0Rpostgres_datetime_typesb pg_catalogintervalz -c_interval: query.sqlY +c_interval" +!c_timestamp_noda_instant_override0Rpostgres_datetime_typesb +pg_catalog timestampz!c_timestamp_noda_instant_override: query.sqlY &TRUNCATE TABLE postgres_datetime_typesTruncatePostgresDateTimeTypes:exec: query.sql SELECT c_date, @@ -10911,4 +10917,4 @@ hSELECT c_point, c_line, c_lseg, c_box, c_path, c_polygon, c_circle FROM postgre c_path0Rpostgres_geometric_typesbpathzc_path"H c_polygon0Rpostgres_geometric_typesb polygonz c_polygon"E c_circle0Rpostgres_geometric_typesbcirclezc_circle: query.sqlU -'TRUNCATE TABLE postgres_geometric_typesTruncatePostgresGeoTypes:exec: query.sql"v1.30.0*{"overrideDriverVersion":"","generateCsproj":true,"targetFramework":"netstandard2.0","namespaceName":"NpgsqlDapperLegacyExampleGen","useDapper":true,"overrideDapperVersion":"","overrides":[{"column":"GetPostgresFunctions:max_integer","csharp_type":{"type":"int","notNull":false}},{"column":"GetPostgresFunctions:max_varchar","csharp_type":{"type":"string","notNull":false}},{"column":"GetPostgresFunctions:max_timestamp","csharp_type":{"type":"DateTime","notNull":true}},{"column":"GetPostgresSpecialTypesCnt:c_json","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"GetPostgresSpecialTypesCnt:c_jsonb","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"*:c_json_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_xml_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_macaddr8","csharp_type":{"type":"string","notNull":false}}],"debugRequest":false} \ No newline at end of file +'TRUNCATE TABLE postgres_geometric_typesTruncatePostgresGeoTypes:exec: query.sql"v1.30.0*{"overrideDriverVersion":"","generateCsproj":true,"targetFramework":"netstandard2.0","namespaceName":"NpgsqlDapperLegacyExampleGen","useDapper":true,"overrideDapperVersion":"","useNodaTime":false,"overrides":[{"column":"GetPostgresFunctions:max_integer","csharp_type":{"type":"int","notNull":false}},{"column":"GetPostgresFunctions:max_varchar","csharp_type":{"type":"string","notNull":false}},{"column":"GetPostgresFunctions:max_timestamp","csharp_type":{"type":"DateTime","notNull":true}},{"column":"GetPostgresSpecialTypesCnt:c_json","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"GetPostgresSpecialTypesCnt:c_jsonb","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"*:c_json_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_xml_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_macaddr8","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_timestamp_noda_instant_override","csharp_type":{"type":"Instant","notNull":false}}],"debugRequest":false} \ No newline at end of file diff --git a/examples/NpgsqlExample/Models.cs b/examples/NpgsqlExample/Models.cs index ed9abc3d..966152d7 100644 --- a/examples/NpgsqlExample/Models.cs +++ b/examples/NpgsqlExample/Models.cs @@ -1,4 +1,6 @@ // auto-generated by sqlc - do not edit +using NodaTime; +using NodaTime.Extensions; using NpgsqlTypes; using System; using System.Collections.Generic; @@ -13,7 +15,7 @@ namespace NpgsqlExampleGen; public readonly record struct Book(Guid Id, string Name, long AuthorId, string? Description); public readonly record struct PostgresNumericType(bool? CBoolean, byte[]? CBit, short? CSmallint, int? CInteger, long? CBigint, decimal? CDecimal, decimal? CNumeric, float? CReal, double? CDoublePrecision, decimal? CMoney); public readonly record struct PostgresStringType(string? CChar, string? CVarchar, string? CCharacterVarying, string? CBpchar, string? CText); -public readonly record struct PostgresDatetimeType(DateTime? CDate, TimeSpan? CTime, DateTime? CTimestamp, DateTime? CTimestampWithTz, TimeSpan? CInterval); +public readonly record struct PostgresDatetimeType(DateTime? CDate, TimeSpan? CTime, DateTime? CTimestamp, DateTime? CTimestampWithTz, TimeSpan? CInterval, DateTime? CTimestampNodaInstantOverride); public readonly record struct PostgresNetworkType(NpgsqlCidr? CCidr, IPAddress? CInet, PhysicalAddress? CMacaddr, string? CMacaddr8); public readonly record struct PostgresArrayType(byte[]? CBytea, bool[]? CBooleanArray, string[]? CTextArray, int[]? CIntegerArray, decimal[]? CDecimalArray, DateTime[]? CDateArray, DateTime[]? CTimestampArray); public readonly record struct PostgresGeometricType(NpgsqlPoint? CPoint, NpgsqlLine? CLine, NpgsqlLSeg? CLseg, NpgsqlBox? CBox, NpgsqlPath? CPath, NpgsqlPolygon? CPolygon, NpgsqlCircle? CCircle); diff --git a/examples/NpgsqlExample/NpgsqlExample.csproj b/examples/NpgsqlExample/NpgsqlExample.csproj index d076798b..15672fca 100644 --- a/examples/NpgsqlExample/NpgsqlExample.csproj +++ b/examples/NpgsqlExample/NpgsqlExample.csproj @@ -13,6 +13,7 @@ + \ No newline at end of file diff --git a/examples/NpgsqlExample/QuerySql.cs b/examples/NpgsqlExample/QuerySql.cs index fb06f2aa..dcdb008c 100644 --- a/examples/NpgsqlExample/QuerySql.cs +++ b/examples/NpgsqlExample/QuerySql.cs @@ -4,6 +4,8 @@ // ReSharper disable ConvertToUsingDeclaration // ReSharper disable NotAccessedPositionalProperty.Global // ReSharper disable UnusedAutoPropertyAccessor.Global +using NodaTime; +using NodaTime.Extensions; using Npgsql; using NpgsqlTypes; using System; @@ -813,7 +815,7 @@ public async Task InsertPostgresNumericTypes(InsertPostgresNumericTypesArgs args command.Parameters.AddWithValue("@c_numeric", args.CNumeric ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_real", args.CReal ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_double_precision", args.CDoublePrecision ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_money", args.CMoney ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_money", NpgsqlDbType.Money, args.CMoney ?? (object)DBNull.Value); await command.ExecuteNonQueryAsync(); } } @@ -836,7 +838,7 @@ public async Task InsertPostgresNumericTypes(InsertPostgresNumericTypesArgs args command.Parameters.AddWithValue("@c_numeric", args.CNumeric ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_real", args.CReal ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_double_precision", args.CDoublePrecision ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_money", args.CMoney ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_money", NpgsqlDbType.Money, args.CMoney ?? (object)DBNull.Value); await command.ExecuteNonQueryAsync(); } } @@ -1287,8 +1289,8 @@ public async Task TruncatePostgresStringTypes() return null; } - private const string InsertPostgresDateTimeTypesSql = " INSERT INTO postgres_datetime_types ( c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval ) VALUES (@c_date, @c_time, @c_timestamp, @c_timestamp_with_tz, @c_interval)"; - public readonly record struct InsertPostgresDateTimeTypesArgs(DateTime? CDate, TimeSpan? CTime, DateTime? CTimestamp, DateTime? CTimestampWithTz, TimeSpan? CInterval); + private const string InsertPostgresDateTimeTypesSql = " INSERT INTO postgres_datetime_types ( c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override ) VALUES (@c_date, @c_time, @c_timestamp, @c_timestamp_with_tz, @c_interval, @c_timestamp_noda_instant_override)"; + public readonly record struct InsertPostgresDateTimeTypesArgs(DateTime? CDate, TimeSpan? CTime, DateTime? CTimestamp, DateTime? CTimestampWithTz, TimeSpan? CInterval, Instant? CTimestampNodaInstantOverride); public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs args) { if (this.Transaction == null) @@ -1297,11 +1299,12 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar { using (var command = connection.CreateCommand(InsertPostgresDateTimeTypesSql)) { - command.Parameters.AddWithValue("@c_date", args.CDate ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_time", args.CTime ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_timestamp", args.CTimestamp ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_timestamp_with_tz", args.CTimestampWithTz ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_interval", args.CInterval ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_date", NpgsqlDbType.Date, args.CDate ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_time", NpgsqlDbType.Time, args.CTime ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp", NpgsqlDbType.Timestamp, args.CTimestamp ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_with_tz", NpgsqlDbType.TimestampTz, args.CTimestampWithTz ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_interval", NpgsqlDbType.Interval, args.CInterval ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", NpgsqlDbType.Timestamp, args.CTimestampNodaInstantOverride?.ToDateTimeUtc().ToLocalTime() ?? (object)DBNull.Value); await command.ExecuteNonQueryAsync(); } } @@ -1315,17 +1318,18 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar { command.CommandText = InsertPostgresDateTimeTypesSql; command.Transaction = this.Transaction; - command.Parameters.AddWithValue("@c_date", args.CDate ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_time", args.CTime ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_timestamp", args.CTimestamp ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_timestamp_with_tz", args.CTimestampWithTz ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_interval", args.CInterval ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_date", NpgsqlDbType.Date, args.CDate ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_time", NpgsqlDbType.Time, args.CTime ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp", NpgsqlDbType.Timestamp, args.CTimestamp ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_with_tz", NpgsqlDbType.TimestampTz, args.CTimestampWithTz ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_interval", NpgsqlDbType.Interval, args.CInterval ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", NpgsqlDbType.Timestamp, args.CTimestampNodaInstantOverride?.ToDateTimeUtc().ToLocalTime() ?? (object)DBNull.Value); await command.ExecuteNonQueryAsync(); } } - private const string GetPostgresDateTimeTypesSql = "SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval FROM postgres_datetime_types LIMIT 1"; - public readonly record struct GetPostgresDateTimeTypesRow(DateTime? CDate, TimeSpan? CTime, DateTime? CTimestamp, DateTime? CTimestampWithTz, TimeSpan? CInterval); + private const string GetPostgresDateTimeTypesSql = "SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override FROM postgres_datetime_types LIMIT 1"; + public readonly record struct GetPostgresDateTimeTypesRow(DateTime? CDate, TimeSpan? CTime, DateTime? CTimestamp, DateTime? CTimestampWithTz, TimeSpan? CInterval, Instant? CTimestampNodaInstantOverride); public async Task GetPostgresDateTimeTypes() { if (this.Transaction == null) @@ -1344,7 +1348,8 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar CTime = reader.IsDBNull(1) ? null : reader.GetFieldValue(1), CTimestamp = reader.IsDBNull(2) ? null : reader.GetDateTime(2), CTimestampWithTz = reader.IsDBNull(3) ? null : reader.GetDateTime(3), - CInterval = reader.IsDBNull(4) ? null : reader.GetFieldValue(4) + CInterval = reader.IsDBNull(4) ? null : reader.GetFieldValue(4), + CTimestampNodaInstantOverride = reader.IsDBNull(5) ? null : reader.GetDateTime(5).ToInstant() }; } } @@ -1370,7 +1375,8 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar CTime = reader.IsDBNull(1) ? null : reader.GetFieldValue(1), CTimestamp = reader.IsDBNull(2) ? null : reader.GetDateTime(2), CTimestampWithTz = reader.IsDBNull(3) ? null : reader.GetDateTime(3), - CInterval = reader.IsDBNull(4) ? null : reader.GetFieldValue(4) + CInterval = reader.IsDBNull(4) ? null : reader.GetFieldValue(4), + CTimestampNodaInstantOverride = reader.IsDBNull(5) ? null : reader.GetDateTime(5).ToInstant() }; } } @@ -1476,8 +1482,8 @@ public async Task InsertPostgresDateTimeTypesBatch(List +c_interval* +!c_timestamp_noda_instant_override0R!publicpostgres_datetime_typesbpg_catalog.timestampz!c_timestamp_noda_instant_override2 DateTime types : query.sqlBpostgres_datetime_types +SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override FROM postgres_datetime_types LIMIT 1GetPostgresDateTimeTypes:one"> c_date0Rpostgres_datetime_typesbdatezc_date"J c_time0Rpostgres_datetime_typesb pg_catalogtimezc_time"Y @@ -10575,7 +10579,9 @@ pg_catalog timestamptzzc_timestamp_with_tz"V c_interval0Rpostgres_datetime_typesb pg_catalogintervalz -c_interval: query.sqlY +c_interval" +!c_timestamp_noda_instant_override0Rpostgres_datetime_typesb +pg_catalog timestampz!c_timestamp_noda_instant_override: query.sqlY &TRUNCATE TABLE postgres_datetime_typesTruncatePostgresDateTimeTypes:exec: query.sql SELECT c_date, @@ -10911,4 +10917,4 @@ hSELECT c_point, c_line, c_lseg, c_box, c_path, c_polygon, c_circle FROM postgre c_path0Rpostgres_geometric_typesbpathzc_path"H c_polygon0Rpostgres_geometric_typesb polygonz c_polygon"E c_circle0Rpostgres_geometric_typesbcirclezc_circle: query.sqlU -'TRUNCATE TABLE postgres_geometric_typesTruncatePostgresGeoTypes:exec: query.sql"v1.30.0*{"overrideDriverVersion":"","generateCsproj":true,"targetFramework":"net8.0","namespaceName":"NpgsqlExampleGen","useDapper":false,"overrideDapperVersion":"","overrides":[{"column":"GetPostgresFunctions:max_integer","csharp_type":{"type":"int","notNull":false}},{"column":"GetPostgresFunctions:max_varchar","csharp_type":{"type":"string","notNull":false}},{"column":"GetPostgresFunctions:max_timestamp","csharp_type":{"type":"DateTime","notNull":true}},{"column":"GetPostgresSpecialTypesCnt:c_json","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"GetPostgresSpecialTypesCnt:c_jsonb","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"*:c_json_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_xml_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_macaddr8","csharp_type":{"type":"string","notNull":false}}],"debugRequest":false} \ No newline at end of file +'TRUNCATE TABLE postgres_geometric_typesTruncatePostgresGeoTypes:exec: query.sql"v1.30.0*{"overrideDriverVersion":"","generateCsproj":true,"targetFramework":"net8.0","namespaceName":"NpgsqlExampleGen","useDapper":false,"overrideDapperVersion":"","useNodaTime":false,"overrides":[{"column":"GetPostgresFunctions:max_integer","csharp_type":{"type":"int","notNull":false}},{"column":"GetPostgresFunctions:max_varchar","csharp_type":{"type":"string","notNull":false}},{"column":"GetPostgresFunctions:max_timestamp","csharp_type":{"type":"DateTime","notNull":true}},{"column":"GetPostgresSpecialTypesCnt:c_json","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"GetPostgresSpecialTypesCnt:c_jsonb","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"*:c_json_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_xml_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_macaddr8","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_timestamp_noda_instant_override","csharp_type":{"type":"Instant","notNull":false}}],"debugRequest":false} \ No newline at end of file diff --git a/examples/NpgsqlLegacyExample/Models.cs b/examples/NpgsqlLegacyExample/Models.cs index 8cac7f32..67d27bf2 100644 --- a/examples/NpgsqlLegacyExample/Models.cs +++ b/examples/NpgsqlLegacyExample/Models.cs @@ -1,6 +1,8 @@ // auto-generated by sqlc - do not edit namespace NpgsqlLegacyExampleGen { + using NodaTime; + using NodaTime.Extensions; using NpgsqlTypes; using System; using System.Collections.Generic; @@ -51,6 +53,7 @@ public class PostgresDatetimeType public DateTime? CTimestamp { get; set; } public DateTime? CTimestampWithTz { get; set; } public TimeSpan? CInterval { get; set; } + public DateTime? CTimestampNodaInstantOverride { get; set; } }; public class PostgresNetworkType { diff --git a/examples/NpgsqlLegacyExample/NpgsqlLegacyExample.csproj b/examples/NpgsqlLegacyExample/NpgsqlLegacyExample.csproj index f9d987d4..2c245f84 100644 --- a/examples/NpgsqlLegacyExample/NpgsqlLegacyExample.csproj +++ b/examples/NpgsqlLegacyExample/NpgsqlLegacyExample.csproj @@ -13,6 +13,7 @@ + \ No newline at end of file diff --git a/examples/NpgsqlLegacyExample/QuerySql.cs b/examples/NpgsqlLegacyExample/QuerySql.cs index aaa0c4af..3582bfaa 100644 --- a/examples/NpgsqlLegacyExample/QuerySql.cs +++ b/examples/NpgsqlLegacyExample/QuerySql.cs @@ -6,6 +6,8 @@ // ReSharper disable UnusedAutoPropertyAccessor.Global namespace NpgsqlLegacyExampleGen { + using NodaTime; + using NodaTime.Extensions; using Npgsql; using NpgsqlTypes; using System; @@ -941,7 +943,7 @@ public async Task InsertPostgresNumericTypes(InsertPostgresNumericTypesArgs args command.Parameters.AddWithValue("@c_numeric", args.CNumeric ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_real", args.CReal ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_double_precision", args.CDoublePrecision ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_money", args.CMoney ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_money", NpgsqlDbType.Money, args.CMoney ?? (object)DBNull.Value); await command.ExecuteNonQueryAsync(); } } @@ -964,7 +966,7 @@ public async Task InsertPostgresNumericTypes(InsertPostgresNumericTypesArgs args command.Parameters.AddWithValue("@c_numeric", args.CNumeric ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_real", args.CReal ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_double_precision", args.CDoublePrecision ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_money", args.CMoney ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_money", NpgsqlDbType.Money, args.CMoney ?? (object)DBNull.Value); await command.ExecuteNonQueryAsync(); } } @@ -1490,7 +1492,7 @@ public async Task GetPostgresStringTypesTex return null; } - private const string InsertPostgresDateTimeTypesSql = " INSERT INTO postgres_datetime_types ( c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval ) VALUES (@c_date, @c_time, @c_timestamp, @c_timestamp_with_tz, @c_interval)"; + private const string InsertPostgresDateTimeTypesSql = " INSERT INTO postgres_datetime_types ( c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override ) VALUES (@c_date, @c_time, @c_timestamp, @c_timestamp_with_tz, @c_interval, @c_timestamp_noda_instant_override)"; public class InsertPostgresDateTimeTypesArgs { public DateTime? CDate { get; set; } @@ -1498,6 +1500,7 @@ public class InsertPostgresDateTimeTypesArgs public DateTime? CTimestamp { get; set; } public DateTime? CTimestampWithTz { get; set; } public TimeSpan? CInterval { get; set; } + public Instant? CTimestampNodaInstantOverride { get; set; } }; public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs args) { @@ -1507,11 +1510,12 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar { using (var command = connection.CreateCommand(InsertPostgresDateTimeTypesSql)) { - command.Parameters.AddWithValue("@c_date", args.CDate ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_time", args.CTime ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_timestamp", args.CTimestamp ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_timestamp_with_tz", args.CTimestampWithTz ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_interval", args.CInterval ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_date", NpgsqlDbType.Date, args.CDate ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_time", NpgsqlDbType.Time, args.CTime ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp", NpgsqlDbType.Timestamp, args.CTimestamp ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_with_tz", NpgsqlDbType.TimestampTz, args.CTimestampWithTz ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_interval", NpgsqlDbType.Interval, args.CInterval ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", NpgsqlDbType.Timestamp, args.CTimestampNodaInstantOverride?.ToDateTimeUtc().ToLocalTime() ?? (object)DBNull.Value); await command.ExecuteNonQueryAsync(); } } @@ -1525,16 +1529,17 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar { command.CommandText = InsertPostgresDateTimeTypesSql; command.Transaction = this.Transaction; - command.Parameters.AddWithValue("@c_date", args.CDate ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_time", args.CTime ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_timestamp", args.CTimestamp ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_timestamp_with_tz", args.CTimestampWithTz ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_interval", args.CInterval ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_date", NpgsqlDbType.Date, args.CDate ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_time", NpgsqlDbType.Time, args.CTime ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp", NpgsqlDbType.Timestamp, args.CTimestamp ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_with_tz", NpgsqlDbType.TimestampTz, args.CTimestampWithTz ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_interval", NpgsqlDbType.Interval, args.CInterval ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", NpgsqlDbType.Timestamp, args.CTimestampNodaInstantOverride?.ToDateTimeUtc().ToLocalTime() ?? (object)DBNull.Value); await command.ExecuteNonQueryAsync(); } } - private const string GetPostgresDateTimeTypesSql = "SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval FROM postgres_datetime_types LIMIT 1"; + private const string GetPostgresDateTimeTypesSql = "SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override FROM postgres_datetime_types LIMIT 1"; public class GetPostgresDateTimeTypesRow { public DateTime? CDate { get; set; } @@ -1542,6 +1547,7 @@ public class GetPostgresDateTimeTypesRow public DateTime? CTimestamp { get; set; } public DateTime? CTimestampWithTz { get; set; } public TimeSpan? CInterval { get; set; } + public Instant? CTimestampNodaInstantOverride { get; set; } }; public async Task GetPostgresDateTimeTypes() { @@ -1561,7 +1567,8 @@ public async Task GetPostgresDateTimeTypes() CTime = reader.IsDBNull(1) ? (TimeSpan? )null : reader.GetFieldValue(1), CTimestamp = reader.IsDBNull(2) ? (DateTime? )null : reader.GetDateTime(2), CTimestampWithTz = reader.IsDBNull(3) ? (DateTime? )null : reader.GetDateTime(3), - CInterval = reader.IsDBNull(4) ? (TimeSpan? )null : reader.GetFieldValue(4) + CInterval = reader.IsDBNull(4) ? (TimeSpan? )null : reader.GetFieldValue(4), + CTimestampNodaInstantOverride = reader.IsDBNull(5) ? (Instant? )null : reader.GetDateTime(5).ToInstant() }; } } @@ -1587,7 +1594,8 @@ public async Task GetPostgresDateTimeTypes() CTime = reader.IsDBNull(1) ? (TimeSpan? )null : reader.GetFieldValue(1), CTimestamp = reader.IsDBNull(2) ? (DateTime? )null : reader.GetDateTime(2), CTimestampWithTz = reader.IsDBNull(3) ? (DateTime? )null : reader.GetDateTime(3), - CInterval = reader.IsDBNull(4) ? (TimeSpan? )null : reader.GetFieldValue(4) + CInterval = reader.IsDBNull(4) ? (TimeSpan? )null : reader.GetFieldValue(4), + CTimestampNodaInstantOverride = reader.IsDBNull(5) ? (Instant? )null : reader.GetDateTime(5).ToInstant() }; } } @@ -1708,8 +1716,8 @@ public async Task InsertPostgresDateTimeTypesBatch(List +c_interval* +!c_timestamp_noda_instant_override0R!publicpostgres_datetime_typesbpg_catalog.timestampz!c_timestamp_noda_instant_override2 DateTime types : query.sqlBpostgres_datetime_types +SELECT c_date, c_time, c_timestamp, c_timestamp_with_tz, c_interval, c_timestamp_noda_instant_override FROM postgres_datetime_types LIMIT 1GetPostgresDateTimeTypes:one"> c_date0Rpostgres_datetime_typesbdatezc_date"J c_time0Rpostgres_datetime_typesb pg_catalogtimezc_time"Y @@ -10575,7 +10579,9 @@ pg_catalog timestamptzzc_timestamp_with_tz"V c_interval0Rpostgres_datetime_typesb pg_catalogintervalz -c_interval: query.sqlY +c_interval" +!c_timestamp_noda_instant_override0Rpostgres_datetime_typesb +pg_catalog timestampz!c_timestamp_noda_instant_override: query.sqlY &TRUNCATE TABLE postgres_datetime_typesTruncatePostgresDateTimeTypes:exec: query.sql SELECT c_date, @@ -10911,4 +10917,4 @@ hSELECT c_point, c_line, c_lseg, c_box, c_path, c_polygon, c_circle FROM postgre c_path0Rpostgres_geometric_typesbpathzc_path"H c_polygon0Rpostgres_geometric_typesb polygonz c_polygon"E c_circle0Rpostgres_geometric_typesbcirclezc_circle: query.sqlU -'TRUNCATE TABLE postgres_geometric_typesTruncatePostgresGeoTypes:exec: query.sql"v1.30.0*{"overrideDriverVersion":"","generateCsproj":true,"targetFramework":"netstandard2.0","namespaceName":"NpgsqlLegacyExampleGen","useDapper":false,"overrideDapperVersion":"","overrides":[{"column":"GetPostgresFunctions:max_integer","csharp_type":{"type":"int","notNull":false}},{"column":"GetPostgresFunctions:max_varchar","csharp_type":{"type":"string","notNull":false}},{"column":"GetPostgresFunctions:max_timestamp","csharp_type":{"type":"DateTime","notNull":true}},{"column":"GetPostgresSpecialTypesCnt:c_json","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"GetPostgresSpecialTypesCnt:c_jsonb","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"*:c_json_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_xml_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_macaddr8","csharp_type":{"type":"string","notNull":false}}],"debugRequest":false} \ No newline at end of file +'TRUNCATE TABLE postgres_geometric_typesTruncatePostgresGeoTypes:exec: query.sql"v1.30.0*{"overrideDriverVersion":"","generateCsproj":true,"targetFramework":"netstandard2.0","namespaceName":"NpgsqlLegacyExampleGen","useDapper":false,"overrideDapperVersion":"","useNodaTime":false,"overrides":[{"column":"GetPostgresFunctions:max_integer","csharp_type":{"type":"int","notNull":false}},{"column":"GetPostgresFunctions:max_varchar","csharp_type":{"type":"string","notNull":false}},{"column":"GetPostgresFunctions:max_timestamp","csharp_type":{"type":"DateTime","notNull":true}},{"column":"GetPostgresSpecialTypesCnt:c_json","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"GetPostgresSpecialTypesCnt:c_jsonb","csharp_type":{"type":"JsonElement","notNull":false}},{"column":"*:c_json_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_xml_string_override","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_macaddr8","csharp_type":{"type":"string","notNull":false}},{"column":"*:c_timestamp_noda_instant_override","csharp_type":{"type":"Instant","notNull":false}}],"debugRequest":false} \ No newline at end of file diff --git a/examples/SqliteDapperExample/SqliteDapperExample.csproj b/examples/SqliteDapperExample/SqliteDapperExample.csproj index e8a48730..4eab67c4 100644 --- a/examples/SqliteDapperExample/SqliteDapperExample.csproj +++ b/examples/SqliteDapperExample/SqliteDapperExample.csproj @@ -14,6 +14,7 @@ + \ No newline at end of file diff --git a/examples/SqliteDapperExample/request.json b/examples/SqliteDapperExample/request.json index 9980e088..6888e99c 100644 --- a/examples/SqliteDapperExample/request.json +++ b/examples/SqliteDapperExample/request.json @@ -1391,5 +1391,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6IlNxbGl0ZURhcHBlckV4YW1wbGVHZW4iLCJ1c2VEYXBwZXIiOnRydWUsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3ZhcmNoYXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfcmVhbCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJkZWNpbWFsIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2Jvb2xfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiYm9vbCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wiLCJub3ROdWxsIjpmYWxzZX19XSwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6IlNxbGl0ZURhcHBlckV4YW1wbGVHZW4iLCJ1c2VEYXBwZXIiOnRydWUsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsInVzZU5vZGFUaW1lIjpmYWxzZSwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X2ludGVnZXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9yZWFsIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImRlY2ltYWwiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfYm9vbF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJib29sIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX2Jvb2xfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiYm9vbCIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" } \ No newline at end of file diff --git a/examples/SqliteDapperExample/request.message b/examples/SqliteDapperExample/request.message index 86cf9998b4b260f32b07562dc2c36d38be6d9ea3..d58db710f13f22f030f25794aa91f94726b2e6bc 100644 GIT binary patch delta 37 tcmX@$bH!%^k22%2$-K%-gi4E3{qj>1Lo#zym8{YdbBa?puUDSP1OO6-4k-Wt delta 18 acmccObHHZ + \ No newline at end of file diff --git a/examples/SqliteDapperLegacyExample/request.json b/examples/SqliteDapperLegacyExample/request.json index 8bfc0f57..b0c34489 100644 --- a/examples/SqliteDapperLegacyExample/request.json +++ b/examples/SqliteDapperLegacyExample/request.json @@ -1391,5 +1391,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlRGFwcGVyTGVnYWN5RXhhbXBsZUdlbiIsInVzZURhcHBlciI6dHJ1ZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X2ludGVnZXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9yZWFsIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImRlY2ltYWwiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfYm9vbF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJib29sIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX2Jvb2xfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiYm9vbCIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlRGFwcGVyTGVnYWN5RXhhbXBsZUdlbiIsInVzZURhcHBlciI6dHJ1ZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwidXNlTm9kYVRpbWUiOmZhbHNlLCJvdmVycmlkZXMiOlt7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfaW50ZWdlciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJpbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3JlYWwiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiZGVjaW1hbCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfdGV4dF9kYXRldGltZV9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9kYXRldGltZV9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfYm9vbF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJib29sIiwibm90TnVsbCI6ZmFsc2V9fV0sImRlYnVnUmVxdWVzdCI6ZmFsc2V9" } \ No newline at end of file diff --git a/examples/SqliteDapperLegacyExample/request.message b/examples/SqliteDapperLegacyExample/request.message index 899015a257d8b205f58a8a24a394768c91029093..aefb4188f338a77aca3bfb2832ba4c3834bc059d 100644 GIT binary patch delta 37 tcmaFl^UY_2f->Wk$%@LGgi4E3{qj>1Lo#zym8{YdbBa?pUsRsR1OOy14$}Yt delta 22 ecmez7^T=m|f->WQ$%@LGCOa|)ZMIagWdZIftN diff --git a/examples/SqliteExample/SqliteExample.csproj b/examples/SqliteExample/SqliteExample.csproj index d31ba452..83965cb6 100644 --- a/examples/SqliteExample/SqliteExample.csproj +++ b/examples/SqliteExample/SqliteExample.csproj @@ -13,6 +13,7 @@ + \ No newline at end of file diff --git a/examples/SqliteExample/request.json b/examples/SqliteExample/request.json index 9471287a..d51d592c 100644 --- a/examples/SqliteExample/request.json +++ b/examples/SqliteExample/request.json @@ -1391,5 +1391,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6IlNxbGl0ZUV4YW1wbGVHZW4iLCJ1c2VEYXBwZXIiOmZhbHNlLCJvdmVycmlkZURhcHBlclZlcnNpb24iOiIiLCJvdmVycmlkZXMiOlt7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfaW50ZWdlciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJpbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3JlYWwiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiZGVjaW1hbCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfdGV4dF9kYXRldGltZV9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9kYXRldGltZV9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfYm9vbF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJib29sIiwibm90TnVsbCI6ZmFsc2V9fV0sImRlYnVnUmVxdWVzdCI6ZmFsc2V9" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6IlNxbGl0ZUV4YW1wbGVHZW4iLCJ1c2VEYXBwZXIiOmZhbHNlLCJvdmVycmlkZURhcHBlclZlcnNpb24iOiIiLCJ1c2VOb2RhVGltZSI6ZmFsc2UsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3ZhcmNoYXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfcmVhbCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJkZWNpbWFsIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2Jvb2xfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiYm9vbCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wiLCJub3ROdWxsIjpmYWxzZX19XSwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" } \ No newline at end of file diff --git a/examples/SqliteExample/request.message b/examples/SqliteExample/request.message index 344dee9b36c260d741d066e8f42606a2692d9bf2..b6bd22a58c24e4232458554f5824a1ad03982f45 100644 GIT binary patch delta 37 tcmdnsbHrx@qcY>c$xO=gg-VN4{qj>1Lo#zym8{YdbBa?p&sUzv1ON&z4cPzy delta 22 ecmX@&v%zNrqcY>#$xO=gCu=eWZDv=oWdZ + \ No newline at end of file diff --git a/examples/SqliteLegacyExample/request.json b/examples/SqliteLegacyExample/request.json index 9cbe112a..cb5b7429 100644 --- a/examples/SqliteLegacyExample/request.json +++ b/examples/SqliteLegacyExample/request.json @@ -1391,5 +1391,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlTGVnYWN5RXhhbXBsZUdlbiIsInVzZURhcHBlciI6ZmFsc2UsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3ZhcmNoYXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfcmVhbCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJkZWNpbWFsIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2Jvb2xfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiYm9vbCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wiLCJub3ROdWxsIjpmYWxzZX19XSwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlTGVnYWN5RXhhbXBsZUdlbiIsInVzZURhcHBlciI6ZmFsc2UsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsInVzZU5vZGFUaW1lIjpmYWxzZSwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X2ludGVnZXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9yZWFsIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImRlY2ltYWwiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfYm9vbF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJib29sIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX2Jvb2xfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiYm9vbCIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" } \ No newline at end of file diff --git a/examples/SqliteLegacyExample/request.message b/examples/SqliteLegacyExample/request.message index 1fc6e7318f64804e5cfc97b751f174d18da064e4..cb12db7c6ef36c301587bddd65fc4feed2cf6ba7 100644 GIT binary patch delta 37 tcmccQ^UP<1s50aE$zsZDg-VN4{qj>1Lo#zym8{YdbBa?pA5@;m1OOY?4ub#y delta 18 acmaFnbIE6es50a3$zsZDH(yuoX956C&Ihaj diff --git a/examples/config/postgresql/types/query.sql b/examples/config/postgresql/types/query.sql index 5f890076..0b482159 100644 --- a/examples/config/postgresql/types/query.sql +++ b/examples/config/postgresql/types/query.sql @@ -143,8 +143,9 @@ INSERT INTO postgres_datetime_types c_time, c_timestamp, c_timestamp_with_tz, - c_interval -) VALUES ($1, $2, $3, $4, $5); + c_interval, + c_timestamp_noda_instant_override +) VALUES ($1, $2, $3, $4, $5, $6); -- name: GetPostgresDateTimeTypes :one SELECT * FROM postgres_datetime_types LIMIT 1; diff --git a/examples/config/postgresql/types/schema.sql b/examples/config/postgresql/types/schema.sql index b35715c0..d5225b32 100644 --- a/examples/config/postgresql/types/schema.sql +++ b/examples/config/postgresql/types/schema.sql @@ -24,7 +24,8 @@ CREATE TABLE postgres_datetime_types ( c_time TIME, c_timestamp TIMESTAMP, c_timestamp_with_tz TIMESTAMP WITH TIME ZONE, - c_interval INTERVAL + c_interval INTERVAL, + c_timestamp_noda_instant_override TIMESTAMP ); CREATE TABLE postgres_network_types ( diff --git a/sqlc.ci.yaml b/sqlc.ci.yaml index fc81c317..2cf7643c 100644 --- a/sqlc.ci.yaml +++ b/sqlc.ci.yaml @@ -50,6 +50,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false - schema: ["examples/config/postgresql/authors/schema.sql", "examples/config/postgresql/types/schema.sql"] queries: ["examples/config/postgresql/authors/query.sql", "examples/config/postgresql/types/query.sql"] engine: "postgresql" @@ -94,6 +98,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false - schema: ["examples/config/postgresql/authors/schema.sql", "examples/config/postgresql/types/schema.sql"] queries: ["examples/config/postgresql/authors/query.sql", "examples/config/postgresql/types/query.sql"] engine: "postgresql" @@ -138,6 +146,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false - schema: ["examples/config/postgresql/authors/schema.sql", "examples/config/postgresql/types/schema.sql"] queries: ["examples/config/postgresql/authors/query.sql", "examples/config/postgresql/types/query.sql"] engine: "postgresql" @@ -182,6 +194,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false # MySQL - schema: ["examples/config/mysql/authors/schema.sql", "examples/config/mysql/types/schema.sql"] diff --git a/sqlc.local.generated.yaml b/sqlc.local.generated.yaml index 94603a55..0778288c 100644 --- a/sqlc.local.generated.yaml +++ b/sqlc.local.generated.yaml @@ -49,6 +49,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false - schema: ["examples/config/postgresql/authors/schema.sql", "examples/config/postgresql/types/schema.sql"] queries: ["examples/config/postgresql/authors/query.sql", "examples/config/postgresql/types/query.sql"] engine: "postgresql" @@ -93,6 +97,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false - schema: ["examples/config/postgresql/authors/schema.sql", "examples/config/postgresql/types/schema.sql"] queries: ["examples/config/postgresql/authors/query.sql", "examples/config/postgresql/types/query.sql"] engine: "postgresql" @@ -137,6 +145,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false - schema: ["examples/config/postgresql/authors/schema.sql", "examples/config/postgresql/types/schema.sql"] queries: ["examples/config/postgresql/authors/query.sql", "examples/config/postgresql/types/query.sql"] engine: "postgresql" @@ -181,6 +193,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false # MySQL - schema: ["examples/config/mysql/authors/schema.sql", "examples/config/mysql/types/schema.sql"] queries: ["examples/config/mysql/authors/query.sql", "examples/config/mysql/types/query.sql"] diff --git a/sqlc.request.generated.yaml b/sqlc.request.generated.yaml index 502a9147..5275c236 100644 --- a/sqlc.request.generated.yaml +++ b/sqlc.request.generated.yaml @@ -49,6 +49,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false debugRequest: true - schema: ["examples/config/postgresql/authors/schema.sql", "examples/config/postgresql/types/schema.sql"] queries: ["examples/config/postgresql/authors/query.sql", "examples/config/postgresql/types/query.sql"] @@ -94,6 +98,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false debugRequest: true - schema: ["examples/config/postgresql/authors/schema.sql", "examples/config/postgresql/types/schema.sql"] queries: ["examples/config/postgresql/authors/query.sql", "examples/config/postgresql/types/query.sql"] @@ -139,6 +147,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false debugRequest: true - schema: ["examples/config/postgresql/authors/schema.sql", "examples/config/postgresql/types/schema.sql"] queries: ["examples/config/postgresql/authors/query.sql", "examples/config/postgresql/types/query.sql"] @@ -184,6 +196,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false debugRequest: true # MySQL - schema: ["examples/config/mysql/authors/schema.sql", "examples/config/mysql/types/schema.sql"] diff --git a/unit-tests/CodegenTests/test-requests/DefaultSchemaEnum/request.json b/unit-tests/CodegenTests/test-requests/DefaultSchemaEnum/request.json index a284ef5a..a616a70b 100644 --- a/unit-tests/CodegenTests/test-requests/DefaultSchemaEnum/request.json +++ b/unit-tests/CodegenTests/test-requests/DefaultSchemaEnum/request.json @@ -101,5 +101,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6IiIsInVzZURhcHBlciI6ZmFsc2UsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsIm92ZXJyaWRlcyI6bnVsbCwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6IiIsInVzZURhcHBlciI6ZmFsc2UsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsInVzZU5vZGFUaW1lIjpmYWxzZSwib3ZlcnJpZGVzIjpudWxsLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" } \ No newline at end of file diff --git a/unit-tests/CodegenTests/test-requests/DefaultSchemaEnum/request.message b/unit-tests/CodegenTests/test-requests/DefaultSchemaEnum/request.message index 8f53eb77..e265d0ac 100644 --- a/unit-tests/CodegenTests/test-requests/DefaultSchemaEnum/request.message +++ b/unit-tests/CodegenTests/test-requests/DefaultSchemaEnum/request.message @@ -10,4 +10,4 @@ dummy_column0R  dummy_tablebdummy_table_dummy_columnz dummy_column: query.sql 1INSERT INTO dummy_table (dummy_column) VALUES (?) TestInsert:exec*UQ - dummy_column0Rpublic dummy_tablebdummy_table_dummy_columnz dummy_column: query.sqlB  dummy_table"v1.30.0*{"overrideDriverVersion":"","generateCsproj":true,"targetFramework":"net8.0","namespaceName":"","useDapper":false,"overrideDapperVersion":"","overrides":null,"debugRequest":false} \ No newline at end of file + dummy_column0Rpublic dummy_tablebdummy_table_dummy_columnz dummy_column: query.sqlB  dummy_table"v1.30.0*{"overrideDriverVersion":"","generateCsproj":true,"targetFramework":"net8.0","namespaceName":"","useDapper":false,"overrideDapperVersion":"","useNodaTime":false,"overrides":null,"debugRequest":false} \ No newline at end of file diff --git a/unit-tests/CodegenTests/test-requests/SchemaScopedEnum/request.json b/unit-tests/CodegenTests/test-requests/SchemaScopedEnum/request.json index 263f668e..6ae7191b 100644 --- a/unit-tests/CodegenTests/test-requests/SchemaScopedEnum/request.json +++ b/unit-tests/CodegenTests/test-requests/SchemaScopedEnum/request.json @@ -81,5 +81,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6IiIsInVzZURhcHBlciI6ZmFsc2UsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsIm92ZXJyaWRlcyI6bnVsbCwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6IiIsInVzZURhcHBlciI6ZmFsc2UsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsInVzZU5vZGFUaW1lIjpmYWxzZSwib3ZlcnJpZGVzIjpudWxsLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" } \ No newline at end of file diff --git a/unit-tests/CodegenTests/test-requests/SchemaScopedEnum/request.message b/unit-tests/CodegenTests/test-requests/SchemaScopedEnum/request.message index 4ecfb22f..4a0c671c 100644 --- a/unit-tests/CodegenTests/test-requests/SchemaScopedEnum/request.message +++ b/unit-tests/CodegenTests/test-requests/SchemaScopedEnum/request.message @@ -7,4 +7,4 @@  dummy_schema dummy_tableI dummy_column0R dummy_schema dummy_tablebdummy_table_dummy_column 9SELECT dummy_column FROM dummy_schema.dummy_table LIMIT 1Test:one"W - dummy_column0R dummy_schema dummy_tablebdummy_table_dummy_columnz dummy_column: query.sql"v1.30.0*{"overrideDriverVersion":"","generateCsproj":true,"targetFramework":"net8.0","namespaceName":"","useDapper":false,"overrideDapperVersion":"","overrides":null,"debugRequest":false} \ No newline at end of file + dummy_column0R dummy_schema dummy_tablebdummy_table_dummy_columnz dummy_column: query.sql"v1.30.0*{"overrideDriverVersion":"","generateCsproj":true,"targetFramework":"net8.0","namespaceName":"","useDapper":false,"overrideDapperVersion":"","useNodaTime":false,"overrides":null,"debugRequest":false} \ No newline at end of file From f6c2f12a665c50c91979249ebcee9fd3cbcae9f2 Mon Sep 17 00:00:00 2001 From: Ilan Uzan Date: Fri, 3 Oct 2025 23:41:31 +0200 Subject: [PATCH 2/6] feat: add option to override DateTime to NodaTime.Instant in Postgres --- Drivers/DbDriver.cs | 4 ++ Drivers/NpgsqlDriver.cs | 14 +++++-- .../Templates/PostgresTests.cs | 42 ++++++++++--------- .../NpgsqlDapperTester.generated.cs | 42 ++++++++++++------- .../EndToEndTests/NpgsqlTester.generated.cs | 42 ++++++++++++------- .../NpgsqlDapperTester.generated.cs | 42 ++++++++++++------- .../NpgsqlTester.generated.cs | 42 ++++++++++++------- examples/NpgsqlDapperExample/QuerySql.cs | 2 +- examples/NpgsqlDapperExample/Utils.cs | 5 +++ .../NpgsqlDapperLegacyExample/QuerySql.cs | 2 +- examples/NpgsqlDapperLegacyExample/Utils.cs | 5 +++ examples/NpgsqlExample/QuerySql.cs | 20 +++++++-- examples/NpgsqlLegacyExample/QuerySql.cs | 20 +++++++-- 13 files changed, 186 insertions(+), 96 deletions(-) diff --git a/Drivers/DbDriver.cs b/Drivers/DbDriver.cs index 91e23b56..a12d7dd8 100644 --- a/Drivers/DbDriver.cs +++ b/Drivers/DbDriver.cs @@ -75,7 +75,11 @@ private class NodaInstantTypeHandler : SqlMapper.TypeHandler public override Instant Parse(object value) { if (value is DateTime dt) + { + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); return dt.ToInstant(); + } throw new DataException($"Cannot convert {value?.GetType()} to Instant"); } diff --git a/Drivers/NpgsqlDriver.cs b/Drivers/NpgsqlDriver.cs index 3403e858..1edb7613 100644 --- a/Drivers/NpgsqlDriver.cs +++ b/Drivers/NpgsqlDriver.cs @@ -139,13 +139,21 @@ public NpgsqlDriver( ), ["Instant"] = new( [], - readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetDateTime({ordinal}).ToInstant()", + readerFn: (ordinal, _) => $$""" + (new Func((r, o) => + { + var dt = {{Variable.Reader.AsVarName()}}.GetDateTime(o); + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); + return dt.ToInstant(); + }))({{Variable.Reader.AsVarName()}}, {{ordinal}}) + """, writerFn: (el, _, notNull, isDapper, isLegacy) => { if (notNull) - return $"{el}.ToDateTimeUtc().ToLocalTime()"; + return $"DateTime.SpecifyKind({el}.ToDateTimeUtc(), DateTimeKind.Unspecified)"; var nullValue = isDapper ? "null" : "(object)DBNull.Value"; - return $"{el}?.ToDateTimeUtc().ToLocalTime() ?? {nullValue}"; + return $"{el} is null ? {nullValue} : (DateTime?) DateTime.SpecifyKind({el}.Value.ToDateTimeUtc(), DateTimeKind.Unspecified)"; }, usingDirectives: ["System", "NodaTime", "NodaTime.Extensions"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(Instant), new NodaInstantTypeHandler());", diff --git a/end2end/EndToEndScaffold/Templates/PostgresTests.cs b/end2end/EndToEndScaffold/Templates/PostgresTests.cs index 8c25925e..75f7150a 100644 --- a/end2end/EndToEndScaffold/Templates/PostgresTests.cs +++ b/end2end/EndToEndScaffold/Templates/PostgresTests.cs @@ -493,7 +493,7 @@ void AssertSingularEquals(QuerySql.GetPostgresDateTimeTypesCntRow x, QuerySql.Ge { Impl = $$""" [Test] - [TestCase("{\"name\": \"Swordfishtrombones\", \"year\": 1983}", "$.\"name\"")] + [TestCase("{\"name\": \"Swordfishtrombones\", \"year\" :1983}", "$.\"name\"")] [TestCase(null, null)] public async Task TestPostgresJsonDataTypes( string cJson, @@ -524,14 +524,18 @@ await QuerySql.InsertPostgresSpecialTypes(new QuerySql.InsertPostgresSpecialType void AssertSingularEquals(QuerySql.GetPostgresSpecialTypesRow x, QuerySql.GetPostgresSpecialTypesRow y) { - Assert.That(x.CJson.HasValue, Is.EqualTo(y.CJson.HasValue)); - if (x.CJson.HasValue) - Assert.That(x.CJson.Value.GetRawText(), Is.EqualTo(y.CJson.Value.GetRawText())); - Assert.That(x.CJsonb.HasValue, Is.EqualTo(y.CJsonb.HasValue)); - if (x.CJsonb.HasValue) - Assert.That(x.CJsonb.Value.GetRawText(), Is.EqualTo(y.CJsonb.Value.GetRawText())); - Assert.That(x.CJsonStringOverride, Is.EqualTo(y.CJsonStringOverride)); - Assert.That(x.CJsonpath, Is.EqualTo(y.CJsonpath)); + AssertJsonElementEquals(y.CJson, x.CJson); + AssertJsonElementEquals(y.CJsonb, x.CJsonb); + Assert.That(y.CJsonStringOverride, Is.EqualTo(x.CJsonStringOverride)); + Assert.That(y.CJsonpath, Is.EqualTo(x.CJsonpath)); + } + + void AssertJsonElementEquals(JsonElement? x, JsonElement? y) + { + var options = new JsonSerializerOptions { WriteIndented = false }; + Assert.That(y.HasValue, Is.EqualTo(x.HasValue)); + if (y.HasValue) + Assert.That(JsonSerializer.Serialize(y.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.Value, options))); } } """ @@ -568,17 +572,17 @@ public async Task TestPostgresJsonCopyFrom(int batchSize, string cJson) void AssertSingularEquals(QuerySql.GetPostgresSpecialTypesCntRow x, QuerySql.GetPostgresSpecialTypesCntRow y) { - var options = new JsonSerializerOptions - { - WriteIndented = false - }; Assert.That(y.Cnt, Is.EqualTo(x.Cnt)); - Assert.That(y.CJson.HasValue, Is.EqualTo(x.CJson.HasValue)); - if (y.CJson.HasValue) - Assert.That(JsonSerializer.Serialize(y.CJson.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.CJson.Value, options))); - Assert.That(y.CJsonb.HasValue, Is.EqualTo(x.CJsonb.HasValue)); - if (y.CJsonb.HasValue) - Assert.That(JsonSerializer.Serialize(y.CJsonb.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.CJsonb.Value, options))); + AssertJsonElementEquals(y.CJson, x.CJson); + AssertJsonElementEquals(y.CJsonb, x.CJsonb); + } + + void AssertJsonElementEquals(JsonElement? x, JsonElement? y) + { + var options = new JsonSerializerOptions { WriteIndented = false }; + Assert.That(y.HasValue, Is.EqualTo(x.HasValue)); + if (y.HasValue) + Assert.That(JsonSerializer.Serialize(y.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.Value, options))); } } """ diff --git a/end2end/EndToEndTests/NpgsqlDapperTester.generated.cs b/end2end/EndToEndTests/NpgsqlDapperTester.generated.cs index 09e84696..d8fcc7f2 100644 --- a/end2end/EndToEndTests/NpgsqlDapperTester.generated.cs +++ b/end2end/EndToEndTests/NpgsqlDapperTester.generated.cs @@ -682,7 +682,7 @@ void AssertSingularEquals(QuerySql.GetPostgresGeoTypesRow x, QuerySql.GetPostgre } [Test] - [TestCase("{\"name\": \"Swordfishtrombones\", \"year\": 1983}", "$.\"name\"")] + [TestCase("{\"name\": \"Swordfishtrombones\", \"year\" :1983}", "$.\"name\"")] [TestCase(null, null)] public async Task TestPostgresJsonDataTypes(string cJson, string cJsonpath) { @@ -701,14 +701,21 @@ public async Task TestPostgresJsonDataTypes(string cJson, string cJsonpath) AssertSingularEquals(expected, actual); void AssertSingularEquals(QuerySql.GetPostgresSpecialTypesRow x, QuerySql.GetPostgresSpecialTypesRow y) { - Assert.That(x.CJson.HasValue, Is.EqualTo(y.CJson.HasValue)); - if (x.CJson.HasValue) - Assert.That(x.CJson.Value.GetRawText(), Is.EqualTo(y.CJson.Value.GetRawText())); - Assert.That(x.CJsonb.HasValue, Is.EqualTo(y.CJsonb.HasValue)); - if (x.CJsonb.HasValue) - Assert.That(x.CJsonb.Value.GetRawText(), Is.EqualTo(y.CJsonb.Value.GetRawText())); - Assert.That(x.CJsonStringOverride, Is.EqualTo(y.CJsonStringOverride)); - Assert.That(x.CJsonpath, Is.EqualTo(y.CJsonpath)); + AssertJsonElementEquals(y.CJson, x.CJson); + AssertJsonElementEquals(y.CJsonb, x.CJsonb); + Assert.That(y.CJsonStringOverride, Is.EqualTo(x.CJsonStringOverride)); + Assert.That(y.CJsonpath, Is.EqualTo(x.CJsonpath)); + } + + void AssertJsonElementEquals(JsonElement? x, JsonElement? y) + { + var options = new JsonSerializerOptions + { + WriteIndented = false + }; + Assert.That(y.HasValue, Is.EqualTo(x.HasValue)); + if (y.HasValue) + Assert.That(JsonSerializer.Serialize(y.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.Value, options))); } } @@ -941,18 +948,21 @@ public async Task TestPostgresJsonCopyFrom(int batchSize, string cJson) var actual = await QuerySql.GetPostgresSpecialTypesCnt(); AssertSingularEquals(expected, actual); void AssertSingularEquals(QuerySql.GetPostgresSpecialTypesCntRow x, QuerySql.GetPostgresSpecialTypesCntRow y) + { + Assert.That(y.Cnt, Is.EqualTo(x.Cnt)); + AssertJsonElementEquals(y.CJson, x.CJson); + AssertJsonElementEquals(y.CJsonb, x.CJsonb); + } + + void AssertJsonElementEquals(JsonElement? x, JsonElement? y) { var options = new JsonSerializerOptions { WriteIndented = false }; - Assert.That(y.Cnt, Is.EqualTo(x.Cnt)); - Assert.That(y.CJson.HasValue, Is.EqualTo(x.CJson.HasValue)); - if (y.CJson.HasValue) - Assert.That(JsonSerializer.Serialize(y.CJson.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.CJson.Value, options))); - Assert.That(y.CJsonb.HasValue, Is.EqualTo(x.CJsonb.HasValue)); - if (y.CJsonb.HasValue) - Assert.That(JsonSerializer.Serialize(y.CJsonb.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.CJsonb.Value, options))); + Assert.That(y.HasValue, Is.EqualTo(x.HasValue)); + if (y.HasValue) + Assert.That(JsonSerializer.Serialize(y.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.Value, options))); } } diff --git a/end2end/EndToEndTests/NpgsqlTester.generated.cs b/end2end/EndToEndTests/NpgsqlTester.generated.cs index 18bb50c4..d2f7e9b8 100644 --- a/end2end/EndToEndTests/NpgsqlTester.generated.cs +++ b/end2end/EndToEndTests/NpgsqlTester.generated.cs @@ -682,7 +682,7 @@ void AssertSingularEquals(QuerySql.GetPostgresGeoTypesRow x, QuerySql.GetPostgre } [Test] - [TestCase("{\"name\": \"Swordfishtrombones\", \"year\": 1983}", "$.\"name\"")] + [TestCase("{\"name\": \"Swordfishtrombones\", \"year\" :1983}", "$.\"name\"")] [TestCase(null, null)] public async Task TestPostgresJsonDataTypes(string cJson, string cJsonpath) { @@ -701,14 +701,21 @@ public async Task TestPostgresJsonDataTypes(string cJson, string cJsonpath) AssertSingularEquals(expected, actual.Value); void AssertSingularEquals(QuerySql.GetPostgresSpecialTypesRow x, QuerySql.GetPostgresSpecialTypesRow y) { - Assert.That(x.CJson.HasValue, Is.EqualTo(y.CJson.HasValue)); - if (x.CJson.HasValue) - Assert.That(x.CJson.Value.GetRawText(), Is.EqualTo(y.CJson.Value.GetRawText())); - Assert.That(x.CJsonb.HasValue, Is.EqualTo(y.CJsonb.HasValue)); - if (x.CJsonb.HasValue) - Assert.That(x.CJsonb.Value.GetRawText(), Is.EqualTo(y.CJsonb.Value.GetRawText())); - Assert.That(x.CJsonStringOverride, Is.EqualTo(y.CJsonStringOverride)); - Assert.That(x.CJsonpath, Is.EqualTo(y.CJsonpath)); + AssertJsonElementEquals(y.CJson, x.CJson); + AssertJsonElementEquals(y.CJsonb, x.CJsonb); + Assert.That(y.CJsonStringOverride, Is.EqualTo(x.CJsonStringOverride)); + Assert.That(y.CJsonpath, Is.EqualTo(x.CJsonpath)); + } + + void AssertJsonElementEquals(JsonElement? x, JsonElement? y) + { + var options = new JsonSerializerOptions + { + WriteIndented = false + }; + Assert.That(y.HasValue, Is.EqualTo(x.HasValue)); + if (y.HasValue) + Assert.That(JsonSerializer.Serialize(y.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.Value, options))); } } @@ -941,18 +948,21 @@ public async Task TestPostgresJsonCopyFrom(int batchSize, string cJson) var actual = await QuerySql.GetPostgresSpecialTypesCnt(); AssertSingularEquals(expected, actual.Value); void AssertSingularEquals(QuerySql.GetPostgresSpecialTypesCntRow x, QuerySql.GetPostgresSpecialTypesCntRow y) + { + Assert.That(y.Cnt, Is.EqualTo(x.Cnt)); + AssertJsonElementEquals(y.CJson, x.CJson); + AssertJsonElementEquals(y.CJsonb, x.CJsonb); + } + + void AssertJsonElementEquals(JsonElement? x, JsonElement? y) { var options = new JsonSerializerOptions { WriteIndented = false }; - Assert.That(y.Cnt, Is.EqualTo(x.Cnt)); - Assert.That(y.CJson.HasValue, Is.EqualTo(x.CJson.HasValue)); - if (y.CJson.HasValue) - Assert.That(JsonSerializer.Serialize(y.CJson.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.CJson.Value, options))); - Assert.That(y.CJsonb.HasValue, Is.EqualTo(x.CJsonb.HasValue)); - if (y.CJsonb.HasValue) - Assert.That(JsonSerializer.Serialize(y.CJsonb.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.CJsonb.Value, options))); + Assert.That(y.HasValue, Is.EqualTo(x.HasValue)); + if (y.HasValue) + Assert.That(JsonSerializer.Serialize(y.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.Value, options))); } } diff --git a/end2end/EndToEndTestsLegacy/NpgsqlDapperTester.generated.cs b/end2end/EndToEndTestsLegacy/NpgsqlDapperTester.generated.cs index deb3d279..7d89c64f 100644 --- a/end2end/EndToEndTestsLegacy/NpgsqlDapperTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/NpgsqlDapperTester.generated.cs @@ -682,7 +682,7 @@ void AssertSingularEquals(QuerySql.GetPostgresGeoTypesRow x, QuerySql.GetPostgre } [Test] - [TestCase("{\"name\": \"Swordfishtrombones\", \"year\": 1983}", "$.\"name\"")] + [TestCase("{\"name\": \"Swordfishtrombones\", \"year\" :1983}", "$.\"name\"")] [TestCase(null, null)] public async Task TestPostgresJsonDataTypes(string cJson, string cJsonpath) { @@ -701,14 +701,21 @@ public async Task TestPostgresJsonDataTypes(string cJson, string cJsonpath) AssertSingularEquals(expected, actual); void AssertSingularEquals(QuerySql.GetPostgresSpecialTypesRow x, QuerySql.GetPostgresSpecialTypesRow y) { - Assert.That(x.CJson.HasValue, Is.EqualTo(y.CJson.HasValue)); - if (x.CJson.HasValue) - Assert.That(x.CJson.Value.GetRawText(), Is.EqualTo(y.CJson.Value.GetRawText())); - Assert.That(x.CJsonb.HasValue, Is.EqualTo(y.CJsonb.HasValue)); - if (x.CJsonb.HasValue) - Assert.That(x.CJsonb.Value.GetRawText(), Is.EqualTo(y.CJsonb.Value.GetRawText())); - Assert.That(x.CJsonStringOverride, Is.EqualTo(y.CJsonStringOverride)); - Assert.That(x.CJsonpath, Is.EqualTo(y.CJsonpath)); + AssertJsonElementEquals(y.CJson, x.CJson); + AssertJsonElementEquals(y.CJsonb, x.CJsonb); + Assert.That(y.CJsonStringOverride, Is.EqualTo(x.CJsonStringOverride)); + Assert.That(y.CJsonpath, Is.EqualTo(x.CJsonpath)); + } + + void AssertJsonElementEquals(JsonElement? x, JsonElement? y) + { + var options = new JsonSerializerOptions + { + WriteIndented = false + }; + Assert.That(y.HasValue, Is.EqualTo(x.HasValue)); + if (y.HasValue) + Assert.That(JsonSerializer.Serialize(y.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.Value, options))); } } @@ -941,18 +948,21 @@ public async Task TestPostgresJsonCopyFrom(int batchSize, string cJson) var actual = await QuerySql.GetPostgresSpecialTypesCnt(); AssertSingularEquals(expected, actual); void AssertSingularEquals(QuerySql.GetPostgresSpecialTypesCntRow x, QuerySql.GetPostgresSpecialTypesCntRow y) + { + Assert.That(y.Cnt, Is.EqualTo(x.Cnt)); + AssertJsonElementEquals(y.CJson, x.CJson); + AssertJsonElementEquals(y.CJsonb, x.CJsonb); + } + + void AssertJsonElementEquals(JsonElement? x, JsonElement? y) { var options = new JsonSerializerOptions { WriteIndented = false }; - Assert.That(y.Cnt, Is.EqualTo(x.Cnt)); - Assert.That(y.CJson.HasValue, Is.EqualTo(x.CJson.HasValue)); - if (y.CJson.HasValue) - Assert.That(JsonSerializer.Serialize(y.CJson.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.CJson.Value, options))); - Assert.That(y.CJsonb.HasValue, Is.EqualTo(x.CJsonb.HasValue)); - if (y.CJsonb.HasValue) - Assert.That(JsonSerializer.Serialize(y.CJsonb.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.CJsonb.Value, options))); + Assert.That(y.HasValue, Is.EqualTo(x.HasValue)); + if (y.HasValue) + Assert.That(JsonSerializer.Serialize(y.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.Value, options))); } } diff --git a/end2end/EndToEndTestsLegacy/NpgsqlTester.generated.cs b/end2end/EndToEndTestsLegacy/NpgsqlTester.generated.cs index fb05b00d..8fc2f9b2 100644 --- a/end2end/EndToEndTestsLegacy/NpgsqlTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/NpgsqlTester.generated.cs @@ -682,7 +682,7 @@ void AssertSingularEquals(QuerySql.GetPostgresGeoTypesRow x, QuerySql.GetPostgre } [Test] - [TestCase("{\"name\": \"Swordfishtrombones\", \"year\": 1983}", "$.\"name\"")] + [TestCase("{\"name\": \"Swordfishtrombones\", \"year\" :1983}", "$.\"name\"")] [TestCase(null, null)] public async Task TestPostgresJsonDataTypes(string cJson, string cJsonpath) { @@ -701,14 +701,21 @@ public async Task TestPostgresJsonDataTypes(string cJson, string cJsonpath) AssertSingularEquals(expected, actual); void AssertSingularEquals(QuerySql.GetPostgresSpecialTypesRow x, QuerySql.GetPostgresSpecialTypesRow y) { - Assert.That(x.CJson.HasValue, Is.EqualTo(y.CJson.HasValue)); - if (x.CJson.HasValue) - Assert.That(x.CJson.Value.GetRawText(), Is.EqualTo(y.CJson.Value.GetRawText())); - Assert.That(x.CJsonb.HasValue, Is.EqualTo(y.CJsonb.HasValue)); - if (x.CJsonb.HasValue) - Assert.That(x.CJsonb.Value.GetRawText(), Is.EqualTo(y.CJsonb.Value.GetRawText())); - Assert.That(x.CJsonStringOverride, Is.EqualTo(y.CJsonStringOverride)); - Assert.That(x.CJsonpath, Is.EqualTo(y.CJsonpath)); + AssertJsonElementEquals(y.CJson, x.CJson); + AssertJsonElementEquals(y.CJsonb, x.CJsonb); + Assert.That(y.CJsonStringOverride, Is.EqualTo(x.CJsonStringOverride)); + Assert.That(y.CJsonpath, Is.EqualTo(x.CJsonpath)); + } + + void AssertJsonElementEquals(JsonElement? x, JsonElement? y) + { + var options = new JsonSerializerOptions + { + WriteIndented = false + }; + Assert.That(y.HasValue, Is.EqualTo(x.HasValue)); + if (y.HasValue) + Assert.That(JsonSerializer.Serialize(y.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.Value, options))); } } @@ -941,18 +948,21 @@ public async Task TestPostgresJsonCopyFrom(int batchSize, string cJson) var actual = await QuerySql.GetPostgresSpecialTypesCnt(); AssertSingularEquals(expected, actual); void AssertSingularEquals(QuerySql.GetPostgresSpecialTypesCntRow x, QuerySql.GetPostgresSpecialTypesCntRow y) + { + Assert.That(y.Cnt, Is.EqualTo(x.Cnt)); + AssertJsonElementEquals(y.CJson, x.CJson); + AssertJsonElementEquals(y.CJsonb, x.CJsonb); + } + + void AssertJsonElementEquals(JsonElement? x, JsonElement? y) { var options = new JsonSerializerOptions { WriteIndented = false }; - Assert.That(y.Cnt, Is.EqualTo(x.Cnt)); - Assert.That(y.CJson.HasValue, Is.EqualTo(x.CJson.HasValue)); - if (y.CJson.HasValue) - Assert.That(JsonSerializer.Serialize(y.CJson.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.CJson.Value, options))); - Assert.That(y.CJsonb.HasValue, Is.EqualTo(x.CJsonb.HasValue)); - if (y.CJsonb.HasValue) - Assert.That(JsonSerializer.Serialize(y.CJsonb.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.CJsonb.Value, options))); + Assert.That(y.HasValue, Is.EqualTo(x.HasValue)); + if (y.HasValue) + Assert.That(JsonSerializer.Serialize(y.Value, options), Is.EqualTo(JsonSerializer.Serialize(x.Value, options))); } } diff --git a/examples/NpgsqlDapperExample/QuerySql.cs b/examples/NpgsqlDapperExample/QuerySql.cs index 59f993bb..8f9aa0e7 100644 --- a/examples/NpgsqlDapperExample/QuerySql.cs +++ b/examples/NpgsqlDapperExample/QuerySql.cs @@ -921,7 +921,7 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar queryParams.Add("c_timestamp", args.CTimestamp); queryParams.Add("c_timestamp_with_tz", args.CTimestampWithTz); queryParams.Add("c_interval", args.CInterval); - queryParams.Add("c_timestamp_noda_instant_override", args.CTimestampNodaInstantOverride?.ToDateTimeUtc().ToLocalTime() ?? null); + queryParams.Add("c_timestamp_noda_instant_override", args.CTimestampNodaInstantOverride is null ? null : (DateTime? )DateTime.SpecifyKind(args.CTimestampNodaInstantOverride.Value.ToDateTimeUtc(), DateTimeKind.Unspecified)); if (this.Transaction == null) { using (var connection = new NpgsqlConnection(ConnectionString)) diff --git a/examples/NpgsqlDapperExample/Utils.cs b/examples/NpgsqlDapperExample/Utils.cs index ce4abff4..59cdf47a 100644 --- a/examples/NpgsqlDapperExample/Utils.cs +++ b/examples/NpgsqlDapperExample/Utils.cs @@ -19,7 +19,12 @@ private class NodaInstantTypeHandler : SqlMapper.TypeHandler public override Instant Parse(object value) { if (value is DateTime dt) + { + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); return dt.ToInstant(); + } + throw new DataException($"Cannot convert {value?.GetType()} to Instant"); } diff --git a/examples/NpgsqlDapperLegacyExample/QuerySql.cs b/examples/NpgsqlDapperLegacyExample/QuerySql.cs index 8e9327d0..df2ca429 100644 --- a/examples/NpgsqlDapperLegacyExample/QuerySql.cs +++ b/examples/NpgsqlDapperLegacyExample/QuerySql.cs @@ -922,7 +922,7 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar queryParams.Add("c_timestamp", args.CTimestamp); queryParams.Add("c_timestamp_with_tz", args.CTimestampWithTz); queryParams.Add("c_interval", args.CInterval); - queryParams.Add("c_timestamp_noda_instant_override", args.CTimestampNodaInstantOverride?.ToDateTimeUtc().ToLocalTime() ?? null); + queryParams.Add("c_timestamp_noda_instant_override", args.CTimestampNodaInstantOverride is null ? null : (DateTime? )DateTime.SpecifyKind(args.CTimestampNodaInstantOverride.Value.ToDateTimeUtc(), DateTimeKind.Unspecified)); if (this.Transaction == null) { using (var connection = new NpgsqlConnection(ConnectionString)) diff --git a/examples/NpgsqlDapperLegacyExample/Utils.cs b/examples/NpgsqlDapperLegacyExample/Utils.cs index 2a322150..caa7529c 100644 --- a/examples/NpgsqlDapperLegacyExample/Utils.cs +++ b/examples/NpgsqlDapperLegacyExample/Utils.cs @@ -20,7 +20,12 @@ private class NodaInstantTypeHandler : SqlMapper.TypeHandler public override Instant Parse(object value) { if (value is DateTime dt) + { + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); return dt.ToInstant(); + } + throw new DataException($"Cannot convert {value?.GetType()} to Instant"); } diff --git a/examples/NpgsqlExample/QuerySql.cs b/examples/NpgsqlExample/QuerySql.cs index dcdb008c..baec11ee 100644 --- a/examples/NpgsqlExample/QuerySql.cs +++ b/examples/NpgsqlExample/QuerySql.cs @@ -1304,7 +1304,7 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar command.Parameters.AddWithValue("@c_timestamp", NpgsqlDbType.Timestamp, args.CTimestamp ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_timestamp_with_tz", NpgsqlDbType.TimestampTz, args.CTimestampWithTz ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_interval", NpgsqlDbType.Interval, args.CInterval ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", NpgsqlDbType.Timestamp, args.CTimestampNodaInstantOverride?.ToDateTimeUtc().ToLocalTime() ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", NpgsqlDbType.Timestamp, args.CTimestampNodaInstantOverride is null ? (object)DBNull.Value : (DateTime? )DateTime.SpecifyKind(args.CTimestampNodaInstantOverride.Value.ToDateTimeUtc(), DateTimeKind.Unspecified)); await command.ExecuteNonQueryAsync(); } } @@ -1323,7 +1323,7 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar command.Parameters.AddWithValue("@c_timestamp", NpgsqlDbType.Timestamp, args.CTimestamp ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_timestamp_with_tz", NpgsqlDbType.TimestampTz, args.CTimestampWithTz ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_interval", NpgsqlDbType.Interval, args.CInterval ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", NpgsqlDbType.Timestamp, args.CTimestampNodaInstantOverride?.ToDateTimeUtc().ToLocalTime() ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", NpgsqlDbType.Timestamp, args.CTimestampNodaInstantOverride is null ? (object)DBNull.Value : (DateTime? )DateTime.SpecifyKind(args.CTimestampNodaInstantOverride.Value.ToDateTimeUtc(), DateTimeKind.Unspecified)); await command.ExecuteNonQueryAsync(); } } @@ -1349,7 +1349,13 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar CTimestamp = reader.IsDBNull(2) ? null : reader.GetDateTime(2), CTimestampWithTz = reader.IsDBNull(3) ? null : reader.GetDateTime(3), CInterval = reader.IsDBNull(4) ? null : reader.GetFieldValue(4), - CTimestampNodaInstantOverride = reader.IsDBNull(5) ? null : reader.GetDateTime(5).ToInstant() + CTimestampNodaInstantOverride = reader.IsDBNull(5) ? null : (new Func((r, o) => + { + var dt = reader.GetDateTime(o); + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); + return dt.ToInstant(); + }))(reader, 5) }; } } @@ -1376,7 +1382,13 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar CTimestamp = reader.IsDBNull(2) ? null : reader.GetDateTime(2), CTimestampWithTz = reader.IsDBNull(3) ? null : reader.GetDateTime(3), CInterval = reader.IsDBNull(4) ? null : reader.GetFieldValue(4), - CTimestampNodaInstantOverride = reader.IsDBNull(5) ? null : reader.GetDateTime(5).ToInstant() + CTimestampNodaInstantOverride = reader.IsDBNull(5) ? null : (new Func((r, o) => + { + var dt = reader.GetDateTime(o); + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); + return dt.ToInstant(); + }))(reader, 5) }; } } diff --git a/examples/NpgsqlLegacyExample/QuerySql.cs b/examples/NpgsqlLegacyExample/QuerySql.cs index 3582bfaa..9f156b89 100644 --- a/examples/NpgsqlLegacyExample/QuerySql.cs +++ b/examples/NpgsqlLegacyExample/QuerySql.cs @@ -1515,7 +1515,7 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar command.Parameters.AddWithValue("@c_timestamp", NpgsqlDbType.Timestamp, args.CTimestamp ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_timestamp_with_tz", NpgsqlDbType.TimestampTz, args.CTimestampWithTz ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_interval", NpgsqlDbType.Interval, args.CInterval ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", NpgsqlDbType.Timestamp, args.CTimestampNodaInstantOverride?.ToDateTimeUtc().ToLocalTime() ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", NpgsqlDbType.Timestamp, args.CTimestampNodaInstantOverride is null ? (object)DBNull.Value : (DateTime? )DateTime.SpecifyKind(args.CTimestampNodaInstantOverride.Value.ToDateTimeUtc(), DateTimeKind.Unspecified)); await command.ExecuteNonQueryAsync(); } } @@ -1534,7 +1534,7 @@ public async Task InsertPostgresDateTimeTypes(InsertPostgresDateTimeTypesArgs ar command.Parameters.AddWithValue("@c_timestamp", NpgsqlDbType.Timestamp, args.CTimestamp ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_timestamp_with_tz", NpgsqlDbType.TimestampTz, args.CTimestampWithTz ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_interval", NpgsqlDbType.Interval, args.CInterval ?? (object)DBNull.Value); - command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", NpgsqlDbType.Timestamp, args.CTimestampNodaInstantOverride?.ToDateTimeUtc().ToLocalTime() ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", NpgsqlDbType.Timestamp, args.CTimestampNodaInstantOverride is null ? (object)DBNull.Value : (DateTime? )DateTime.SpecifyKind(args.CTimestampNodaInstantOverride.Value.ToDateTimeUtc(), DateTimeKind.Unspecified)); await command.ExecuteNonQueryAsync(); } } @@ -1568,7 +1568,13 @@ public async Task GetPostgresDateTimeTypes() CTimestamp = reader.IsDBNull(2) ? (DateTime? )null : reader.GetDateTime(2), CTimestampWithTz = reader.IsDBNull(3) ? (DateTime? )null : reader.GetDateTime(3), CInterval = reader.IsDBNull(4) ? (TimeSpan? )null : reader.GetFieldValue(4), - CTimestampNodaInstantOverride = reader.IsDBNull(5) ? (Instant? )null : reader.GetDateTime(5).ToInstant() + CTimestampNodaInstantOverride = reader.IsDBNull(5) ? (Instant? )null : (new Func((r, o) => + { + var dt = reader.GetDateTime(o); + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); + return dt.ToInstant(); + }))(reader, 5) }; } } @@ -1595,7 +1601,13 @@ public async Task GetPostgresDateTimeTypes() CTimestamp = reader.IsDBNull(2) ? (DateTime? )null : reader.GetDateTime(2), CTimestampWithTz = reader.IsDBNull(3) ? (DateTime? )null : reader.GetDateTime(3), CInterval = reader.IsDBNull(4) ? (TimeSpan? )null : reader.GetFieldValue(4), - CTimestampNodaInstantOverride = reader.IsDBNull(5) ? (Instant? )null : reader.GetDateTime(5).ToInstant() + CTimestampNodaInstantOverride = reader.IsDBNull(5) ? (Instant? )null : (new Func((r, o) => + { + var dt = reader.GetDateTime(o); + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); + return dt.ToInstant(); + }))(reader, 5) }; } } From a951c3f88b6a1360d48acc0b50aa0fa4d48ba637 Mon Sep 17 00:00:00 2001 From: Ilan Uzan Date: Sat, 4 Oct 2025 00:04:57 +0200 Subject: [PATCH 3/6] feat: add option to override DateTime to NodaTime.Instant in MySQL --- Drivers/MySqlConnectorDriver.cs | 23 +++++++++ .../EndToEndScaffold/Templates/MySqlTests.cs | 37 +++++++++++++-- .../MySqlConnectorDapperTester.generated.cs | 20 ++++++-- .../MySqlConnectorTester.generated.cs | 20 ++++++-- .../MySqlConnectorDapperTester.generated.cs | 20 ++++++-- .../MySqlConnectorTester.generated.cs | 20 ++++++-- .../MySqlConnectorDapperExample/Models.cs | 3 ++ .../MySqlConnectorDapperExample/QuerySql.cs | 9 +++- examples/MySqlConnectorDapperExample/Utils.cs | 24 ++++++++++ .../MySqlConnectorDapperExample/request.json | 44 ++++++++++++++++-- .../request.message | Bin 25770 -> 26353 bytes .../Models.cs | 3 ++ .../QuerySql.cs | 9 +++- .../Utils.cs | 24 ++++++++++ .../request.json | 44 ++++++++++++++++-- .../request.message | Bin 25804 -> 26387 bytes examples/MySqlConnectorExample/Models.cs | 4 +- examples/MySqlConnectorExample/QuerySql.cs | 30 +++++++++--- examples/MySqlConnectorExample/request.json | 44 ++++++++++++++++-- .../MySqlConnectorExample/request.message | Bin 25754 -> 26337 bytes .../MySqlConnectorLegacyExample/Models.cs | 3 ++ .../MySqlConnectorLegacyExample/QuerySql.cs | 28 +++++++++-- .../MySqlConnectorLegacyExample/request.json | 44 ++++++++++++++++-- .../request.message | Bin 25788 -> 26371 bytes examples/config/mysql/types/query.sql | 5 +- examples/config/mysql/types/schema.sql | 11 +++-- sqlc.ci.yaml | 16 +++++++ sqlc.local.generated.yaml | 16 +++++++ sqlc.request.generated.yaml | 16 +++++++ 29 files changed, 454 insertions(+), 63 deletions(-) diff --git a/Drivers/MySqlConnectorDriver.cs b/Drivers/MySqlConnectorDriver.cs index 9dd89272..e67ea08e 100644 --- a/Drivers/MySqlConnectorDriver.cs +++ b/Drivers/MySqlConnectorDriver.cs @@ -124,6 +124,29 @@ public sealed partial class MySqlConnectorDriver( }, readerFn: (ordinal, _) => $"{Variable.Reader.AsVarName()}.GetFieldValue({ordinal})" ), + ["Instant"] = new( + [], + readerFn: (ordinal, _) => $$""" + (new Func((r, o) => + { + var dt = {{Variable.Reader.AsVarName()}}.GetDateTime(o); + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); + return dt.ToInstant(); + }))({{Variable.Reader.AsVarName()}}, {{ordinal}}) + """, + writerFn: (el, _, notNull, isDapper, isLegacy) => + { + if (notNull) + return $"DateTime.SpecifyKind({el}.ToDateTimeUtc(), DateTimeKind.Unspecified)"; + var nullValue = isDapper ? "null" : "(object)DBNull.Value"; + return $"{el} is null ? {nullValue} : (DateTime?) DateTime.SpecifyKind({el}.Value.ToDateTimeUtc(), DateTimeKind.Unspecified)"; + }, + usingDirectives: ["System", "NodaTime", "NodaTime.Extensions"], + sqlMapper: "SqlMapper.AddTypeHandler(typeof(Instant), new NodaInstantTypeHandler());", + sqlMapperImpl: NodaInstantTypeHandler + ), + /* Unstructured data types */ ["JsonElement"] = new( diff --git a/end2end/EndToEndScaffold/Templates/MySqlTests.cs b/end2end/EndToEndScaffold/Templates/MySqlTests.cs index d5745d34..3d63e68d 100644 --- a/end2end/EndToEndScaffold/Templates/MySqlTests.cs +++ b/end2end/EndToEndScaffold/Templates/MySqlTests.cs @@ -174,15 +174,39 @@ void AssertSingularEquals(QuerySql.GetMysqlNumericTypesRow x, QuerySql.GetMysqlN [KnownTestType.MySqlDateTimeDataTypes] = new TestImpl { Impl = $$""" + + private static IEnumerable MySqlDateTimeTypesTestCases + { + get + { + yield return new TestCaseData( + (short) 1999, + DateTime.Parse("2000-1-30"), + DateTime.Parse("1983-11-3 02:01:22"), + DateTime.Parse("2010-1-30 08:11:00"), + TimeSpan.Parse("02:01:22"), + Instant.FromUtc(2025, 10, 15, 19, 55, 2) + ).SetName("DateTimeTypes with values"); + yield return new TestCaseData( + null, + null, + null, + null, + null, + null + ).SetName("DateTimeTypes with null values"); + } + } + [Test] - [TestCase(1999, "2000-1-30", "1983-11-3 02:01:22", "2010-1-30 08:11:00", "02:01:22")] - [TestCase(null, null, null, null, null)] + [TestCaseSource(nameof(MySqlDateTimeTypesTestCases))] public async Task TestMySqlDateTimeTypes( short? cYear, DateTime? cDate, DateTime? cDatetime, DateTime? cTimestamp, - TimeSpan? cTime) + TimeSpan? cTime, + Instant? cTimestampNodaInstantOverride) { await QuerySql.InsertMysqlDatetimeTypes(new QuerySql.InsertMysqlDatetimeTypesArgs { @@ -190,7 +214,8 @@ await QuerySql.InsertMysqlDatetimeTypes(new QuerySql.InsertMysqlDatetimeTypesArg CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, - CTime = cTime + CTime = cTime, + CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }); var expected = new QuerySql.GetMysqlDatetimeTypesRow @@ -199,7 +224,8 @@ await QuerySql.InsertMysqlDatetimeTypes(new QuerySql.InsertMysqlDatetimeTypesArg CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, - CTime = cTime + CTime = cTime, + CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }; var actual = await QuerySql.GetMysqlDatetimeTypes(); AssertSingularEquals(expected, actual{{Consts.UnknownRecordValuePlaceholder}}); @@ -211,6 +237,7 @@ void AssertSingularEquals(QuerySql.GetMysqlDatetimeTypesRow x, QuerySql.GetMysql Assert.That(x.CDatetime, Is.EqualTo(y.CDatetime)); Assert.That(x.CTimestamp, Is.EqualTo(y.CTimestamp)); Assert.That(x.CTime, Is.EqualTo(y.CTime)); + Assert.That(x.CTimestampNodaInstantOverride, Is.EqualTo(y.CTimestampNodaInstantOverride)); } } """ diff --git a/end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs b/end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs index 21d365d1..ee0dbacc 100644 --- a/end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs +++ b/end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs @@ -519,19 +519,28 @@ void AssertSingularEquals(QuerySql.GetMysqlNumericTypesRow x, QuerySql.GetMysqlN } } + private static IEnumerable MySqlDateTimeTypesTestCases + { + get + { + yield return new TestCaseData((short)1999, DateTime.Parse("2000-1-30"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2010-1-30 08:11:00"), TimeSpan.Parse("02:01:22"), Instant.FromUtc(2025, 1, 1, 1, 1, 1)).SetName("DateTimeTypes with values"); + yield return new TestCaseData(null, null, null, null, null, null).SetName("DateTimeTypes with null values"); + } + } + [Test] - [TestCase(1999, "2000-1-30", "1983-11-3 02:01:22", "2010-1-30 08:11:00", "02:01:22")] - [TestCase(null, null, null, null, null)] - public async Task TestMySqlDateTimeTypes(short? cYear, DateTime? cDate, DateTime? cDatetime, DateTime? cTimestamp, TimeSpan? cTime) + [TestCaseSource(nameof(MySqlDateTimeTypesTestCases))] + public async Task TestMySqlDateTimeTypes(short? cYear, DateTime? cDate, DateTime? cDatetime, DateTime? cTimestamp, TimeSpan? cTime, Instant? cTimestampNodaInstantOverride) { - await QuerySql.InsertMysqlDatetimeTypes(new QuerySql.InsertMysqlDatetimeTypesArgs { CYear = cYear, CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, CTime = cTime }); + await QuerySql.InsertMysqlDatetimeTypes(new QuerySql.InsertMysqlDatetimeTypesArgs { CYear = cYear, CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, CTime = cTime, CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }); var expected = new QuerySql.GetMysqlDatetimeTypesRow { CYear = cYear, CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, - CTime = cTime + CTime = cTime, + CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }; var actual = await QuerySql.GetMysqlDatetimeTypes(); AssertSingularEquals(expected, actual); @@ -542,6 +551,7 @@ void AssertSingularEquals(QuerySql.GetMysqlDatetimeTypesRow x, QuerySql.GetMysql Assert.That(x.CDatetime, Is.EqualTo(y.CDatetime)); Assert.That(x.CTimestamp, Is.EqualTo(y.CTimestamp)); Assert.That(x.CTime, Is.EqualTo(y.CTime)); + Assert.That(x.CTimestampNodaInstantOverride, Is.EqualTo(y.CTimestampNodaInstantOverride)); } } diff --git a/end2end/EndToEndTests/MySqlConnectorTester.generated.cs b/end2end/EndToEndTests/MySqlConnectorTester.generated.cs index bc1cddfc..4c952627 100644 --- a/end2end/EndToEndTests/MySqlConnectorTester.generated.cs +++ b/end2end/EndToEndTests/MySqlConnectorTester.generated.cs @@ -519,19 +519,28 @@ void AssertSingularEquals(QuerySql.GetMysqlNumericTypesRow x, QuerySql.GetMysqlN } } + private static IEnumerable MySqlDateTimeTypesTestCases + { + get + { + yield return new TestCaseData((short)1999, DateTime.Parse("2000-1-30"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2010-1-30 08:11:00"), TimeSpan.Parse("02:01:22"), Instant.FromUtc(2025, 1, 1, 1, 1, 1)).SetName("DateTimeTypes with values"); + yield return new TestCaseData(null, null, null, null, null, null).SetName("DateTimeTypes with null values"); + } + } + [Test] - [TestCase(1999, "2000-1-30", "1983-11-3 02:01:22", "2010-1-30 08:11:00", "02:01:22")] - [TestCase(null, null, null, null, null)] - public async Task TestMySqlDateTimeTypes(short? cYear, DateTime? cDate, DateTime? cDatetime, DateTime? cTimestamp, TimeSpan? cTime) + [TestCaseSource(nameof(MySqlDateTimeTypesTestCases))] + public async Task TestMySqlDateTimeTypes(short? cYear, DateTime? cDate, DateTime? cDatetime, DateTime? cTimestamp, TimeSpan? cTime, Instant? cTimestampNodaInstantOverride) { - await QuerySql.InsertMysqlDatetimeTypes(new QuerySql.InsertMysqlDatetimeTypesArgs { CYear = cYear, CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, CTime = cTime }); + await QuerySql.InsertMysqlDatetimeTypes(new QuerySql.InsertMysqlDatetimeTypesArgs { CYear = cYear, CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, CTime = cTime, CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }); var expected = new QuerySql.GetMysqlDatetimeTypesRow { CYear = cYear, CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, - CTime = cTime + CTime = cTime, + CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }; var actual = await QuerySql.GetMysqlDatetimeTypes(); AssertSingularEquals(expected, actual.Value); @@ -542,6 +551,7 @@ void AssertSingularEquals(QuerySql.GetMysqlDatetimeTypesRow x, QuerySql.GetMysql Assert.That(x.CDatetime, Is.EqualTo(y.CDatetime)); Assert.That(x.CTimestamp, Is.EqualTo(y.CTimestamp)); Assert.That(x.CTime, Is.EqualTo(y.CTime)); + Assert.That(x.CTimestampNodaInstantOverride, Is.EqualTo(y.CTimestampNodaInstantOverride)); } } diff --git a/end2end/EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs b/end2end/EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs index 876c7e31..be3698cc 100644 --- a/end2end/EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs @@ -519,19 +519,28 @@ void AssertSingularEquals(QuerySql.GetMysqlNumericTypesRow x, QuerySql.GetMysqlN } } + private static IEnumerable MySqlDateTimeTypesTestCases + { + get + { + yield return new TestCaseData((short)1999, DateTime.Parse("2000-1-30"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2010-1-30 08:11:00"), TimeSpan.Parse("02:01:22"), Instant.FromUtc(2025, 1, 1, 1, 1, 1)).SetName("DateTimeTypes with values"); + yield return new TestCaseData(null, null, null, null, null, null).SetName("DateTimeTypes with null values"); + } + } + [Test] - [TestCase(1999, "2000-1-30", "1983-11-3 02:01:22", "2010-1-30 08:11:00", "02:01:22")] - [TestCase(null, null, null, null, null)] - public async Task TestMySqlDateTimeTypes(short? cYear, DateTime? cDate, DateTime? cDatetime, DateTime? cTimestamp, TimeSpan? cTime) + [TestCaseSource(nameof(MySqlDateTimeTypesTestCases))] + public async Task TestMySqlDateTimeTypes(short? cYear, DateTime? cDate, DateTime? cDatetime, DateTime? cTimestamp, TimeSpan? cTime, Instant? cTimestampNodaInstantOverride) { - await QuerySql.InsertMysqlDatetimeTypes(new QuerySql.InsertMysqlDatetimeTypesArgs { CYear = cYear, CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, CTime = cTime }); + await QuerySql.InsertMysqlDatetimeTypes(new QuerySql.InsertMysqlDatetimeTypesArgs { CYear = cYear, CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, CTime = cTime, CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }); var expected = new QuerySql.GetMysqlDatetimeTypesRow { CYear = cYear, CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, - CTime = cTime + CTime = cTime, + CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }; var actual = await QuerySql.GetMysqlDatetimeTypes(); AssertSingularEquals(expected, actual); @@ -542,6 +551,7 @@ void AssertSingularEquals(QuerySql.GetMysqlDatetimeTypesRow x, QuerySql.GetMysql Assert.That(x.CDatetime, Is.EqualTo(y.CDatetime)); Assert.That(x.CTimestamp, Is.EqualTo(y.CTimestamp)); Assert.That(x.CTime, Is.EqualTo(y.CTime)); + Assert.That(x.CTimestampNodaInstantOverride, Is.EqualTo(y.CTimestampNodaInstantOverride)); } } diff --git a/end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs b/end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs index 944bda04..d68b319e 100644 --- a/end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs @@ -519,19 +519,28 @@ void AssertSingularEquals(QuerySql.GetMysqlNumericTypesRow x, QuerySql.GetMysqlN } } + private static IEnumerable MySqlDateTimeTypesTestCases + { + get + { + yield return new TestCaseData((short)1999, DateTime.Parse("2000-1-30"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2010-1-30 08:11:00"), TimeSpan.Parse("02:01:22"), Instant.FromUtc(2025, 1, 1, 1, 1, 1)).SetName("DateTimeTypes with values"); + yield return new TestCaseData(null, null, null, null, null, null).SetName("DateTimeTypes with null values"); + } + } + [Test] - [TestCase(1999, "2000-1-30", "1983-11-3 02:01:22", "2010-1-30 08:11:00", "02:01:22")] - [TestCase(null, null, null, null, null)] - public async Task TestMySqlDateTimeTypes(short? cYear, DateTime? cDate, DateTime? cDatetime, DateTime? cTimestamp, TimeSpan? cTime) + [TestCaseSource(nameof(MySqlDateTimeTypesTestCases))] + public async Task TestMySqlDateTimeTypes(short? cYear, DateTime? cDate, DateTime? cDatetime, DateTime? cTimestamp, TimeSpan? cTime, Instant? cTimestampNodaInstantOverride) { - await QuerySql.InsertMysqlDatetimeTypes(new QuerySql.InsertMysqlDatetimeTypesArgs { CYear = cYear, CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, CTime = cTime }); + await QuerySql.InsertMysqlDatetimeTypes(new QuerySql.InsertMysqlDatetimeTypesArgs { CYear = cYear, CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, CTime = cTime, CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }); var expected = new QuerySql.GetMysqlDatetimeTypesRow { CYear = cYear, CDate = cDate, CDatetime = cDatetime, CTimestamp = cTimestamp, - CTime = cTime + CTime = cTime, + CTimestampNodaInstantOverride = cTimestampNodaInstantOverride }; var actual = await QuerySql.GetMysqlDatetimeTypes(); AssertSingularEquals(expected, actual); @@ -542,6 +551,7 @@ void AssertSingularEquals(QuerySql.GetMysqlDatetimeTypesRow x, QuerySql.GetMysql Assert.That(x.CDatetime, Is.EqualTo(y.CDatetime)); Assert.That(x.CTimestamp, Is.EqualTo(y.CTimestamp)); Assert.That(x.CTime, Is.EqualTo(y.CTime)); + Assert.That(x.CTimestampNodaInstantOverride, Is.EqualTo(y.CTimestampNodaInstantOverride)); } } diff --git a/examples/MySqlConnectorDapperExample/Models.cs b/examples/MySqlConnectorDapperExample/Models.cs index f2e1b2e3..5b323bf6 100644 --- a/examples/MySqlConnectorDapperExample/Models.cs +++ b/examples/MySqlConnectorDapperExample/Models.cs @@ -1,4 +1,6 @@ // auto-generated by sqlc - do not edit +using NodaTime; +using NodaTime.Extensions; using System; using System.Collections.Generic; using System.Linq; @@ -58,6 +60,7 @@ public class MysqlDatetimeType public DateTime? CDatetime { get; init; } public DateTime? CTimestamp { get; init; } public TimeSpan? CTime { get; init; } + public DateTime? CTimestampNodaInstantOverride { get; init; } }; public class MysqlBinaryType { diff --git a/examples/MySqlConnectorDapperExample/QuerySql.cs b/examples/MySqlConnectorDapperExample/QuerySql.cs index 1f610152..a133ac09 100644 --- a/examples/MySqlConnectorDapperExample/QuerySql.cs +++ b/examples/MySqlConnectorDapperExample/QuerySql.cs @@ -9,6 +9,8 @@ using CsvHelper.TypeConversion; using Dapper; using MySqlConnector; +using NodaTime; +using NodaTime.Extensions; using System; using System.Collections.Generic; using System.Globalization; @@ -952,7 +954,7 @@ public async Task TruncateMysqlStringTypes() await this.Transaction.Connection.ExecuteAsync(TruncateMysqlStringTypesSql, transaction: this.Transaction); } - private const string InsertMysqlDatetimeTypesSql = " INSERT INTO mysql_datetime_types ( c_year, c_date, c_datetime, c_timestamp, c_time ) VALUES (@c_year, @c_date, @c_datetime, @c_timestamp, @c_time)"; + private const string InsertMysqlDatetimeTypesSql = " INSERT INTO mysql_datetime_types ( c_year, c_date, c_datetime, c_timestamp, c_time, c_timestamp_noda_instant_override ) VALUES (@c_year, @c_date, @c_datetime, @c_timestamp, @c_time, @c_timestamp_noda_instant_override)"; public class InsertMysqlDatetimeTypesArgs { public short? CYear { get; init; } @@ -960,6 +962,7 @@ public class InsertMysqlDatetimeTypesArgs public DateTime? CDatetime { get; init; } public DateTime? CTimestamp { get; init; } public TimeSpan? CTime { get; init; } + public Instant? CTimestampNodaInstantOverride { get; init; } }; public async Task InsertMysqlDatetimeTypes(InsertMysqlDatetimeTypesArgs args) { @@ -969,6 +972,7 @@ public async Task InsertMysqlDatetimeTypes(InsertMysqlDatetimeTypesArgs args) queryParams.Add("c_datetime", args.CDatetime); queryParams.Add("c_timestamp", args.CTimestamp); queryParams.Add("c_time", args.CTime); + queryParams.Add("c_timestamp_noda_instant_override", args.CTimestampNodaInstantOverride is null ? null : (DateTime? )DateTime.SpecifyKind(args.CTimestampNodaInstantOverride.Value.ToDateTimeUtc(), DateTimeKind.Unspecified)); if (this.Transaction == null) { using (var connection = new MySqlConnection(ConnectionString)) @@ -1036,7 +1040,7 @@ public async Task InsertMysqlDatetimeTypesBatch(List GetMysqlDatetimeTypes() { diff --git a/examples/MySqlConnectorDapperExample/Utils.cs b/examples/MySqlConnectorDapperExample/Utils.cs index 86043902..a5913f0d 100644 --- a/examples/MySqlConnectorDapperExample/Utils.cs +++ b/examples/MySqlConnectorDapperExample/Utils.cs @@ -3,6 +3,9 @@ using CsvHelper.Configuration; using CsvHelper.TypeConversion; using Dapper; +using NodaTime; +using NodaTime.Extensions; +using System; using System.Collections.Generic; using System.Data; using System.Linq; @@ -11,6 +14,26 @@ namespace MySqlConnectorDapperExampleGen; public static class Utils { + private class NodaInstantTypeHandler : SqlMapper.TypeHandler + { + public override Instant Parse(object value) + { + if (value is DateTime dt) + { + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); + return dt.ToInstant(); + } + + throw new DataException($"Cannot convert {value?.GetType()} to Instant"); + } + + public override void SetValue(IDbDataParameter parameter, Instant value) + { + parameter.Value = value; + } + } + private class JsonElementTypeHandler : SqlMapper.TypeHandler { public override JsonElement Parse(object value) @@ -28,6 +51,7 @@ public override void SetValue(IDbDataParameter parameter, JsonElement value) public static void ConfigureSqlMapper() { + SqlMapper.AddTypeHandler(typeof(Instant), new NodaInstantTypeHandler()); SqlMapper.AddTypeHandler(typeof(JsonElement), new JsonElementTypeHandler()); SqlMapper.AddTypeHandler(typeof(HashSet), new BiosAuthorTypeTypeHandler()); SqlMapper.AddTypeHandler(typeof(HashSet), new MysqlStringTypesCSetTypeHandler()); diff --git a/examples/MySqlConnectorDapperExample/request.json b/examples/MySqlConnectorDapperExample/request.json index 09a43ac1..54a1a6a9 100644 --- a/examples/MySqlConnectorDapperExample/request.json +++ b/examples/MySqlConnectorDapperExample/request.json @@ -13,7 +13,7 @@ "codegen": { "out": "examples/MySqlConnectorDapperExample", "plugin": "csharp", - "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JEYXBwZXJFeGFtcGxlR2VuIiwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJpbnQifX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOnRydWUsInR5cGUiOiJEYXRlVGltZSJ9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19XSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwidXNlRGFwcGVyIjp0cnVlfQ==", + "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JEYXBwZXJFeGFtcGxlR2VuIiwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJpbnQifX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOnRydWUsInR5cGUiOiJEYXRlVGltZSJ9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiKjpjX3RpbWVzdGFtcF9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJub3ROdWxsIjpmYWxzZSwidHlwZSI6Ikluc3RhbnQifX1dLCJ0YXJnZXRGcmFtZXdvcmsiOiJuZXQ4LjAiLCJ1c2VEYXBwZXIiOnRydWV9", "process": { "cmd": "./dist/LocalRunner" } @@ -452,6 +452,16 @@ "type": { "name": "time" } + }, + { + "name": "c_timestamp_noda_instant_override", + "length": 19, + "table": { + "name": "mysql_datetime_types" + }, + "type": { + "name": "timestamp" + } } ] }, @@ -2996,7 +3006,7 @@ "filename": "query.sql" }, { - "text": "\nINSERT INTO mysql_datetime_types \n(\n c_year,\n c_date,\n c_datetime,\n c_timestamp,\n c_time\n) \nVALUES (?, ?, ?, ?, ?)", + "text": "\nINSERT INTO mysql_datetime_types \n(\n c_year,\n c_date,\n c_datetime,\n c_timestamp,\n c_time,\n c_timestamp_noda_instant_override\n) \nVALUES (?, ?, ?, ?, ?, ?)", "name": "InsertMysqlDatetimeTypes", "cmd": ":exec", "parameters": [ @@ -3074,6 +3084,21 @@ }, "originalName": "c_time" } + }, + { + "number": 6, + "column": { + "name": "c_timestamp_noda_instant_override", + "length": 19, + "table": { + "schema": "public", + "name": "mysql_datetime_types" + }, + "type": { + "name": "timestamp" + }, + "originalName": "c_timestamp_noda_instant_override" + } } ], "comments": [ @@ -3171,7 +3196,7 @@ } }, { - "text": "SELECT c_year, c_date, c_datetime, c_timestamp, c_time FROM mysql_datetime_types LIMIT 1", + "text": "SELECT c_year, c_date, c_datetime, c_timestamp, c_time, c_timestamp_noda_instant_override FROM mysql_datetime_types LIMIT 1", "name": "GetMysqlDatetimeTypes", "cmd": ":one", "columns": [ @@ -3229,6 +3254,17 @@ "name": "time" }, "originalName": "c_time" + }, + { + "name": "c_timestamp_noda_instant_override", + "length": 19, + "table": { + "name": "mysql_datetime_types" + }, + "type": { + "name": "timestamp" + }, + "originalName": "c_timestamp_noda_instant_override" } ], "filename": "query.sql" @@ -3771,5 +3807,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6Ik15U3FsQ29ubmVjdG9yRGFwcGVyRXhhbXBsZUdlbiIsInVzZURhcHBlciI6dHJ1ZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwidXNlTm9kYVRpbWUiOmZhbHNlLCJvdmVycmlkZXMiOlt7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF9pbnQiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdGltZXN0YW1wIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6dHJ1ZX19LHsiY29sdW1uIjoiKjpjX2pzb25fc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6Ik15U3FsQ29ubmVjdG9yRGFwcGVyRXhhbXBsZUdlbiIsInVzZURhcHBlciI6dHJ1ZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwidXNlTm9kYVRpbWUiOmZhbHNlLCJvdmVycmlkZXMiOlt7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF9pbnQiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdGltZXN0YW1wIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6dHJ1ZX19LHsiY29sdW1uIjoiKjpjX2pzb25fc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfdGltZXN0YW1wX25vZGFfaW5zdGFudF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJJbnN0YW50Iiwibm90TnVsbCI6ZmFsc2V9fV0sImRlYnVnUmVxdWVzdCI6ZmFsc2V9" } \ No newline at end of file diff --git a/examples/MySqlConnectorDapperExample/request.message b/examples/MySqlConnectorDapperExample/request.message index 7a9cb19ed8ddf920aa92411285d549f0bf249dcd..a97dd9c1c3550caafb09af43ab5f023bb7eba7ff 100644 GIT binary patch delta 543 zcmZ2=lJVnNMt-h~Y+Q^+Lae!!#f3Ri8WR)cCh9ixE@I_UNv%lCEyzhN)}JiTD9tUz zmRy{XSX3Z&n`PtU(~OgUG4d#DStZApWag$8mjG49=jEp)#%JaMIe8`V`DLj^MVTq7 zlM5I%**zhGlUFl&@LUoXVk;<3%E?Stda?OGlPNp%6DF?79|Oe~`*AU<3VCrU5;pT) zp!#M%?n@4AZ&|t4Fmg>U@Jm1Wi|s^nl3DkZ`?1L4UJeH16_ z2k#}a=O>F!o}3~M0N`=Q>;M1& delta 176 zcmV;h08jt%%>k;(0S^lA1quN&5(RB}b8&1MD3M_vku8G_zyt~;Wq4t2aBO9BFOweu z8w(N!V{>R>a&Q{?1F_@F0h15|MGS@)5(aQ}Vr*$+BAl~f12qQ&m;wrukqZ~2unGYL z8i)f5lOYThvlR@vKm^DH3WAgHRuq$HQV)~$Oh%I`P#d#=O^pGwh);I{1hWGQSd#-% eHnUt(Z~>ExRt&R8R00qJ#00ZTWGw=d+GZDhDLB{w diff --git a/examples/MySqlConnectorDapperLegacyExample/Models.cs b/examples/MySqlConnectorDapperLegacyExample/Models.cs index ed69a748..7ef2a24a 100644 --- a/examples/MySqlConnectorDapperLegacyExample/Models.cs +++ b/examples/MySqlConnectorDapperLegacyExample/Models.cs @@ -1,6 +1,8 @@ // auto-generated by sqlc - do not edit namespace MySqlConnectorDapperLegacyExampleGen { + using NodaTime; + using NodaTime.Extensions; using System; using System.Collections.Generic; using System.Linq; @@ -59,6 +61,7 @@ public class MysqlDatetimeType public DateTime? CDatetime { get; set; } public DateTime? CTimestamp { get; set; } public TimeSpan? CTime { get; set; } + public DateTime? CTimestampNodaInstantOverride { get; set; } }; public class MysqlBinaryType { diff --git a/examples/MySqlConnectorDapperLegacyExample/QuerySql.cs b/examples/MySqlConnectorDapperLegacyExample/QuerySql.cs index d196b9ff..754ae049 100644 --- a/examples/MySqlConnectorDapperLegacyExample/QuerySql.cs +++ b/examples/MySqlConnectorDapperLegacyExample/QuerySql.cs @@ -11,6 +11,8 @@ namespace MySqlConnectorDapperLegacyExampleGen using CsvHelper.TypeConversion; using Dapper; using MySqlConnector; + using NodaTime; + using NodaTime.Extensions; using System; using System.Collections.Generic; using System.Globalization; @@ -952,7 +954,7 @@ public async Task TruncateMysqlStringTypes() await this.Transaction.Connection.ExecuteAsync(TruncateMysqlStringTypesSql, transaction: this.Transaction); } - private const string InsertMysqlDatetimeTypesSql = " INSERT INTO mysql_datetime_types ( c_year, c_date, c_datetime, c_timestamp, c_time ) VALUES (@c_year, @c_date, @c_datetime, @c_timestamp, @c_time)"; + private const string InsertMysqlDatetimeTypesSql = " INSERT INTO mysql_datetime_types ( c_year, c_date, c_datetime, c_timestamp, c_time, c_timestamp_noda_instant_override ) VALUES (@c_year, @c_date, @c_datetime, @c_timestamp, @c_time, @c_timestamp_noda_instant_override)"; public class InsertMysqlDatetimeTypesArgs { public short? CYear { get; set; } @@ -960,6 +962,7 @@ public class InsertMysqlDatetimeTypesArgs public DateTime? CDatetime { get; set; } public DateTime? CTimestamp { get; set; } public TimeSpan? CTime { get; set; } + public Instant? CTimestampNodaInstantOverride { get; set; } }; public async Task InsertMysqlDatetimeTypes(InsertMysqlDatetimeTypesArgs args) { @@ -969,6 +972,7 @@ public async Task InsertMysqlDatetimeTypes(InsertMysqlDatetimeTypesArgs args) queryParams.Add("c_datetime", args.CDatetime); queryParams.Add("c_timestamp", args.CTimestamp); queryParams.Add("c_time", args.CTime); + queryParams.Add("c_timestamp_noda_instant_override", args.CTimestampNodaInstantOverride is null ? null : (DateTime? )DateTime.SpecifyKind(args.CTimestampNodaInstantOverride.Value.ToDateTimeUtc(), DateTimeKind.Unspecified)); if (this.Transaction == null) { using (var connection = new MySqlConnection(ConnectionString)) @@ -1036,7 +1040,7 @@ public async Task InsertMysqlDatetimeTypesBatch(List GetMysqlDatetimeTypes() { diff --git a/examples/MySqlConnectorDapperLegacyExample/Utils.cs b/examples/MySqlConnectorDapperLegacyExample/Utils.cs index 1ab285b0..f77d7ec7 100644 --- a/examples/MySqlConnectorDapperLegacyExample/Utils.cs +++ b/examples/MySqlConnectorDapperLegacyExample/Utils.cs @@ -5,6 +5,9 @@ namespace MySqlConnectorDapperLegacyExampleGen using CsvHelper.Configuration; using CsvHelper.TypeConversion; using Dapper; + using NodaTime; + using NodaTime.Extensions; + using System; using System.Collections.Generic; using System.Data; using System.Linq; @@ -12,6 +15,26 @@ namespace MySqlConnectorDapperLegacyExampleGen public static class Utils { + private class NodaInstantTypeHandler : SqlMapper.TypeHandler + { + public override Instant Parse(object value) + { + if (value is DateTime dt) + { + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); + return dt.ToInstant(); + } + + throw new DataException($"Cannot convert {value?.GetType()} to Instant"); + } + + public override void SetValue(IDbDataParameter parameter, Instant value) + { + parameter.Value = value; + } + } + private class JsonElementTypeHandler : SqlMapper.TypeHandler { public override JsonElement Parse(object value) @@ -29,6 +52,7 @@ public override void SetValue(IDbDataParameter parameter, JsonElement value) public static void ConfigureSqlMapper() { + SqlMapper.AddTypeHandler(typeof(Instant), new NodaInstantTypeHandler()); SqlMapper.AddTypeHandler(typeof(JsonElement), new JsonElementTypeHandler()); SqlMapper.AddTypeHandler(typeof(HashSet), new BiosAuthorTypeTypeHandler()); SqlMapper.AddTypeHandler(typeof(HashSet), new MysqlStringTypesCSetTypeHandler()); diff --git a/examples/MySqlConnectorDapperLegacyExample/request.json b/examples/MySqlConnectorDapperLegacyExample/request.json index aff66a41..83dfad9f 100644 --- a/examples/MySqlConnectorDapperLegacyExample/request.json +++ b/examples/MySqlConnectorDapperLegacyExample/request.json @@ -13,7 +13,7 @@ "codegen": { "out": "examples/MySqlConnectorDapperLegacyExample", "plugin": "csharp", - "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JEYXBwZXJMZWdhY3lFeGFtcGxlR2VuIiwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJpbnQifX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOnRydWUsInR5cGUiOiJEYXRlVGltZSJ9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19XSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJ1c2VEYXBwZXIiOnRydWV9", + "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JEYXBwZXJMZWdhY3lFeGFtcGxlR2VuIiwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJpbnQifX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOnRydWUsInR5cGUiOiJEYXRlVGltZSJ9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiKjpjX3RpbWVzdGFtcF9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJub3ROdWxsIjpmYWxzZSwidHlwZSI6Ikluc3RhbnQifX1dLCJ0YXJnZXRGcmFtZXdvcmsiOiJuZXRzdGFuZGFyZDIuMCIsInVzZURhcHBlciI6dHJ1ZX0=", "process": { "cmd": "./dist/LocalRunner" } @@ -452,6 +452,16 @@ "type": { "name": "time" } + }, + { + "name": "c_timestamp_noda_instant_override", + "length": 19, + "table": { + "name": "mysql_datetime_types" + }, + "type": { + "name": "timestamp" + } } ] }, @@ -2996,7 +3006,7 @@ "filename": "query.sql" }, { - "text": "\nINSERT INTO mysql_datetime_types \n(\n c_year,\n c_date,\n c_datetime,\n c_timestamp,\n c_time\n) \nVALUES (?, ?, ?, ?, ?)", + "text": "\nINSERT INTO mysql_datetime_types \n(\n c_year,\n c_date,\n c_datetime,\n c_timestamp,\n c_time,\n c_timestamp_noda_instant_override\n) \nVALUES (?, ?, ?, ?, ?, ?)", "name": "InsertMysqlDatetimeTypes", "cmd": ":exec", "parameters": [ @@ -3074,6 +3084,21 @@ }, "originalName": "c_time" } + }, + { + "number": 6, + "column": { + "name": "c_timestamp_noda_instant_override", + "length": 19, + "table": { + "schema": "public", + "name": "mysql_datetime_types" + }, + "type": { + "name": "timestamp" + }, + "originalName": "c_timestamp_noda_instant_override" + } } ], "comments": [ @@ -3171,7 +3196,7 @@ } }, { - "text": "SELECT c_year, c_date, c_datetime, c_timestamp, c_time FROM mysql_datetime_types LIMIT 1", + "text": "SELECT c_year, c_date, c_datetime, c_timestamp, c_time, c_timestamp_noda_instant_override FROM mysql_datetime_types LIMIT 1", "name": "GetMysqlDatetimeTypes", "cmd": ":one", "columns": [ @@ -3229,6 +3254,17 @@ "name": "time" }, "originalName": "c_time" + }, + { + "name": "c_timestamp_noda_instant_override", + "length": 19, + "table": { + "name": "mysql_datetime_types" + }, + "type": { + "name": "timestamp" + }, + "originalName": "c_timestamp_noda_instant_override" } ], "filename": "query.sql" @@ -3771,5 +3807,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JEYXBwZXJMZWdhY3lFeGFtcGxlR2VuIiwidXNlRGFwcGVyIjp0cnVlLCJvdmVycmlkZURhcHBlclZlcnNpb24iOiIiLCJ1c2VOb2RhVGltZSI6ZmFsc2UsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X2ludCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJpbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3ZhcmNoYXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF90aW1lc3RhbXAiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjp0cnVlfX0seyJjb2x1bW4iOiIqOmNfanNvbl9zdHJpbmdfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fV0sImRlYnVnUmVxdWVzdCI6ZmFsc2V9" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JEYXBwZXJMZWdhY3lFeGFtcGxlR2VuIiwidXNlRGFwcGVyIjp0cnVlLCJvdmVycmlkZURhcHBlclZlcnNpb24iOiIiLCJ1c2VOb2RhVGltZSI6ZmFsc2UsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X2ludCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJpbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3ZhcmNoYXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF90aW1lc3RhbXAiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjp0cnVlfX0seyJjb2x1bW4iOiIqOmNfanNvbl9zdHJpbmdfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190aW1lc3RhbXBfbm9kYV9pbnN0YW50X292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6Ikluc3RhbnQiLCJub3ROdWxsIjpmYWxzZX19XSwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" } \ No newline at end of file diff --git a/examples/MySqlConnectorDapperLegacyExample/request.message b/examples/MySqlConnectorDapperLegacyExample/request.message index d507c9657a385a5e38d608ff501371f7871fa6d3..c83fe603dc1238d44ddde05072552f872f50f258 100644 GIT binary patch delta 529 zcmX?el5z4mMt-iRY+Q^+Lae!!#f3Ri8WR)cCh9ixZe!)rO07uDEyzhN)}QUT3iB@j?c?aNsQ0T19I|8Cf73=v3o+<+nEA*E{O}V6_h6B zWF{-U*euL!%Fg_RiEFZdp!nh>E=Cn0FD}L8c=6U$K+uIkB00?agZ6bN}CRlzOD-&bKWqp!$jk-#uU6{TFlj)D4{mk9S{ z2Js6pZDHM9m1NDNrcg delta 143 zcmV;A0C4}4&H>EH0S^j;1_}W(5(RB}b8&1MD3M_vku8G))C7^TH35gQ=+XfJU6YVx zC6ht}Ck%!c5(aQ}Vr*$+BAl~z12qQ&m;wru!BrQd#0mkk5Dd~l1jqymf|KS? CSet); -public readonly record struct MysqlDatetimeType(short? CYear, DateTime? CDate, DateTime? CDatetime, DateTime? CTimestamp, TimeSpan? CTime); +public readonly record struct MysqlDatetimeType(short? CYear, DateTime? CDate, DateTime? CDatetime, DateTime? CTimestamp, TimeSpan? CTime, DateTime? CTimestampNodaInstantOverride); public readonly record struct MysqlBinaryType(byte? CBit, byte[]? CBinary, byte[]? CVarbinary, byte[]? CTinyblob, byte[]? CBlob, byte[]? CMediumblob, byte[]? CLongblob); public readonly record struct ExtendedBio(string? AuthorName, string? Name, BiosBioType? BioType, HashSet? AuthorType); public enum BiosBioType diff --git a/examples/MySqlConnectorExample/QuerySql.cs b/examples/MySqlConnectorExample/QuerySql.cs index 0caaf50b..ea54a03d 100644 --- a/examples/MySqlConnectorExample/QuerySql.cs +++ b/examples/MySqlConnectorExample/QuerySql.cs @@ -8,6 +8,8 @@ using CsvHelper.Configuration; using CsvHelper.TypeConversion; using MySqlConnector; +using NodaTime; +using NodaTime.Extensions; using System; using System.Collections.Generic; using System.Globalization; @@ -1312,8 +1314,8 @@ public async Task TruncateMysqlStringTypes() } } - private const string InsertMysqlDatetimeTypesSql = " INSERT INTO mysql_datetime_types ( c_year, c_date, c_datetime, c_timestamp, c_time ) VALUES (@c_year, @c_date, @c_datetime, @c_timestamp, @c_time)"; - public readonly record struct InsertMysqlDatetimeTypesArgs(short? CYear, DateTime? CDate, DateTime? CDatetime, DateTime? CTimestamp, TimeSpan? CTime); + private const string InsertMysqlDatetimeTypesSql = " INSERT INTO mysql_datetime_types ( c_year, c_date, c_datetime, c_timestamp, c_time, c_timestamp_noda_instant_override ) VALUES (@c_year, @c_date, @c_datetime, @c_timestamp, @c_time, @c_timestamp_noda_instant_override)"; + public readonly record struct InsertMysqlDatetimeTypesArgs(short? CYear, DateTime? CDate, DateTime? CDatetime, DateTime? CTimestamp, TimeSpan? CTime, Instant? CTimestampNodaInstantOverride); public async Task InsertMysqlDatetimeTypes(InsertMysqlDatetimeTypesArgs args) { if (this.Transaction == null) @@ -1328,6 +1330,7 @@ public async Task InsertMysqlDatetimeTypes(InsertMysqlDatetimeTypesArgs args) command.Parameters.AddWithValue("@c_datetime", args.CDatetime ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_timestamp", args.CTimestamp ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_time", args.CTime ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", args.CTimestampNodaInstantOverride is null ? (object)DBNull.Value : (DateTime? )DateTime.SpecifyKind(args.CTimestampNodaInstantOverride.Value.ToDateTimeUtc(), DateTimeKind.Unspecified)); await command.ExecuteNonQueryAsync(); } } @@ -1346,6 +1349,7 @@ public async Task InsertMysqlDatetimeTypes(InsertMysqlDatetimeTypesArgs args) command.Parameters.AddWithValue("@c_datetime", args.CDatetime ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_timestamp", args.CTimestamp ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_time", args.CTime ?? (object)DBNull.Value); + command.Parameters.AddWithValue("@c_timestamp_noda_instant_override", args.CTimestampNodaInstantOverride is null ? (object)DBNull.Value : (DateTime? )DateTime.SpecifyKind(args.CTimestampNodaInstantOverride.Value.ToDateTimeUtc(), DateTimeKind.Unspecified)); await command.ExecuteNonQueryAsync(); } } @@ -1398,8 +1402,8 @@ public async Task InsertMysqlDatetimeTypesBatch(List GetMysqlDatetimeTypes() { if (this.Transaction == null) @@ -1419,7 +1423,14 @@ public async Task InsertMysqlDatetimeTypesBatch(List(4) + CTime = reader.IsDBNull(4) ? null : reader.GetFieldValue(4), + CTimestampNodaInstantOverride = reader.IsDBNull(5) ? null : (new Func((r, o) => + { + var dt = reader.GetDateTime(o); + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); + return dt.ToInstant(); + }))(reader, 5) }; } } @@ -1445,7 +1456,14 @@ public async Task InsertMysqlDatetimeTypesBatch(List(4) + CTime = reader.IsDBNull(4) ? null : reader.GetFieldValue(4), + CTimestampNodaInstantOverride = reader.IsDBNull(5) ? null : (new Func((r, o) => + { + var dt = reader.GetDateTime(o); + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); + return dt.ToInstant(); + }))(reader, 5) }; } } diff --git a/examples/MySqlConnectorExample/request.json b/examples/MySqlConnectorExample/request.json index 38d6d266..d2143afb 100644 --- a/examples/MySqlConnectorExample/request.json +++ b/examples/MySqlConnectorExample/request.json @@ -13,7 +13,7 @@ "codegen": { "out": "examples/MySqlConnectorExample", "plugin": "csharp", - "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JFeGFtcGxlR2VuIiwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJpbnQifX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOnRydWUsInR5cGUiOiJEYXRlVGltZSJ9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19XSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwidXNlRGFwcGVyIjpmYWxzZX0=", + "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JFeGFtcGxlR2VuIiwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJpbnQifX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOnRydWUsInR5cGUiOiJEYXRlVGltZSJ9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiKjpjX3RpbWVzdGFtcF9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJub3ROdWxsIjpmYWxzZSwidHlwZSI6Ikluc3RhbnQifX1dLCJ0YXJnZXRGcmFtZXdvcmsiOiJuZXQ4LjAiLCJ1c2VEYXBwZXIiOmZhbHNlfQ==", "process": { "cmd": "./dist/LocalRunner" } @@ -452,6 +452,16 @@ "type": { "name": "time" } + }, + { + "name": "c_timestamp_noda_instant_override", + "length": 19, + "table": { + "name": "mysql_datetime_types" + }, + "type": { + "name": "timestamp" + } } ] }, @@ -2996,7 +3006,7 @@ "filename": "query.sql" }, { - "text": "\nINSERT INTO mysql_datetime_types \n(\n c_year,\n c_date,\n c_datetime,\n c_timestamp,\n c_time\n) \nVALUES (?, ?, ?, ?, ?)", + "text": "\nINSERT INTO mysql_datetime_types \n(\n c_year,\n c_date,\n c_datetime,\n c_timestamp,\n c_time,\n c_timestamp_noda_instant_override\n) \nVALUES (?, ?, ?, ?, ?, ?)", "name": "InsertMysqlDatetimeTypes", "cmd": ":exec", "parameters": [ @@ -3074,6 +3084,21 @@ }, "originalName": "c_time" } + }, + { + "number": 6, + "column": { + "name": "c_timestamp_noda_instant_override", + "length": 19, + "table": { + "schema": "public", + "name": "mysql_datetime_types" + }, + "type": { + "name": "timestamp" + }, + "originalName": "c_timestamp_noda_instant_override" + } } ], "comments": [ @@ -3171,7 +3196,7 @@ } }, { - "text": "SELECT c_year, c_date, c_datetime, c_timestamp, c_time FROM mysql_datetime_types LIMIT 1", + "text": "SELECT c_year, c_date, c_datetime, c_timestamp, c_time, c_timestamp_noda_instant_override FROM mysql_datetime_types LIMIT 1", "name": "GetMysqlDatetimeTypes", "cmd": ":one", "columns": [ @@ -3229,6 +3254,17 @@ "name": "time" }, "originalName": "c_time" + }, + { + "name": "c_timestamp_noda_instant_override", + "length": 19, + "table": { + "name": "mysql_datetime_types" + }, + "type": { + "name": "timestamp" + }, + "originalName": "c_timestamp_noda_instant_override" } ], "filename": "query.sql" @@ -3771,5 +3807,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6Ik15U3FsQ29ubmVjdG9yRXhhbXBsZUdlbiIsInVzZURhcHBlciI6ZmFsc2UsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsInVzZU5vZGFUaW1lIjpmYWxzZSwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOnRydWV9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19XSwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6Ik15U3FsQ29ubmVjdG9yRXhhbXBsZUdlbiIsInVzZURhcHBlciI6ZmFsc2UsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsInVzZU5vZGFUaW1lIjpmYWxzZSwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOnRydWV9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RpbWVzdGFtcF9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSW5zdGFudCIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" } \ No newline at end of file diff --git a/examples/MySqlConnectorExample/request.message b/examples/MySqlConnectorExample/request.message index 216298c63c4aaeb8656122bf8601e819cc1405b5..47e27a7fa57b193b4cdf4a00b3432d82915392f1 100644 GIT binary patch delta 499 zcmbPrlJVhLMt-hiY+Q^+Lae!!#f3Ri8WR)cCh9gbO=q3BNt5Xs%f`D$87IGE{ zN{%nd%uOvWNz5&X&&y9qjL*yia`H+hr!yI`dqUasnLK$ei3_n6lqTh5CM&(z{DsMs zo%sn9*JOi0@x{(uj4DE2T#C4iiq9`gEh@@PnY=JiX7ay49u}z%X0FMOv7(z}xOY0R zyk+HDGbvPLvaV0)kOp0S^k~1quN&5(RB}b8&1MD3M_vku8G)wFHr}DFXBZvE9W1lLP}s z42BmH25@y^Y-wX6oU>K~H3tKj0t%Dx3KyfL3IVh63(`OZ$OH<40h8f46O-FaRg)i3 x8?$vyjRCWLPj> GetMysqlDatetimeTypes() { @@ -1667,7 +1673,14 @@ public async Task GetMysqlDatetimeTypes() CDate = reader.IsDBNull(1) ? (DateTime? )null : reader.GetDateTime(1), CDatetime = reader.IsDBNull(2) ? (DateTime? )null : reader.GetDateTime(2), CTimestamp = reader.IsDBNull(3) ? (DateTime? )null : reader.GetDateTime(3), - CTime = reader.IsDBNull(4) ? (TimeSpan? )null : reader.GetFieldValue(4) + CTime = reader.IsDBNull(4) ? (TimeSpan? )null : reader.GetFieldValue(4), + CTimestampNodaInstantOverride = reader.IsDBNull(5) ? (Instant? )null : (new Func((r, o) => + { + var dt = reader.GetDateTime(o); + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); + return dt.ToInstant(); + }))(reader, 5) }; } } @@ -1693,7 +1706,14 @@ public async Task GetMysqlDatetimeTypes() CDate = reader.IsDBNull(1) ? (DateTime? )null : reader.GetDateTime(1), CDatetime = reader.IsDBNull(2) ? (DateTime? )null : reader.GetDateTime(2), CTimestamp = reader.IsDBNull(3) ? (DateTime? )null : reader.GetDateTime(3), - CTime = reader.IsDBNull(4) ? (TimeSpan? )null : reader.GetFieldValue(4) + CTime = reader.IsDBNull(4) ? (TimeSpan? )null : reader.GetFieldValue(4), + CTimestampNodaInstantOverride = reader.IsDBNull(5) ? (Instant? )null : (new Func((r, o) => + { + var dt = reader.GetDateTime(o); + if (dt.Kind != DateTimeKind.Utc) + dt = DateTime.SpecifyKind(dt, DateTimeKind.Utc); + return dt.ToInstant(); + }))(reader, 5) }; } } diff --git a/examples/MySqlConnectorLegacyExample/request.json b/examples/MySqlConnectorLegacyExample/request.json index 24f79ce3..4a274882 100644 --- a/examples/MySqlConnectorLegacyExample/request.json +++ b/examples/MySqlConnectorLegacyExample/request.json @@ -13,7 +13,7 @@ "codegen": { "out": "examples/MySqlConnectorLegacyExample", "plugin": "csharp", - "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JMZWdhY3lFeGFtcGxlR2VuIiwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJpbnQifX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOnRydWUsInR5cGUiOiJEYXRlVGltZSJ9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19XSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJ1c2VEYXBwZXIiOmZhbHNlfQ==", + "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JMZWdhY3lFeGFtcGxlR2VuIiwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfaW50IiwiY3NoYXJwX3R5cGUiOnsibm90TnVsbCI6ZmFsc2UsInR5cGUiOiJpbnQifX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiR2V0TXlzcWxGdW5jdGlvbnM6bWF4X3RpbWVzdGFtcCIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOnRydWUsInR5cGUiOiJEYXRlVGltZSJ9fSx7ImNvbHVtbiI6Iio6Y19qc29uX3N0cmluZ19vdmVycmlkZSIsImNzaGFycF90eXBlIjp7Im5vdE51bGwiOmZhbHNlLCJ0eXBlIjoic3RyaW5nIn19LHsiY29sdW1uIjoiKjpjX3RpbWVzdGFtcF9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJub3ROdWxsIjpmYWxzZSwidHlwZSI6Ikluc3RhbnQifX1dLCJ0YXJnZXRGcmFtZXdvcmsiOiJuZXRzdGFuZGFyZDIuMCIsInVzZURhcHBlciI6ZmFsc2V9", "process": { "cmd": "./dist/LocalRunner" } @@ -452,6 +452,16 @@ "type": { "name": "time" } + }, + { + "name": "c_timestamp_noda_instant_override", + "length": 19, + "table": { + "name": "mysql_datetime_types" + }, + "type": { + "name": "timestamp" + } } ] }, @@ -2996,7 +3006,7 @@ "filename": "query.sql" }, { - "text": "\nINSERT INTO mysql_datetime_types \n(\n c_year,\n c_date,\n c_datetime,\n c_timestamp,\n c_time\n) \nVALUES (?, ?, ?, ?, ?)", + "text": "\nINSERT INTO mysql_datetime_types \n(\n c_year,\n c_date,\n c_datetime,\n c_timestamp,\n c_time,\n c_timestamp_noda_instant_override\n) \nVALUES (?, ?, ?, ?, ?, ?)", "name": "InsertMysqlDatetimeTypes", "cmd": ":exec", "parameters": [ @@ -3074,6 +3084,21 @@ }, "originalName": "c_time" } + }, + { + "number": 6, + "column": { + "name": "c_timestamp_noda_instant_override", + "length": 19, + "table": { + "schema": "public", + "name": "mysql_datetime_types" + }, + "type": { + "name": "timestamp" + }, + "originalName": "c_timestamp_noda_instant_override" + } } ], "comments": [ @@ -3171,7 +3196,7 @@ } }, { - "text": "SELECT c_year, c_date, c_datetime, c_timestamp, c_time FROM mysql_datetime_types LIMIT 1", + "text": "SELECT c_year, c_date, c_datetime, c_timestamp, c_time, c_timestamp_noda_instant_override FROM mysql_datetime_types LIMIT 1", "name": "GetMysqlDatetimeTypes", "cmd": ":one", "columns": [ @@ -3229,6 +3254,17 @@ "name": "time" }, "originalName": "c_time" + }, + { + "name": "c_timestamp_noda_instant_override", + "length": 19, + "table": { + "name": "mysql_datetime_types" + }, + "type": { + "name": "timestamp" + }, + "originalName": "c_timestamp_noda_instant_override" } ], "filename": "query.sql" @@ -3771,5 +3807,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JMZWdhY3lFeGFtcGxlR2VuIiwidXNlRGFwcGVyIjpmYWxzZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwidXNlTm9kYVRpbWUiOmZhbHNlLCJvdmVycmlkZXMiOlt7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF9pbnQiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdGltZXN0YW1wIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6dHJ1ZX19LHsiY29sdW1uIjoiKjpjX2pzb25fc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiTXlTcWxDb25uZWN0b3JMZWdhY3lFeGFtcGxlR2VuIiwidXNlRGFwcGVyIjpmYWxzZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwidXNlTm9kYVRpbWUiOmZhbHNlLCJvdmVycmlkZXMiOlt7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF9pbnQiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldE15c3FsRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRNeXNxbEZ1bmN0aW9uczptYXhfdGltZXN0YW1wIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6dHJ1ZX19LHsiY29sdW1uIjoiKjpjX2pzb25fc3RyaW5nX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfdGltZXN0YW1wX25vZGFfaW5zdGFudF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJJbnN0YW50Iiwibm90TnVsbCI6ZmFsc2V9fV0sImRlYnVnUmVxdWVzdCI6ZmFsc2V9" } \ No newline at end of file diff --git a/examples/MySqlConnectorLegacyExample/request.message b/examples/MySqlConnectorLegacyExample/request.message index 5301c5388af3c3aabd1079bab02ab5e2bc9040e6..27b0ad87d207cd1ddd186554dc8f69c36b8e9cf9 100644 GIT binary patch delta 551 zcmdmUlCk+5BR|(IHZDdZA=cc=;=&v$jfshJ6Lp(;SF>`dq*f&67UZNB>ra+vl;#p* zOD@hxEGm$CvhmRw#>u}Jd8D+glH*G3GyGxLC)ypqXTDbkbsn8dj~ zA$+CU+Sthpl2j*OVbb8aBre2OP@0sJnXL3;GY7LNJM$AJuE~vo;)}z%7}bTmxD;_2 z8=qg6T2z#ol4>A4c_EkNWO;5L7O4(quE_^^L^l_3?{r{!%gVK8vaV0&zy2^A+veCPd}r!RwW0UP$_ZNB?c&htW&BY=(x?ceickCM_IV4C+`d}Q_@i&*o9R>a&Q`gvEs}DlMn+=42BmH25@y^Y-wX6oU>{JH3tEhv!DtY0R$R|0}7Kt zVHL9;47orA$OH<4liN&blQU2ovx!ZO0ke@$cLD^n0}5D^3{o})AVyM8O_Q-!6|;X* WRspj_R1OdV%>=VlWHthm>}D6FH8vCg diff --git a/examples/config/mysql/types/query.sql b/examples/config/mysql/types/query.sql index de837a17..1b57d41d 100644 --- a/examples/config/mysql/types/query.sql +++ b/examples/config/mysql/types/query.sql @@ -169,9 +169,10 @@ INSERT INTO mysql_datetime_types c_date, c_datetime, c_timestamp, - c_time + c_time, + c_timestamp_noda_instant_override ) -VALUES (?, ?, ?, ?, ?); +VALUES (?, ?, ?, ?, ?, ?); -- name: InsertMysqlDatetimeTypesBatch :copyfrom INSERT INTO mysql_datetime_types diff --git a/examples/config/mysql/types/schema.sql b/examples/config/mysql/types/schema.sql index e5755cf5..4758e9c8 100644 --- a/examples/config/mysql/types/schema.sql +++ b/examples/config/mysql/types/schema.sql @@ -32,11 +32,12 @@ CREATE TABLE mysql_string_types ( ); CREATE TABLE mysql_datetime_types ( - c_year YEAR, - c_date DATE, - c_datetime DATETIME, - c_timestamp TIMESTAMP, - c_time TIME + c_year YEAR, + c_date DATE, + c_datetime DATETIME, + c_timestamp TIMESTAMP, + c_time TIME, + c_timestamp_noda_instant_override TIMESTAMP ); CREATE TABLE mysql_binary_types ( diff --git a/sqlc.ci.yaml b/sqlc.ci.yaml index 2cf7643c..0bfc924c 100644 --- a/sqlc.ci.yaml +++ b/sqlc.ci.yaml @@ -228,6 +228,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false - schema: ["examples/config/mysql/authors/schema.sql", "examples/config/mysql/types/schema.sql"] queries: ["examples/config/mysql/authors/query.sql", "examples/config/mysql/types/query.sql"] engine: "mysql" @@ -256,6 +260,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false - schema: ["examples/config/mysql/authors/schema.sql", "examples/config/mysql/types/schema.sql"] queries: ["examples/config/mysql/authors/query.sql", "examples/config/mysql/types/query.sql"] engine: "mysql" @@ -284,6 +292,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false - schema: ["examples/config/mysql/authors/schema.sql", "examples/config/mysql/types/schema.sql"] queries: ["examples/config/mysql/authors/query.sql", "examples/config/mysql/types/query.sql"] engine: "mysql" @@ -312,6 +324,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false # Sqlite - schema: ["examples/config/sqlite/authors/schema.sql", "examples/config/sqlite/types/schema.sql"] diff --git a/sqlc.local.generated.yaml b/sqlc.local.generated.yaml index 0778288c..643a8461 100644 --- a/sqlc.local.generated.yaml +++ b/sqlc.local.generated.yaml @@ -226,6 +226,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false - schema: ["examples/config/mysql/authors/schema.sql", "examples/config/mysql/types/schema.sql"] queries: ["examples/config/mysql/authors/query.sql", "examples/config/mysql/types/query.sql"] engine: "mysql" @@ -254,6 +258,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false - schema: ["examples/config/mysql/authors/schema.sql", "examples/config/mysql/types/schema.sql"] queries: ["examples/config/mysql/authors/query.sql", "examples/config/mysql/types/query.sql"] engine: "mysql" @@ -282,6 +290,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false - schema: ["examples/config/mysql/authors/schema.sql", "examples/config/mysql/types/schema.sql"] queries: ["examples/config/mysql/authors/query.sql", "examples/config/mysql/types/query.sql"] engine: "mysql" @@ -310,6 +322,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false # Sqlite - schema: ["examples/config/sqlite/authors/schema.sql", "examples/config/sqlite/types/schema.sql"] queries: ["examples/config/sqlite/authors/query.sql", "examples/config/sqlite/types/query.sql"] diff --git a/sqlc.request.generated.yaml b/sqlc.request.generated.yaml index 5275c236..d59839cc 100644 --- a/sqlc.request.generated.yaml +++ b/sqlc.request.generated.yaml @@ -230,6 +230,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false debugRequest: true - schema: ["examples/config/mysql/authors/schema.sql", "examples/config/mysql/types/schema.sql"] queries: ["examples/config/mysql/authors/query.sql", "examples/config/mysql/types/query.sql"] @@ -259,6 +263,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false debugRequest: true - schema: ["examples/config/mysql/authors/schema.sql", "examples/config/mysql/types/schema.sql"] queries: ["examples/config/mysql/authors/query.sql", "examples/config/mysql/types/query.sql"] @@ -288,6 +296,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false debugRequest: true - schema: ["examples/config/mysql/authors/schema.sql", "examples/config/mysql/types/schema.sql"] queries: ["examples/config/mysql/authors/query.sql", "examples/config/mysql/types/query.sql"] @@ -317,6 +329,10 @@ sql: csharp_type: type: "string" notNull: false + - column: "*:c_timestamp_noda_instant_override" + csharp_type: + type: "Instant" + notNull: false debugRequest: true # Sqlite - schema: ["examples/config/sqlite/authors/schema.sql", "examples/config/sqlite/types/schema.sql"] From 6d6bbb1ba10b2b88abb317052a0055e04cd2ecb9 Mon Sep 17 00:00:00 2001 From: Ilan Uzan Date: Sat, 4 Oct 2025 00:14:11 +0200 Subject: [PATCH 4/6] fix: regenerate code --- end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs | 2 +- end2end/EndToEndTests/MySqlConnectorTester.generated.cs | 2 +- .../EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs | 2 +- end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs b/end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs index ee0dbacc..5be30570 100644 --- a/end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs +++ b/end2end/EndToEndTests/MySqlConnectorDapperTester.generated.cs @@ -523,7 +523,7 @@ private static IEnumerable MySqlDateTimeTypesTestCases { get { - yield return new TestCaseData((short)1999, DateTime.Parse("2000-1-30"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2010-1-30 08:11:00"), TimeSpan.Parse("02:01:22"), Instant.FromUtc(2025, 1, 1, 1, 1, 1)).SetName("DateTimeTypes with values"); + yield return new TestCaseData((short)1999, DateTime.Parse("2000-1-30"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2010-1-30 08:11:00"), TimeSpan.Parse("02:01:22"), Instant.FromUtc(2025, 10, 15, 19, 55, 2)).SetName("DateTimeTypes with values"); yield return new TestCaseData(null, null, null, null, null, null).SetName("DateTimeTypes with null values"); } } diff --git a/end2end/EndToEndTests/MySqlConnectorTester.generated.cs b/end2end/EndToEndTests/MySqlConnectorTester.generated.cs index 4c952627..1510db11 100644 --- a/end2end/EndToEndTests/MySqlConnectorTester.generated.cs +++ b/end2end/EndToEndTests/MySqlConnectorTester.generated.cs @@ -523,7 +523,7 @@ private static IEnumerable MySqlDateTimeTypesTestCases { get { - yield return new TestCaseData((short)1999, DateTime.Parse("2000-1-30"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2010-1-30 08:11:00"), TimeSpan.Parse("02:01:22"), Instant.FromUtc(2025, 1, 1, 1, 1, 1)).SetName("DateTimeTypes with values"); + yield return new TestCaseData((short)1999, DateTime.Parse("2000-1-30"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2010-1-30 08:11:00"), TimeSpan.Parse("02:01:22"), Instant.FromUtc(2025, 10, 15, 19, 55, 2)).SetName("DateTimeTypes with values"); yield return new TestCaseData(null, null, null, null, null, null).SetName("DateTimeTypes with null values"); } } diff --git a/end2end/EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs b/end2end/EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs index be3698cc..314d17a1 100644 --- a/end2end/EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/MySqlConnectorDapperTester.generated.cs @@ -523,7 +523,7 @@ private static IEnumerable MySqlDateTimeTypesTestCases { get { - yield return new TestCaseData((short)1999, DateTime.Parse("2000-1-30"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2010-1-30 08:11:00"), TimeSpan.Parse("02:01:22"), Instant.FromUtc(2025, 1, 1, 1, 1, 1)).SetName("DateTimeTypes with values"); + yield return new TestCaseData((short)1999, DateTime.Parse("2000-1-30"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2010-1-30 08:11:00"), TimeSpan.Parse("02:01:22"), Instant.FromUtc(2025, 10, 15, 19, 55, 2)).SetName("DateTimeTypes with values"); yield return new TestCaseData(null, null, null, null, null, null).SetName("DateTimeTypes with null values"); } } diff --git a/end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs b/end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs index d68b319e..16f149ec 100644 --- a/end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/MySqlConnectorTester.generated.cs @@ -523,7 +523,7 @@ private static IEnumerable MySqlDateTimeTypesTestCases { get { - yield return new TestCaseData((short)1999, DateTime.Parse("2000-1-30"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2010-1-30 08:11:00"), TimeSpan.Parse("02:01:22"), Instant.FromUtc(2025, 1, 1, 1, 1, 1)).SetName("DateTimeTypes with values"); + yield return new TestCaseData((short)1999, DateTime.Parse("2000-1-30"), DateTime.Parse("1983-11-3 02:01:22"), DateTime.Parse("2010-1-30 08:11:00"), TimeSpan.Parse("02:01:22"), Instant.FromUtc(2025, 10, 15, 19, 55, 2)).SetName("DateTimeTypes with values"); yield return new TestCaseData(null, null, null, null, null, null).SetName("DateTimeTypes with null values"); } } From f6a9b602128c99c0970da6a1d12a60aeb6452723 Mon Sep 17 00:00:00 2001 From: Ilan Uzan Date: Sun, 5 Oct 2025 00:49:27 +0200 Subject: [PATCH 5/6] feat: add option to override either integer or string to NodaTime.Instant in SQLite --- Drivers/DbDriver.cs | 2 +- Drivers/MySqlConnectorDriver.cs | 2 +- Drivers/NpgsqlDriver.cs | 2 +- Drivers/SqliteDriver.cs | 38 ++++++++ .../EndToEndScaffold/Templates/SqliteTests.cs | 70 ++++++++------- .../SqliteDapperTester.generated.cs | 47 +++++----- .../EndToEndTests/SqliteTester.generated.cs | 47 +++++----- .../SqliteDapperTester.generated.cs | 47 +++++----- .../SqliteTester.generated.cs | 47 +++++----- examples/SqliteDapperExample/Models.cs | 5 ++ examples/SqliteDapperExample/QuerySql.cs | 13 ++- examples/SqliteDapperExample/Utils.cs | 21 +++++ examples/SqliteDapperExample/request.json | 82 ++++++++++++++++-- examples/SqliteDapperExample/request.message | Bin 9812 -> 10872 bytes examples/SqliteDapperLegacyExample/Models.cs | 5 ++ .../SqliteDapperLegacyExample/QuerySql.cs | 13 ++- examples/SqliteDapperLegacyExample/Utils.cs | 21 +++++ .../SqliteDapperLegacyExample/request.json | 82 ++++++++++++++++-- .../SqliteDapperLegacyExample/request.message | Bin 9846 -> 10906 bytes examples/SqliteExample/Models.cs | 5 +- examples/SqliteExample/QuerySql.cs | 27 ++++-- examples/SqliteExample/request.json | 82 ++++++++++++++++-- examples/SqliteExample/request.message | Bin 9796 -> 10856 bytes examples/SqliteLegacyExample/Models.cs | 5 ++ examples/SqliteLegacyExample/QuerySql.cs | 27 ++++-- examples/SqliteLegacyExample/request.json | 82 ++++++++++++++++-- examples/SqliteLegacyExample/request.message | Bin 9830 -> 10890 bytes examples/config/sqlite/types/query.sql | 6 +- examples/config/sqlite/types/schema.sql | 2 + sqlc.ci.yaml | 26 +++++- sqlc.local.generated.yaml | 24 +++++ sqlc.request.generated.yaml | 24 +++++ 32 files changed, 673 insertions(+), 181 deletions(-) diff --git a/Drivers/DbDriver.cs b/Drivers/DbDriver.cs index a12d7dd8..42f7fa56 100644 --- a/Drivers/DbDriver.cs +++ b/Drivers/DbDriver.cs @@ -69,7 +69,7 @@ public static string TransformQueryForSliceArgs(string originalSql, int sliceSiz throw new InvalidOperationException("Transaction is provided, but its connection is null."); """; - protected static readonly SqlMapperImplFunc NodaInstantTypeHandler = _ => $$""" + protected static readonly SqlMapperImplFunc DateTimeNodaInstantTypeHandler = _ => $$""" private class NodaInstantTypeHandler : SqlMapper.TypeHandler { public override Instant Parse(object value) diff --git a/Drivers/MySqlConnectorDriver.cs b/Drivers/MySqlConnectorDriver.cs index e67ea08e..9c2666ef 100644 --- a/Drivers/MySqlConnectorDriver.cs +++ b/Drivers/MySqlConnectorDriver.cs @@ -144,7 +144,7 @@ public sealed partial class MySqlConnectorDriver( }, usingDirectives: ["System", "NodaTime", "NodaTime.Extensions"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(Instant), new NodaInstantTypeHandler());", - sqlMapperImpl: NodaInstantTypeHandler + sqlMapperImpl: DateTimeNodaInstantTypeHandler ), diff --git a/Drivers/NpgsqlDriver.cs b/Drivers/NpgsqlDriver.cs index 1edb7613..25b33b39 100644 --- a/Drivers/NpgsqlDriver.cs +++ b/Drivers/NpgsqlDriver.cs @@ -157,7 +157,7 @@ public NpgsqlDriver( }, usingDirectives: ["System", "NodaTime", "NodaTime.Extensions"], sqlMapper: "SqlMapper.AddTypeHandler(typeof(Instant), new NodaInstantTypeHandler());", - sqlMapperImpl: NodaInstantTypeHandler + sqlMapperImpl: DateTimeNodaInstantTypeHandler ), /* Unstructured data types */ diff --git a/Drivers/SqliteDriver.cs b/Drivers/SqliteDriver.cs index e13a7775..ce33c0b2 100644 --- a/Drivers/SqliteDriver.cs +++ b/Drivers/SqliteDriver.cs @@ -19,6 +19,25 @@ public sealed partial class SqliteDriver( private const string DateTimeStringFormat = "yyyy-MM-dd HH:mm:ss"; // Default format for DateTime strings - TODO make configurable via Options + private static readonly SqlMapperImplFunc NodaInstantTypeHandler = _ => $$""" + private class NodaInstantTypeHandler : SqlMapper.TypeHandler + { + public override Instant Parse(object value) + { + if (value is string s) + return InstantPattern.CreateWithInvariantCulture("{{DateTimeStringFormat}}").Parse(s).Value; + if (value is long l) + return Instant.FromUnixTimeSeconds(l); + throw new DataException($"Cannot convert {value?.GetType()} to Instant"); + } + + public override void SetValue(IDbDataParameter parameter, Instant value) + { + parameter.Value = value; + } + } + """; + protected override Dictionary ColumnMappings { get; } = new() { @@ -71,6 +90,25 @@ public sealed partial class SqliteDriver( sqlMapper: "SqlMapper.AddTypeHandler(typeof(DateTime), new DateTimeTypeHandler());", sqlMapperImpl: DateTimeTypeHandler ), + ["Instant"] = new( + [], + readerFn: (ordinal, dbType) => + { + if (IntegerDbTypes.Contains(dbType.ToLower())) + return $"Instant.FromUnixTimeSeconds({Variable.Reader.AsVarName()}.GetInt32({ordinal}))"; + return $"InstantPattern.CreateWithInvariantCulture(\"{DateTimeStringFormat}\").Parse({Variable.Reader.AsVarName()}.GetString({ordinal})).Value"; + }, + writerFn: (el, dbType, notNull, isDapper, isLegacy) => + { + var nullValue = isDapper ? "null" : "(object)DBNull.Value"; + if (IntegerDbTypes.Contains(dbType.ToLower())) + return $"{el} != null ? (long?) {el}.Value.ToUnixTimeSeconds() : {nullValue}"; + return $"{el} != null ? InstantPattern.CreateWithInvariantCulture(\"{DateTimeStringFormat}\").Format({el}.Value) : {nullValue}"; + }, + usingDirectives: ["NodaTime", "NodaTime.Extensions", "NodaTime.Text"], + sqlMapper: "SqlMapper.AddTypeHandler(typeof(Instant), new NodaInstantTypeHandler());", + sqlMapperImpl: NodaInstantTypeHandler + ), ["bool"] = new( [], readerFn: (ordinal, dbType) => diff --git a/end2end/EndToEndScaffold/Templates/SqliteTests.cs b/end2end/EndToEndScaffold/Templates/SqliteTests.cs index a6f6713f..2b264fae 100644 --- a/end2end/EndToEndScaffold/Templates/SqliteTests.cs +++ b/end2end/EndToEndScaffold/Templates/SqliteTests.cs @@ -9,10 +9,35 @@ public static class SqliteTests [KnownTestType.SqliteDataTypes] = new TestImpl { Impl = $$""" + private static IEnumerable SqliteTypesTestCases + { + get + { + yield return new TestCaseData( + -54355, + 9787.66m, + "Songs of Love and Hate", + new byte[] { 0x15, 0x20, 0x33 }, + true, + false, + DateTime.SpecifyKind(DateTime.Parse("2020-01-01 14:15:16"), DateTimeKind.Utc), + DateTime.SpecifyKind(DateTime.Parse("2025-01-01 17:18:19"), DateTimeKind.Utc), + Instant.FromUtc(2025, 10, 15, 19, 55, 2), + Instant.FromUtc(1993, 9, 27, 03, 55, 2) + ).SetName("SqliteTypes with values"); + + yield return new TestCaseData( + null, null, null, new byte[] { }, null, null, null, null, null, null + ).SetName("SqliteTypes with empty values"); + + yield return new TestCaseData( + null, null, null, null, null, null, null, null, null, null + ).SetName("SqliteTypes with null values"); + } + } + [Test] - [TestCase(-54355, 9787.66, "Songs of Love and Hate", new byte[] { 0x15, 0x20, 0x33 }, true, false, "2020-01-01 14:15:16", "2025-01-01 17:18:19")] - [TestCase(null, null, null, new byte[] { }, null, null, null, null)] - [TestCase(null, null, null, null, null, null, null, null)] + [TestCaseSource(nameof(SqliteTypesTestCases))] public async Task TestSqliteTypes( int? cInteger, decimal? cReal, @@ -21,13 +46,10 @@ public async Task TestSqliteTypes( bool? cTextBoolOverride, bool? cIntegerBoolOverride, DateTime? cTextDatetimeOverride, - DateTime? cIntegerDatetimeOverride) + DateTime? cIntegerDatetimeOverride, + Instant? cTextNodaInstantOverride, + Instant? cIntegerNodaInstantOverride) { - if (cTextDatetimeOverride.HasValue && cTextDatetimeOverride.Value.Kind != DateTimeKind.Utc) - cTextDatetimeOverride = DateTime.SpecifyKind(cTextDatetimeOverride.Value, DateTimeKind.Utc); - if (cIntegerDatetimeOverride.HasValue && cIntegerDatetimeOverride.Value.Kind != DateTimeKind.Utc) - cIntegerDatetimeOverride = DateTime.SpecifyKind(cIntegerDatetimeOverride.Value, DateTimeKind.Utc); - await QuerySql.InsertSqliteTypes(new QuerySql.InsertSqliteTypesArgs { CInteger = cInteger, @@ -37,7 +59,9 @@ await QuerySql.InsertSqliteTypes(new QuerySql.InsertSqliteTypesArgs CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, - CIntegerDatetimeOverride = cIntegerDatetimeOverride + CIntegerDatetimeOverride = cIntegerDatetimeOverride, + CTextNodaInstantOverride = cTextNodaInstantOverride, + CIntegerNodaInstantOverride = cIntegerNodaInstantOverride }); var expected = new QuerySql.GetSqliteTypesRow @@ -49,7 +73,9 @@ await QuerySql.InsertSqliteTypes(new QuerySql.InsertSqliteTypesArgs CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, - CIntegerDatetimeOverride = cIntegerDatetimeOverride + CIntegerDatetimeOverride = cIntegerDatetimeOverride, + CTextNodaInstantOverride = cTextNodaInstantOverride, + CIntegerNodaInstantOverride = cIntegerNodaInstantOverride }; var actual = await QuerySql.GetSqliteTypes(); AssertSingularEquals(expected, actual{{Consts.UnknownRecordValuePlaceholder}}); @@ -62,24 +88,10 @@ void AssertSingularEquals(QuerySql.GetSqliteTypesRow x, QuerySql.GetSqliteTypesR Assert.That(x.CBlob, Is.EqualTo(y.CBlob)); Assert.That(x.CTextBoolOverride, Is.EqualTo(y.CTextBoolOverride)); Assert.That(x.CIntegerBoolOverride, Is.EqualTo(y.CIntegerBoolOverride)); - AssertDateTimeEquals(x.CTextDatetimeOverride, y.CTextDatetimeOverride); - AssertDateTimeEquals(x.CIntegerDatetimeOverride, y.CIntegerDatetimeOverride); - } - - void AssertDateTimeEquals(DateTime? x, DateTime? y) - { - Assert.That(x.HasValue, Is.EqualTo(y.HasValue)); - if (!x.HasValue) - return; - - var xv = x.Value; - var yv = y.Value; - Assert.That(xv.Year, Is.EqualTo(yv.Year)); - Assert.That(xv.Month, Is.EqualTo(yv.Month)); - Assert.That(xv.Day, Is.EqualTo(yv.Day)); - Assert.That(xv.Hour, Is.EqualTo(yv.Hour)); - Assert.That(xv.Minute, Is.EqualTo(yv.Minute)); - Assert.That(xv.Second, Is.EqualTo(yv.Second)); + Assert.That(x.CTextDatetimeOverride, Is.EqualTo(y.CTextDatetimeOverride)); + Assert.That(x.CIntegerDatetimeOverride, Is.EqualTo(y.CIntegerDatetimeOverride)); + Assert.That(x.CTextNodaInstantOverride, Is.EqualTo(y.CTextNodaInstantOverride)); + Assert.That(x.CIntegerNodaInstantOverride, Is.EqualTo(y.CIntegerNodaInstantOverride)); } } """ diff --git a/end2end/EndToEndTests/SqliteDapperTester.generated.cs b/end2end/EndToEndTests/SqliteDapperTester.generated.cs index 7011e8e5..86924139 100644 --- a/end2end/EndToEndTests/SqliteDapperTester.generated.cs +++ b/end2end/EndToEndTests/SqliteDapperTester.generated.cs @@ -328,17 +328,21 @@ void AssertSingularEquals(QuerySql.GetAuthorByNamePatternRow x, QuerySql.GetAuth } } + private static IEnumerable SqliteTypesTestCases + { + get + { + yield return new TestCaseData(-54355, 9787.66m, "Songs of Love and Hate", new byte[] { 0x15, 0x20, 0x33 }, true, false, DateTime.SpecifyKind(DateTime.Parse("2020-01-01 14:15:16"), DateTimeKind.Utc), DateTime.SpecifyKind(DateTime.Parse("2025-01-01 17:18:19"), DateTimeKind.Utc), Instant.FromUtc(2025, 10, 15, 19, 55, 2), Instant.FromUtc(1993, 9, 27, 03, 55, 2)).SetName("SqliteTypes with values"); + yield return new TestCaseData(null, null, null, new byte[] { }, null, null, null, null, null, null).SetName("SqliteTypes with empty values"); + yield return new TestCaseData(null, null, null, null, null, null, null, null, null, null).SetName("SqliteTypes with null values"); + } + } + [Test] - [TestCase(-54355, 9787.66, "Songs of Love and Hate", new byte[] { 0x15, 0x20, 0x33 }, true, false, "2020-01-01 14:15:16", "2025-01-01 17:18:19")] - [TestCase(null, null, null, new byte[] { }, null, null, null, null)] - [TestCase(null, null, null, null, null, null, null, null)] - public async Task TestSqliteTypes(int? cInteger, decimal? cReal, string cText, byte[] cBlob, bool? cTextBoolOverride, bool? cIntegerBoolOverride, DateTime? cTextDatetimeOverride, DateTime? cIntegerDatetimeOverride) + [TestCaseSource(nameof(SqliteTypesTestCases))] + public async Task TestSqliteTypes(int? cInteger, decimal? cReal, string cText, byte[] cBlob, bool? cTextBoolOverride, bool? cIntegerBoolOverride, DateTime? cTextDatetimeOverride, DateTime? cIntegerDatetimeOverride, Instant? cTextNodaInstantOverride, Instant? cIntegerNodaInstantOverride) { - if (cTextDatetimeOverride.HasValue && cTextDatetimeOverride.Value.Kind != DateTimeKind.Utc) - cTextDatetimeOverride = DateTime.SpecifyKind(cTextDatetimeOverride.Value, DateTimeKind.Utc); - if (cIntegerDatetimeOverride.HasValue && cIntegerDatetimeOverride.Value.Kind != DateTimeKind.Utc) - cIntegerDatetimeOverride = DateTime.SpecifyKind(cIntegerDatetimeOverride.Value, DateTimeKind.Utc); - await QuerySql.InsertSqliteTypes(new QuerySql.InsertSqliteTypesArgs { CInteger = cInteger, CReal = cReal, CText = cText, CBlob = cBlob, CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, CIntegerDatetimeOverride = cIntegerDatetimeOverride }); + await QuerySql.InsertSqliteTypes(new QuerySql.InsertSqliteTypesArgs { CInteger = cInteger, CReal = cReal, CText = cText, CBlob = cBlob, CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, CIntegerDatetimeOverride = cIntegerDatetimeOverride, CTextNodaInstantOverride = cTextNodaInstantOverride, CIntegerNodaInstantOverride = cIntegerNodaInstantOverride }); var expected = new QuerySql.GetSqliteTypesRow { CInteger = cInteger, @@ -348,7 +352,9 @@ public async Task TestSqliteTypes(int? cInteger, decimal? cReal, string cText, b CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, - CIntegerDatetimeOverride = cIntegerDatetimeOverride + CIntegerDatetimeOverride = cIntegerDatetimeOverride, + CTextNodaInstantOverride = cTextNodaInstantOverride, + CIntegerNodaInstantOverride = cIntegerNodaInstantOverride }; var actual = await QuerySql.GetSqliteTypes(); AssertSingularEquals(expected, actual); @@ -360,23 +366,10 @@ void AssertSingularEquals(QuerySql.GetSqliteTypesRow x, QuerySql.GetSqliteTypesR Assert.That(x.CBlob, Is.EqualTo(y.CBlob)); Assert.That(x.CTextBoolOverride, Is.EqualTo(y.CTextBoolOverride)); Assert.That(x.CIntegerBoolOverride, Is.EqualTo(y.CIntegerBoolOverride)); - AssertDateTimeEquals(x.CTextDatetimeOverride, y.CTextDatetimeOverride); - AssertDateTimeEquals(x.CIntegerDatetimeOverride, y.CIntegerDatetimeOverride); - } - - void AssertDateTimeEquals(DateTime? x, DateTime? y) - { - Assert.That(x.HasValue, Is.EqualTo(y.HasValue)); - if (!x.HasValue) - return; - var xv = x.Value; - var yv = y.Value; - Assert.That(xv.Year, Is.EqualTo(yv.Year)); - Assert.That(xv.Month, Is.EqualTo(yv.Month)); - Assert.That(xv.Day, Is.EqualTo(yv.Day)); - Assert.That(xv.Hour, Is.EqualTo(yv.Hour)); - Assert.That(xv.Minute, Is.EqualTo(yv.Minute)); - Assert.That(xv.Second, Is.EqualTo(yv.Second)); + Assert.That(x.CTextDatetimeOverride, Is.EqualTo(y.CTextDatetimeOverride)); + Assert.That(x.CIntegerDatetimeOverride, Is.EqualTo(y.CIntegerDatetimeOverride)); + Assert.That(x.CTextNodaInstantOverride, Is.EqualTo(y.CTextNodaInstantOverride)); + Assert.That(x.CIntegerNodaInstantOverride, Is.EqualTo(y.CIntegerNodaInstantOverride)); } } diff --git a/end2end/EndToEndTests/SqliteTester.generated.cs b/end2end/EndToEndTests/SqliteTester.generated.cs index d90f1896..92275628 100644 --- a/end2end/EndToEndTests/SqliteTester.generated.cs +++ b/end2end/EndToEndTests/SqliteTester.generated.cs @@ -328,17 +328,21 @@ void AssertSingularEquals(QuerySql.GetAuthorByNamePatternRow x, QuerySql.GetAuth } } + private static IEnumerable SqliteTypesTestCases + { + get + { + yield return new TestCaseData(-54355, 9787.66m, "Songs of Love and Hate", new byte[] { 0x15, 0x20, 0x33 }, true, false, DateTime.SpecifyKind(DateTime.Parse("2020-01-01 14:15:16"), DateTimeKind.Utc), DateTime.SpecifyKind(DateTime.Parse("2025-01-01 17:18:19"), DateTimeKind.Utc), Instant.FromUtc(2025, 10, 15, 19, 55, 2), Instant.FromUtc(1993, 9, 27, 03, 55, 2)).SetName("SqliteTypes with values"); + yield return new TestCaseData(null, null, null, new byte[] { }, null, null, null, null, null, null).SetName("SqliteTypes with empty values"); + yield return new TestCaseData(null, null, null, null, null, null, null, null, null, null).SetName("SqliteTypes with null values"); + } + } + [Test] - [TestCase(-54355, 9787.66, "Songs of Love and Hate", new byte[] { 0x15, 0x20, 0x33 }, true, false, "2020-01-01 14:15:16", "2025-01-01 17:18:19")] - [TestCase(null, null, null, new byte[] { }, null, null, null, null)] - [TestCase(null, null, null, null, null, null, null, null)] - public async Task TestSqliteTypes(int? cInteger, decimal? cReal, string cText, byte[] cBlob, bool? cTextBoolOverride, bool? cIntegerBoolOverride, DateTime? cTextDatetimeOverride, DateTime? cIntegerDatetimeOverride) + [TestCaseSource(nameof(SqliteTypesTestCases))] + public async Task TestSqliteTypes(int? cInteger, decimal? cReal, string cText, byte[] cBlob, bool? cTextBoolOverride, bool? cIntegerBoolOverride, DateTime? cTextDatetimeOverride, DateTime? cIntegerDatetimeOverride, Instant? cTextNodaInstantOverride, Instant? cIntegerNodaInstantOverride) { - if (cTextDatetimeOverride.HasValue && cTextDatetimeOverride.Value.Kind != DateTimeKind.Utc) - cTextDatetimeOverride = DateTime.SpecifyKind(cTextDatetimeOverride.Value, DateTimeKind.Utc); - if (cIntegerDatetimeOverride.HasValue && cIntegerDatetimeOverride.Value.Kind != DateTimeKind.Utc) - cIntegerDatetimeOverride = DateTime.SpecifyKind(cIntegerDatetimeOverride.Value, DateTimeKind.Utc); - await QuerySql.InsertSqliteTypes(new QuerySql.InsertSqliteTypesArgs { CInteger = cInteger, CReal = cReal, CText = cText, CBlob = cBlob, CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, CIntegerDatetimeOverride = cIntegerDatetimeOverride }); + await QuerySql.InsertSqliteTypes(new QuerySql.InsertSqliteTypesArgs { CInteger = cInteger, CReal = cReal, CText = cText, CBlob = cBlob, CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, CIntegerDatetimeOverride = cIntegerDatetimeOverride, CTextNodaInstantOverride = cTextNodaInstantOverride, CIntegerNodaInstantOverride = cIntegerNodaInstantOverride }); var expected = new QuerySql.GetSqliteTypesRow { CInteger = cInteger, @@ -348,7 +352,9 @@ public async Task TestSqliteTypes(int? cInteger, decimal? cReal, string cText, b CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, - CIntegerDatetimeOverride = cIntegerDatetimeOverride + CIntegerDatetimeOverride = cIntegerDatetimeOverride, + CTextNodaInstantOverride = cTextNodaInstantOverride, + CIntegerNodaInstantOverride = cIntegerNodaInstantOverride }; var actual = await QuerySql.GetSqliteTypes(); AssertSingularEquals(expected, actual.Value); @@ -360,23 +366,10 @@ void AssertSingularEquals(QuerySql.GetSqliteTypesRow x, QuerySql.GetSqliteTypesR Assert.That(x.CBlob, Is.EqualTo(y.CBlob)); Assert.That(x.CTextBoolOverride, Is.EqualTo(y.CTextBoolOverride)); Assert.That(x.CIntegerBoolOverride, Is.EqualTo(y.CIntegerBoolOverride)); - AssertDateTimeEquals(x.CTextDatetimeOverride, y.CTextDatetimeOverride); - AssertDateTimeEquals(x.CIntegerDatetimeOverride, y.CIntegerDatetimeOverride); - } - - void AssertDateTimeEquals(DateTime? x, DateTime? y) - { - Assert.That(x.HasValue, Is.EqualTo(y.HasValue)); - if (!x.HasValue) - return; - var xv = x.Value; - var yv = y.Value; - Assert.That(xv.Year, Is.EqualTo(yv.Year)); - Assert.That(xv.Month, Is.EqualTo(yv.Month)); - Assert.That(xv.Day, Is.EqualTo(yv.Day)); - Assert.That(xv.Hour, Is.EqualTo(yv.Hour)); - Assert.That(xv.Minute, Is.EqualTo(yv.Minute)); - Assert.That(xv.Second, Is.EqualTo(yv.Second)); + Assert.That(x.CTextDatetimeOverride, Is.EqualTo(y.CTextDatetimeOverride)); + Assert.That(x.CIntegerDatetimeOverride, Is.EqualTo(y.CIntegerDatetimeOverride)); + Assert.That(x.CTextNodaInstantOverride, Is.EqualTo(y.CTextNodaInstantOverride)); + Assert.That(x.CIntegerNodaInstantOverride, Is.EqualTo(y.CIntegerNodaInstantOverride)); } } diff --git a/end2end/EndToEndTestsLegacy/SqliteDapperTester.generated.cs b/end2end/EndToEndTestsLegacy/SqliteDapperTester.generated.cs index 9a1bea7a..7e8720a4 100644 --- a/end2end/EndToEndTestsLegacy/SqliteDapperTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/SqliteDapperTester.generated.cs @@ -328,17 +328,21 @@ void AssertSingularEquals(QuerySql.GetAuthorByNamePatternRow x, QuerySql.GetAuth } } + private static IEnumerable SqliteTypesTestCases + { + get + { + yield return new TestCaseData(-54355, 9787.66m, "Songs of Love and Hate", new byte[] { 0x15, 0x20, 0x33 }, true, false, DateTime.SpecifyKind(DateTime.Parse("2020-01-01 14:15:16"), DateTimeKind.Utc), DateTime.SpecifyKind(DateTime.Parse("2025-01-01 17:18:19"), DateTimeKind.Utc), Instant.FromUtc(2025, 10, 15, 19, 55, 2), Instant.FromUtc(1993, 9, 27, 03, 55, 2)).SetName("SqliteTypes with values"); + yield return new TestCaseData(null, null, null, new byte[] { }, null, null, null, null, null, null).SetName("SqliteTypes with empty values"); + yield return new TestCaseData(null, null, null, null, null, null, null, null, null, null).SetName("SqliteTypes with null values"); + } + } + [Test] - [TestCase(-54355, 9787.66, "Songs of Love and Hate", new byte[] { 0x15, 0x20, 0x33 }, true, false, "2020-01-01 14:15:16", "2025-01-01 17:18:19")] - [TestCase(null, null, null, new byte[] { }, null, null, null, null)] - [TestCase(null, null, null, null, null, null, null, null)] - public async Task TestSqliteTypes(int? cInteger, decimal? cReal, string cText, byte[] cBlob, bool? cTextBoolOverride, bool? cIntegerBoolOverride, DateTime? cTextDatetimeOverride, DateTime? cIntegerDatetimeOverride) + [TestCaseSource(nameof(SqliteTypesTestCases))] + public async Task TestSqliteTypes(int? cInteger, decimal? cReal, string cText, byte[] cBlob, bool? cTextBoolOverride, bool? cIntegerBoolOverride, DateTime? cTextDatetimeOverride, DateTime? cIntegerDatetimeOverride, Instant? cTextNodaInstantOverride, Instant? cIntegerNodaInstantOverride) { - if (cTextDatetimeOverride.HasValue && cTextDatetimeOverride.Value.Kind != DateTimeKind.Utc) - cTextDatetimeOverride = DateTime.SpecifyKind(cTextDatetimeOverride.Value, DateTimeKind.Utc); - if (cIntegerDatetimeOverride.HasValue && cIntegerDatetimeOverride.Value.Kind != DateTimeKind.Utc) - cIntegerDatetimeOverride = DateTime.SpecifyKind(cIntegerDatetimeOverride.Value, DateTimeKind.Utc); - await QuerySql.InsertSqliteTypes(new QuerySql.InsertSqliteTypesArgs { CInteger = cInteger, CReal = cReal, CText = cText, CBlob = cBlob, CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, CIntegerDatetimeOverride = cIntegerDatetimeOverride }); + await QuerySql.InsertSqliteTypes(new QuerySql.InsertSqliteTypesArgs { CInteger = cInteger, CReal = cReal, CText = cText, CBlob = cBlob, CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, CIntegerDatetimeOverride = cIntegerDatetimeOverride, CTextNodaInstantOverride = cTextNodaInstantOverride, CIntegerNodaInstantOverride = cIntegerNodaInstantOverride }); var expected = new QuerySql.GetSqliteTypesRow { CInteger = cInteger, @@ -348,7 +352,9 @@ public async Task TestSqliteTypes(int? cInteger, decimal? cReal, string cText, b CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, - CIntegerDatetimeOverride = cIntegerDatetimeOverride + CIntegerDatetimeOverride = cIntegerDatetimeOverride, + CTextNodaInstantOverride = cTextNodaInstantOverride, + CIntegerNodaInstantOverride = cIntegerNodaInstantOverride }; var actual = await QuerySql.GetSqliteTypes(); AssertSingularEquals(expected, actual); @@ -360,23 +366,10 @@ void AssertSingularEquals(QuerySql.GetSqliteTypesRow x, QuerySql.GetSqliteTypesR Assert.That(x.CBlob, Is.EqualTo(y.CBlob)); Assert.That(x.CTextBoolOverride, Is.EqualTo(y.CTextBoolOverride)); Assert.That(x.CIntegerBoolOverride, Is.EqualTo(y.CIntegerBoolOverride)); - AssertDateTimeEquals(x.CTextDatetimeOverride, y.CTextDatetimeOverride); - AssertDateTimeEquals(x.CIntegerDatetimeOverride, y.CIntegerDatetimeOverride); - } - - void AssertDateTimeEquals(DateTime? x, DateTime? y) - { - Assert.That(x.HasValue, Is.EqualTo(y.HasValue)); - if (!x.HasValue) - return; - var xv = x.Value; - var yv = y.Value; - Assert.That(xv.Year, Is.EqualTo(yv.Year)); - Assert.That(xv.Month, Is.EqualTo(yv.Month)); - Assert.That(xv.Day, Is.EqualTo(yv.Day)); - Assert.That(xv.Hour, Is.EqualTo(yv.Hour)); - Assert.That(xv.Minute, Is.EqualTo(yv.Minute)); - Assert.That(xv.Second, Is.EqualTo(yv.Second)); + Assert.That(x.CTextDatetimeOverride, Is.EqualTo(y.CTextDatetimeOverride)); + Assert.That(x.CIntegerDatetimeOverride, Is.EqualTo(y.CIntegerDatetimeOverride)); + Assert.That(x.CTextNodaInstantOverride, Is.EqualTo(y.CTextNodaInstantOverride)); + Assert.That(x.CIntegerNodaInstantOverride, Is.EqualTo(y.CIntegerNodaInstantOverride)); } } diff --git a/end2end/EndToEndTestsLegacy/SqliteTester.generated.cs b/end2end/EndToEndTestsLegacy/SqliteTester.generated.cs index 27113668..5e4472ba 100644 --- a/end2end/EndToEndTestsLegacy/SqliteTester.generated.cs +++ b/end2end/EndToEndTestsLegacy/SqliteTester.generated.cs @@ -328,17 +328,21 @@ void AssertSingularEquals(QuerySql.GetAuthorByNamePatternRow x, QuerySql.GetAuth } } + private static IEnumerable SqliteTypesTestCases + { + get + { + yield return new TestCaseData(-54355, 9787.66m, "Songs of Love and Hate", new byte[] { 0x15, 0x20, 0x33 }, true, false, DateTime.SpecifyKind(DateTime.Parse("2020-01-01 14:15:16"), DateTimeKind.Utc), DateTime.SpecifyKind(DateTime.Parse("2025-01-01 17:18:19"), DateTimeKind.Utc), Instant.FromUtc(2025, 10, 15, 19, 55, 2), Instant.FromUtc(1993, 9, 27, 03, 55, 2)).SetName("SqliteTypes with values"); + yield return new TestCaseData(null, null, null, new byte[] { }, null, null, null, null, null, null).SetName("SqliteTypes with empty values"); + yield return new TestCaseData(null, null, null, null, null, null, null, null, null, null).SetName("SqliteTypes with null values"); + } + } + [Test] - [TestCase(-54355, 9787.66, "Songs of Love and Hate", new byte[] { 0x15, 0x20, 0x33 }, true, false, "2020-01-01 14:15:16", "2025-01-01 17:18:19")] - [TestCase(null, null, null, new byte[] { }, null, null, null, null)] - [TestCase(null, null, null, null, null, null, null, null)] - public async Task TestSqliteTypes(int? cInteger, decimal? cReal, string cText, byte[] cBlob, bool? cTextBoolOverride, bool? cIntegerBoolOverride, DateTime? cTextDatetimeOverride, DateTime? cIntegerDatetimeOverride) + [TestCaseSource(nameof(SqliteTypesTestCases))] + public async Task TestSqliteTypes(int? cInteger, decimal? cReal, string cText, byte[] cBlob, bool? cTextBoolOverride, bool? cIntegerBoolOverride, DateTime? cTextDatetimeOverride, DateTime? cIntegerDatetimeOverride, Instant? cTextNodaInstantOverride, Instant? cIntegerNodaInstantOverride) { - if (cTextDatetimeOverride.HasValue && cTextDatetimeOverride.Value.Kind != DateTimeKind.Utc) - cTextDatetimeOverride = DateTime.SpecifyKind(cTextDatetimeOverride.Value, DateTimeKind.Utc); - if (cIntegerDatetimeOverride.HasValue && cIntegerDatetimeOverride.Value.Kind != DateTimeKind.Utc) - cIntegerDatetimeOverride = DateTime.SpecifyKind(cIntegerDatetimeOverride.Value, DateTimeKind.Utc); - await QuerySql.InsertSqliteTypes(new QuerySql.InsertSqliteTypesArgs { CInteger = cInteger, CReal = cReal, CText = cText, CBlob = cBlob, CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, CIntegerDatetimeOverride = cIntegerDatetimeOverride }); + await QuerySql.InsertSqliteTypes(new QuerySql.InsertSqliteTypesArgs { CInteger = cInteger, CReal = cReal, CText = cText, CBlob = cBlob, CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, CIntegerDatetimeOverride = cIntegerDatetimeOverride, CTextNodaInstantOverride = cTextNodaInstantOverride, CIntegerNodaInstantOverride = cIntegerNodaInstantOverride }); var expected = new QuerySql.GetSqliteTypesRow { CInteger = cInteger, @@ -348,7 +352,9 @@ public async Task TestSqliteTypes(int? cInteger, decimal? cReal, string cText, b CTextBoolOverride = cTextBoolOverride, CIntegerBoolOverride = cIntegerBoolOverride, CTextDatetimeOverride = cTextDatetimeOverride, - CIntegerDatetimeOverride = cIntegerDatetimeOverride + CIntegerDatetimeOverride = cIntegerDatetimeOverride, + CTextNodaInstantOverride = cTextNodaInstantOverride, + CIntegerNodaInstantOverride = cIntegerNodaInstantOverride }; var actual = await QuerySql.GetSqliteTypes(); AssertSingularEquals(expected, actual); @@ -360,23 +366,10 @@ void AssertSingularEquals(QuerySql.GetSqliteTypesRow x, QuerySql.GetSqliteTypesR Assert.That(x.CBlob, Is.EqualTo(y.CBlob)); Assert.That(x.CTextBoolOverride, Is.EqualTo(y.CTextBoolOverride)); Assert.That(x.CIntegerBoolOverride, Is.EqualTo(y.CIntegerBoolOverride)); - AssertDateTimeEquals(x.CTextDatetimeOverride, y.CTextDatetimeOverride); - AssertDateTimeEquals(x.CIntegerDatetimeOverride, y.CIntegerDatetimeOverride); - } - - void AssertDateTimeEquals(DateTime? x, DateTime? y) - { - Assert.That(x.HasValue, Is.EqualTo(y.HasValue)); - if (!x.HasValue) - return; - var xv = x.Value; - var yv = y.Value; - Assert.That(xv.Year, Is.EqualTo(yv.Year)); - Assert.That(xv.Month, Is.EqualTo(yv.Month)); - Assert.That(xv.Day, Is.EqualTo(yv.Day)); - Assert.That(xv.Hour, Is.EqualTo(yv.Hour)); - Assert.That(xv.Minute, Is.EqualTo(yv.Minute)); - Assert.That(xv.Second, Is.EqualTo(yv.Second)); + Assert.That(x.CTextDatetimeOverride, Is.EqualTo(y.CTextDatetimeOverride)); + Assert.That(x.CIntegerDatetimeOverride, Is.EqualTo(y.CIntegerDatetimeOverride)); + Assert.That(x.CTextNodaInstantOverride, Is.EqualTo(y.CTextNodaInstantOverride)); + Assert.That(x.CIntegerNodaInstantOverride, Is.EqualTo(y.CIntegerNodaInstantOverride)); } } diff --git a/examples/SqliteDapperExample/Models.cs b/examples/SqliteDapperExample/Models.cs index ce95a5a1..ecf8be70 100644 --- a/examples/SqliteDapperExample/Models.cs +++ b/examples/SqliteDapperExample/Models.cs @@ -1,4 +1,7 @@ // auto-generated by sqlc - do not edit +using NodaTime; +using NodaTime.Extensions; +using NodaTime.Text; using System.Linq; namespace SqliteDapperExampleGen; @@ -23,6 +26,8 @@ public class TypesSqlite public byte[]? CBlob { get; init; } public string? CTextDatetimeOverride { get; init; } public int? CIntegerDatetimeOverride { get; init; } + public string? CTextNodaInstantOverride { get; init; } + public int? CIntegerNodaInstantOverride { get; init; } public string? CTextBoolOverride { get; init; } public int? CIntegerBoolOverride { get; init; } }; \ No newline at end of file diff --git a/examples/SqliteDapperExample/QuerySql.cs b/examples/SqliteDapperExample/QuerySql.cs index 7f936975..087befc5 100644 --- a/examples/SqliteDapperExample/QuerySql.cs +++ b/examples/SqliteDapperExample/QuerySql.cs @@ -6,6 +6,9 @@ // ReSharper disable UnusedAutoPropertyAccessor.Global using Dapper; using Microsoft.Data.Sqlite; +using NodaTime; +using NodaTime.Extensions; +using NodaTime.Text; using System; using System.Collections.Generic; using System.Threading.Tasks; @@ -521,7 +524,7 @@ public async Task DeleteAllAuthors() await this.Transaction.Connection.ExecuteAsync(DeleteAllAuthorsSql, transaction: this.Transaction); } - private const string InsertSqliteTypesSql = "INSERT INTO types_sqlite ( c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_bool_override, c_integer_bool_override ) VALUES (@c_integer, @c_real, @c_text, @c_blob, @c_text_datetime_override, @c_integer_datetime_override, @c_text_bool_override, @c_integer_bool_override)"; + private const string InsertSqliteTypesSql = "INSERT INTO types_sqlite ( c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_noda_instant_override, c_integer_noda_instant_override, c_text_bool_override, c_integer_bool_override ) VALUES (@c_integer, @c_real, @c_text, @c_blob, @c_text_datetime_override, @c_integer_datetime_override, @c_text_noda_instant_override, @c_integer_noda_instant_override, @c_text_bool_override, @c_integer_bool_override)"; public class InsertSqliteTypesArgs { public int? CInteger { get; init; } @@ -530,6 +533,8 @@ public class InsertSqliteTypesArgs public byte[]? CBlob { get; init; } public DateTime? CTextDatetimeOverride { get; init; } public DateTime? CIntegerDatetimeOverride { get; init; } + public Instant? CTextNodaInstantOverride { get; init; } + public Instant? CIntegerNodaInstantOverride { get; init; } public bool? CTextBoolOverride { get; init; } public bool? CIntegerBoolOverride { get; init; } }; @@ -542,6 +547,8 @@ public async Task InsertSqliteTypes(InsertSqliteTypesArgs args) queryParams.Add("c_blob", args.CBlob); queryParams.Add("c_text_datetime_override", args.CTextDatetimeOverride != null ? args.CTextDatetimeOverride.Value.ToString("yyyy-MM-dd HH:mm:ss") : null); queryParams.Add("c_integer_datetime_override", args.CIntegerDatetimeOverride != null ? (int? )new DateTimeOffset(args.CIntegerDatetimeOverride.Value.ToUniversalTime()).ToUnixTimeSeconds() : null); + queryParams.Add("c_text_noda_instant_override", args.CTextNodaInstantOverride != null ? InstantPattern.CreateWithInvariantCulture("yyyy-MM-dd HH:mm:ss").Format(args.CTextNodaInstantOverride.Value) : null); + queryParams.Add("c_integer_noda_instant_override", args.CIntegerNodaInstantOverride != null ? (long? )args.CIntegerNodaInstantOverride.Value.ToUnixTimeSeconds() : null); queryParams.Add("c_text_bool_override", args.CTextBoolOverride != null ? Convert.ToString(args.CTextBoolOverride) : null); queryParams.Add("c_integer_bool_override", args.CIntegerBoolOverride != null ? (int? )Convert.ToInt32(args.CIntegerBoolOverride) : null); if (this.Transaction == null) @@ -583,7 +590,7 @@ public async Task InsertSqliteTypesBatch(List args) } } - private const string GetSqliteTypesSql = "SELECT c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_bool_override, c_integer_bool_override FROM types_sqlite LIMIT 1"; + private const string GetSqliteTypesSql = "SELECT c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_noda_instant_override, c_integer_noda_instant_override, c_text_bool_override, c_integer_bool_override FROM types_sqlite LIMIT 1"; public class GetSqliteTypesRow { public int? CInteger { get; init; } @@ -592,6 +599,8 @@ public class GetSqliteTypesRow public byte[]? CBlob { get; init; } public DateTime? CTextDatetimeOverride { get; init; } public DateTime? CIntegerDatetimeOverride { get; init; } + public Instant? CTextNodaInstantOverride { get; init; } + public Instant? CIntegerNodaInstantOverride { get; init; } public bool? CTextBoolOverride { get; init; } public bool? CIntegerBoolOverride { get; init; } }; diff --git a/examples/SqliteDapperExample/Utils.cs b/examples/SqliteDapperExample/Utils.cs index 51bdcc1f..9b81929e 100644 --- a/examples/SqliteDapperExample/Utils.cs +++ b/examples/SqliteDapperExample/Utils.cs @@ -1,5 +1,8 @@ // auto-generated by sqlc - do not edit using Dapper; +using NodaTime; +using NodaTime.Extensions; +using NodaTime.Text; using System; using System.Data; using System.Linq; @@ -25,9 +28,27 @@ public override void SetValue(IDbDataParameter parameter, DateTime value) } } + private class NodaInstantTypeHandler : SqlMapper.TypeHandler + { + public override Instant Parse(object value) + { + if (value is string s) + return InstantPattern.CreateWithInvariantCulture("yyyy-MM-dd HH:mm:ss").Parse(s).Value; + if (value is long l) + return Instant.FromUnixTimeSeconds(l); + throw new DataException($"Cannot convert {value?.GetType()} to Instant"); + } + + public override void SetValue(IDbDataParameter parameter, Instant value) + { + parameter.Value = value; + } + } + public static void ConfigureSqlMapper() { SqlMapper.AddTypeHandler(typeof(DateTime), new DateTimeTypeHandler()); + SqlMapper.AddTypeHandler(typeof(Instant), new NodaInstantTypeHandler()); } public static string TransformQueryForSliceArgs(string originalSql, int sliceSize, string paramName) diff --git a/examples/SqliteDapperExample/request.json b/examples/SqliteDapperExample/request.json index 6888e99c..847e0470 100644 --- a/examples/SqliteDapperExample/request.json +++ b/examples/SqliteDapperExample/request.json @@ -13,7 +13,7 @@ "codegen": { "out": "examples/SqliteDapperExample", "plugin": "csharp", - "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlRGFwcGVyRXhhbXBsZUdlbiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCJ9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3JlYWwiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiZGVjaW1hbCJ9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIn19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUifX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX1dLCJ0YXJnZXRGcmFtZXdvcmsiOiJuZXQ4LjAiLCJ1c2VEYXBwZXIiOnRydWV9", + "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlRGFwcGVyRXhhbXBsZUdlbiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCJ9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3JlYWwiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiZGVjaW1hbCJ9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIn19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUifX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSW5zdGFudCJ9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX25vZGFfaW5zdGFudF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJJbnN0YW50In19XSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwidXNlRGFwcGVyIjp0cnVlfQ==", "process": { "cmd": "./dist/LocalRunner" } @@ -179,6 +179,26 @@ "name": "INTEGER" } }, + { + "name": "c_text_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "TEXT" + } + }, + { + "name": "c_integer_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "INTEGER" + } + }, { "name": "c_text_bool_override", "length": -1, @@ -1008,7 +1028,7 @@ "filename": "query.sql" }, { - "text": "INSERT INTO types_sqlite \n(\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_bool_override,\n c_integer_bool_override\n) \nVALUES (?, ?, ?, ?, ?, ?, ?, ?)", + "text": "INSERT INTO types_sqlite \n(\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_noda_instant_override,\n c_integer_noda_instant_override,\n c_text_bool_override,\n c_integer_bool_override\n) \nVALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", "name": "InsertSqliteTypes", "cmd": ":exec", "parameters": [ @@ -1104,6 +1124,36 @@ }, { "number": 7, + "column": { + "name": "c_text_noda_instant_override", + "length": -1, + "table": { + "schema": "main", + "name": "types_sqlite" + }, + "type": { + "name": "TEXT" + }, + "originalName": "c_text_noda_instant_override" + } + }, + { + "number": 8, + "column": { + "name": "c_integer_noda_instant_override", + "length": -1, + "table": { + "schema": "main", + "name": "types_sqlite" + }, + "type": { + "name": "INTEGER" + }, + "originalName": "c_integer_noda_instant_override" + } + }, + { + "number": 9, "column": { "name": "c_text_bool_override", "length": -1, @@ -1118,7 +1168,7 @@ } }, { - "number": 8, + "number": 10, "column": { "name": "c_integer_bool_override", "length": -1, @@ -1195,7 +1245,7 @@ } }, { - "text": "SELECT\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_bool_override,\n c_integer_bool_override\nFROM types_sqlite\nLIMIT 1", + "text": "SELECT\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_noda_instant_override,\n c_integer_noda_instant_override,\n c_text_bool_override,\n c_integer_bool_override\nFROM types_sqlite\nLIMIT 1", "name": "GetSqliteTypes", "cmd": ":one", "columns": [ @@ -1265,6 +1315,28 @@ }, "originalName": "c_integer_datetime_override" }, + { + "name": "c_text_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "TEXT" + }, + "originalName": "c_text_noda_instant_override" + }, + { + "name": "c_integer_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "INTEGER" + }, + "originalName": "c_integer_noda_instant_override" + }, { "name": "c_text_bool_override", "length": -1, @@ -1391,5 +1463,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6IlNxbGl0ZURhcHBlckV4YW1wbGVHZW4iLCJ1c2VEYXBwZXIiOnRydWUsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsInVzZU5vZGFUaW1lIjpmYWxzZSwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X2ludGVnZXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9yZWFsIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImRlY2ltYWwiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfYm9vbF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJib29sIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX2Jvb2xfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiYm9vbCIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6IlNxbGl0ZURhcHBlckV4YW1wbGVHZW4iLCJ1c2VEYXBwZXIiOnRydWUsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsInVzZU5vZGFUaW1lIjpmYWxzZSwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X2ludGVnZXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9yZWFsIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImRlY2ltYWwiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfYm9vbF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJib29sIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX2Jvb2xfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiYm9vbCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSW5zdGFudCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSW5zdGFudCIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" } \ No newline at end of file diff --git a/examples/SqliteDapperExample/request.message b/examples/SqliteDapperExample/request.message index d58db710f13f22f030f25794aa91f94726b2e6bc..fa6a7bd16a71408e55373300a1765a4318fb8f99 100644 GIT binary patch delta 667 zcmccO^CN_rYc|J3=1ok`*(PpRXIjCw@j)!pTJfsE&`9l|&VYkVx9RMdBNyR3-P##W4eU#LmEWpO4T7|>a2y-GiI47@_ielyxikrMZUUjp+^kPQtgB)D_Ou?=` zuFfHoKZw_%x*v;&95=Vgo?sM<$L<+W82ZU^nB(=3QU*@XFv=T<1F{0j1(CNW0*eK);9UZf+5<%kk_Hk4ZDDC{B8djGDg-?N z0?GrkX$4OKvqT5A5e2aa3g!Wm{ur5)-Wg1@FdFay23ZIP5>*P5@FEqH%pwevPaGbT z@FEokDq;u-5?+&l2PKnF92S#)8Vi$0BO|lO9bW+iuLcUplW!wHlWQMElinFCvmzkK V0kgFtz5@cr2D5c0F9VZdDi?z1H)8+* diff --git a/examples/SqliteDapperLegacyExample/Models.cs b/examples/SqliteDapperLegacyExample/Models.cs index 2c501aef..c3e40e54 100644 --- a/examples/SqliteDapperLegacyExample/Models.cs +++ b/examples/SqliteDapperLegacyExample/Models.cs @@ -1,6 +1,9 @@ // auto-generated by sqlc - do not edit namespace SqliteDapperLegacyExampleGen { + using NodaTime; + using NodaTime.Extensions; + using NodaTime.Text; using System.Linq; public class Author @@ -24,6 +27,8 @@ public class TypesSqlite public byte[] CBlob { get; set; } public string CTextDatetimeOverride { get; set; } public int? CIntegerDatetimeOverride { get; set; } + public string CTextNodaInstantOverride { get; set; } + public int? CIntegerNodaInstantOverride { get; set; } public string CTextBoolOverride { get; set; } public int? CIntegerBoolOverride { get; set; } }; diff --git a/examples/SqliteDapperLegacyExample/QuerySql.cs b/examples/SqliteDapperLegacyExample/QuerySql.cs index 20dc1e2b..e754db3c 100644 --- a/examples/SqliteDapperLegacyExample/QuerySql.cs +++ b/examples/SqliteDapperLegacyExample/QuerySql.cs @@ -8,6 +8,9 @@ namespace SqliteDapperLegacyExampleGen { using Dapper; using Microsoft.Data.Sqlite; + using NodaTime; + using NodaTime.Extensions; + using NodaTime.Text; using System; using System.Collections.Generic; using System.Threading.Tasks; @@ -522,7 +525,7 @@ public async Task DeleteAllAuthors() await this.Transaction.Connection.ExecuteAsync(DeleteAllAuthorsSql, transaction: this.Transaction); } - private const string InsertSqliteTypesSql = "INSERT INTO types_sqlite ( c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_bool_override, c_integer_bool_override ) VALUES (@c_integer, @c_real, @c_text, @c_blob, @c_text_datetime_override, @c_integer_datetime_override, @c_text_bool_override, @c_integer_bool_override)"; + private const string InsertSqliteTypesSql = "INSERT INTO types_sqlite ( c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_noda_instant_override, c_integer_noda_instant_override, c_text_bool_override, c_integer_bool_override ) VALUES (@c_integer, @c_real, @c_text, @c_blob, @c_text_datetime_override, @c_integer_datetime_override, @c_text_noda_instant_override, @c_integer_noda_instant_override, @c_text_bool_override, @c_integer_bool_override)"; public class InsertSqliteTypesArgs { public int? CInteger { get; set; } @@ -531,6 +534,8 @@ public class InsertSqliteTypesArgs public byte[] CBlob { get; set; } public DateTime? CTextDatetimeOverride { get; set; } public DateTime? CIntegerDatetimeOverride { get; set; } + public Instant? CTextNodaInstantOverride { get; set; } + public Instant? CIntegerNodaInstantOverride { get; set; } public bool? CTextBoolOverride { get; set; } public bool? CIntegerBoolOverride { get; set; } }; @@ -543,6 +548,8 @@ public async Task InsertSqliteTypes(InsertSqliteTypesArgs args) queryParams.Add("c_blob", args.CBlob); queryParams.Add("c_text_datetime_override", args.CTextDatetimeOverride != null ? args.CTextDatetimeOverride.Value.ToString("yyyy-MM-dd HH:mm:ss") : null); queryParams.Add("c_integer_datetime_override", args.CIntegerDatetimeOverride != null ? (int? )new DateTimeOffset(args.CIntegerDatetimeOverride.Value.ToUniversalTime()).ToUnixTimeSeconds() : null); + queryParams.Add("c_text_noda_instant_override", args.CTextNodaInstantOverride != null ? InstantPattern.CreateWithInvariantCulture("yyyy-MM-dd HH:mm:ss").Format(args.CTextNodaInstantOverride.Value) : null); + queryParams.Add("c_integer_noda_instant_override", args.CIntegerNodaInstantOverride != null ? (long? )args.CIntegerNodaInstantOverride.Value.ToUnixTimeSeconds() : null); queryParams.Add("c_text_bool_override", args.CTextBoolOverride != null ? Convert.ToString(args.CTextBoolOverride) : null); queryParams.Add("c_integer_bool_override", args.CIntegerBoolOverride != null ? (int? )Convert.ToInt32(args.CIntegerBoolOverride) : null); if (this.Transaction == null) @@ -584,7 +591,7 @@ public async Task InsertSqliteTypesBatch(List args) } } - private const string GetSqliteTypesSql = "SELECT c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_bool_override, c_integer_bool_override FROM types_sqlite LIMIT 1"; + private const string GetSqliteTypesSql = "SELECT c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_noda_instant_override, c_integer_noda_instant_override, c_text_bool_override, c_integer_bool_override FROM types_sqlite LIMIT 1"; public class GetSqliteTypesRow { public int? CInteger { get; set; } @@ -593,6 +600,8 @@ public class GetSqliteTypesRow public byte[] CBlob { get; set; } public DateTime? CTextDatetimeOverride { get; set; } public DateTime? CIntegerDatetimeOverride { get; set; } + public Instant? CTextNodaInstantOverride { get; set; } + public Instant? CIntegerNodaInstantOverride { get; set; } public bool? CTextBoolOverride { get; set; } public bool? CIntegerBoolOverride { get; set; } }; diff --git a/examples/SqliteDapperLegacyExample/Utils.cs b/examples/SqliteDapperLegacyExample/Utils.cs index 5f682d42..b945b847 100644 --- a/examples/SqliteDapperLegacyExample/Utils.cs +++ b/examples/SqliteDapperLegacyExample/Utils.cs @@ -2,6 +2,9 @@ namespace SqliteDapperLegacyExampleGen { using Dapper; + using NodaTime; + using NodaTime.Extensions; + using NodaTime.Text; using System; using System.Data; using System.Linq; @@ -26,9 +29,27 @@ public override void SetValue(IDbDataParameter parameter, DateTime value) } } + private class NodaInstantTypeHandler : SqlMapper.TypeHandler + { + public override Instant Parse(object value) + { + if (value is string s) + return InstantPattern.CreateWithInvariantCulture("yyyy-MM-dd HH:mm:ss").Parse(s).Value; + if (value is long l) + return Instant.FromUnixTimeSeconds(l); + throw new DataException($"Cannot convert {value?.GetType()} to Instant"); + } + + public override void SetValue(IDbDataParameter parameter, Instant value) + { + parameter.Value = value; + } + } + public static void ConfigureSqlMapper() { SqlMapper.AddTypeHandler(typeof(DateTime), new DateTimeTypeHandler()); + SqlMapper.AddTypeHandler(typeof(Instant), new NodaInstantTypeHandler()); } public static string TransformQueryForSliceArgs(string originalSql, int sliceSize, string paramName) diff --git a/examples/SqliteDapperLegacyExample/request.json b/examples/SqliteDapperLegacyExample/request.json index b0c34489..32591fac 100644 --- a/examples/SqliteDapperLegacyExample/request.json +++ b/examples/SqliteDapperLegacyExample/request.json @@ -13,7 +13,7 @@ "codegen": { "out": "examples/SqliteDapperLegacyExample", "plugin": "csharp", - "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlRGFwcGVyTGVnYWN5RXhhbXBsZUdlbiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCJ9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3JlYWwiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiZGVjaW1hbCJ9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIn19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUifX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX1dLCJ0YXJnZXRGcmFtZXdvcmsiOiJuZXRzdGFuZGFyZDIuMCIsInVzZURhcHBlciI6dHJ1ZX0=", + "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlRGFwcGVyTGVnYWN5RXhhbXBsZUdlbiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCJ9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3JlYWwiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiZGVjaW1hbCJ9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIn19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUifX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSW5zdGFudCJ9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX25vZGFfaW5zdGFudF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJJbnN0YW50In19XSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJ1c2VEYXBwZXIiOnRydWV9", "process": { "cmd": "./dist/LocalRunner" } @@ -179,6 +179,26 @@ "name": "INTEGER" } }, + { + "name": "c_text_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "TEXT" + } + }, + { + "name": "c_integer_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "INTEGER" + } + }, { "name": "c_text_bool_override", "length": -1, @@ -1008,7 +1028,7 @@ "filename": "query.sql" }, { - "text": "INSERT INTO types_sqlite \n(\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_bool_override,\n c_integer_bool_override\n) \nVALUES (?, ?, ?, ?, ?, ?, ?, ?)", + "text": "INSERT INTO types_sqlite \n(\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_noda_instant_override,\n c_integer_noda_instant_override,\n c_text_bool_override,\n c_integer_bool_override\n) \nVALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", "name": "InsertSqliteTypes", "cmd": ":exec", "parameters": [ @@ -1104,6 +1124,36 @@ }, { "number": 7, + "column": { + "name": "c_text_noda_instant_override", + "length": -1, + "table": { + "schema": "main", + "name": "types_sqlite" + }, + "type": { + "name": "TEXT" + }, + "originalName": "c_text_noda_instant_override" + } + }, + { + "number": 8, + "column": { + "name": "c_integer_noda_instant_override", + "length": -1, + "table": { + "schema": "main", + "name": "types_sqlite" + }, + "type": { + "name": "INTEGER" + }, + "originalName": "c_integer_noda_instant_override" + } + }, + { + "number": 9, "column": { "name": "c_text_bool_override", "length": -1, @@ -1118,7 +1168,7 @@ } }, { - "number": 8, + "number": 10, "column": { "name": "c_integer_bool_override", "length": -1, @@ -1195,7 +1245,7 @@ } }, { - "text": "SELECT\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_bool_override,\n c_integer_bool_override\nFROM types_sqlite\nLIMIT 1", + "text": "SELECT\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_noda_instant_override,\n c_integer_noda_instant_override,\n c_text_bool_override,\n c_integer_bool_override\nFROM types_sqlite\nLIMIT 1", "name": "GetSqliteTypes", "cmd": ":one", "columns": [ @@ -1265,6 +1315,28 @@ }, "originalName": "c_integer_datetime_override" }, + { + "name": "c_text_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "TEXT" + }, + "originalName": "c_text_noda_instant_override" + }, + { + "name": "c_integer_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "INTEGER" + }, + "originalName": "c_integer_noda_instant_override" + }, { "name": "c_text_bool_override", "length": -1, @@ -1391,5 +1463,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlRGFwcGVyTGVnYWN5RXhhbXBsZUdlbiIsInVzZURhcHBlciI6dHJ1ZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwidXNlTm9kYVRpbWUiOmZhbHNlLCJvdmVycmlkZXMiOlt7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfaW50ZWdlciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJpbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3JlYWwiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiZGVjaW1hbCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfdGV4dF9kYXRldGltZV9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9kYXRldGltZV9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfYm9vbF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJib29sIiwibm90TnVsbCI6ZmFsc2V9fV0sImRlYnVnUmVxdWVzdCI6ZmFsc2V9" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlRGFwcGVyTGVnYWN5RXhhbXBsZUdlbiIsInVzZURhcHBlciI6dHJ1ZSwib3ZlcnJpZGVEYXBwZXJWZXJzaW9uIjoiIiwidXNlTm9kYVRpbWUiOmZhbHNlLCJvdmVycmlkZXMiOlt7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfaW50ZWdlciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJpbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF92YXJjaGFyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6InN0cmluZyIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3JlYWwiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiZGVjaW1hbCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfdGV4dF9kYXRldGltZV9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9kYXRldGltZV9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJEYXRlVGltZSIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfYm9vbF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJib29sIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X25vZGFfaW5zdGFudF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJJbnN0YW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX25vZGFfaW5zdGFudF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJJbnN0YW50Iiwibm90TnVsbCI6ZmFsc2V9fV0sImRlYnVnUmVxdWVzdCI6ZmFsc2V9" } \ No newline at end of file diff --git a/examples/SqliteDapperLegacyExample/request.message b/examples/SqliteDapperLegacyExample/request.message index aefb4188f338a77aca3bfb2832ba4c3834bc059d..65fbb210a58b999009b0e3cb7c1ea954c5f2f7ed 100644 GIT binary patch delta 641 zcmez7Gb@ytYdyzA=1ok$*(Pq+W!lEJ@mVs{WEN%t!IIR9lK8y*l*IVVyyB9?ypqWm zRh8I1p=?HGX&#)CZp;DP^Vo%0auYN2l%}$8UdU|A$aIZm^8*%tMlnY&ndEp(!wckf zq=ekL zNt;hdd}EZ#5$f|+R|$7UsETjt5ps)SOH0RrX8+3X%tr1F{0%1(CNc0+|J|=3@c@U6Z;dC6f#UCkv7W5(I5wX>KBk z2D3f{JplsB1G9YvPXV)72elCeu?Gs~0h93^8Ivm+fRhU#E0Y}>A+tmp@Bs%|2nP~X z3KWyj0u+ I1CxU)7re|ce*gdg diff --git a/examples/SqliteExample/Models.cs b/examples/SqliteExample/Models.cs index 707ef0f4..89b65235 100644 --- a/examples/SqliteExample/Models.cs +++ b/examples/SqliteExample/Models.cs @@ -1,7 +1,10 @@ // auto-generated by sqlc - do not edit +using NodaTime; +using NodaTime.Extensions; +using NodaTime.Text; using System.Linq; namespace SqliteExampleGen; public readonly record struct Author(int Id, string Name, string? Bio); public readonly record struct Book(int Id, string Name, int AuthorId, string? Description); -public readonly record struct TypesSqlite(int? CInteger, decimal? CReal, string? CText, byte[]? CBlob, string? CTextDatetimeOverride, int? CIntegerDatetimeOverride, string? CTextBoolOverride, int? CIntegerBoolOverride); \ No newline at end of file +public readonly record struct TypesSqlite(int? CInteger, decimal? CReal, string? CText, byte[]? CBlob, string? CTextDatetimeOverride, int? CIntegerDatetimeOverride, string? CTextNodaInstantOverride, int? CIntegerNodaInstantOverride, string? CTextBoolOverride, int? CIntegerBoolOverride); \ No newline at end of file diff --git a/examples/SqliteExample/QuerySql.cs b/examples/SqliteExample/QuerySql.cs index 993439e6..91559ed0 100644 --- a/examples/SqliteExample/QuerySql.cs +++ b/examples/SqliteExample/QuerySql.cs @@ -5,6 +5,9 @@ // ReSharper disable NotAccessedPositionalProperty.Global // ReSharper disable UnusedAutoPropertyAccessor.Global using Microsoft.Data.Sqlite; +using NodaTime; +using NodaTime.Extensions; +using NodaTime.Text; using System; using System.Collections.Generic; using System.Threading.Tasks; @@ -682,8 +685,8 @@ public async Task DeleteAllAuthors() } } - private const string InsertSqliteTypesSql = "INSERT INTO types_sqlite ( c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_bool_override, c_integer_bool_override ) VALUES (@c_integer, @c_real, @c_text, @c_blob, @c_text_datetime_override, @c_integer_datetime_override, @c_text_bool_override, @c_integer_bool_override)"; - public readonly record struct InsertSqliteTypesArgs(int? CInteger, decimal? CReal, string? CText, byte[]? CBlob, DateTime? CTextDatetimeOverride, DateTime? CIntegerDatetimeOverride, bool? CTextBoolOverride, bool? CIntegerBoolOverride); + private const string InsertSqliteTypesSql = "INSERT INTO types_sqlite ( c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_noda_instant_override, c_integer_noda_instant_override, c_text_bool_override, c_integer_bool_override ) VALUES (@c_integer, @c_real, @c_text, @c_blob, @c_text_datetime_override, @c_integer_datetime_override, @c_text_noda_instant_override, @c_integer_noda_instant_override, @c_text_bool_override, @c_integer_bool_override)"; + public readonly record struct InsertSqliteTypesArgs(int? CInteger, decimal? CReal, string? CText, byte[]? CBlob, DateTime? CTextDatetimeOverride, DateTime? CIntegerDatetimeOverride, Instant? CTextNodaInstantOverride, Instant? CIntegerNodaInstantOverride, bool? CTextBoolOverride, bool? CIntegerBoolOverride); public async Task InsertSqliteTypes(InsertSqliteTypesArgs args) { if (this.Transaction == null) @@ -699,6 +702,8 @@ public async Task InsertSqliteTypes(InsertSqliteTypesArgs args) command.Parameters.AddWithValue("@c_blob", args.CBlob ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_text_datetime_override", args.CTextDatetimeOverride != null ? args.CTextDatetimeOverride.Value.ToString("yyyy-MM-dd HH:mm:ss") : (object)DBNull.Value); command.Parameters.AddWithValue("@c_integer_datetime_override", args.CIntegerDatetimeOverride != null ? (int? )new DateTimeOffset(args.CIntegerDatetimeOverride.Value.ToUniversalTime()).ToUnixTimeSeconds() : (object)DBNull.Value); + command.Parameters.AddWithValue("@c_text_noda_instant_override", args.CTextNodaInstantOverride != null ? InstantPattern.CreateWithInvariantCulture("yyyy-MM-dd HH:mm:ss").Format(args.CTextNodaInstantOverride.Value) : (object)DBNull.Value); + command.Parameters.AddWithValue("@c_integer_noda_instant_override", args.CIntegerNodaInstantOverride != null ? (long? )args.CIntegerNodaInstantOverride.Value.ToUnixTimeSeconds() : (object)DBNull.Value); command.Parameters.AddWithValue("@c_text_bool_override", args.CTextBoolOverride != null ? Convert.ToString(args.CTextBoolOverride) : (object)DBNull.Value); command.Parameters.AddWithValue("@c_integer_bool_override", args.CIntegerBoolOverride != null ? (int? )Convert.ToInt32(args.CIntegerBoolOverride) : (object)DBNull.Value); await command.ExecuteNonQueryAsync(); @@ -720,6 +725,8 @@ public async Task InsertSqliteTypes(InsertSqliteTypesArgs args) command.Parameters.AddWithValue("@c_blob", args.CBlob ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_text_datetime_override", args.CTextDatetimeOverride != null ? args.CTextDatetimeOverride.Value.ToString("yyyy-MM-dd HH:mm:ss") : (object)DBNull.Value); command.Parameters.AddWithValue("@c_integer_datetime_override", args.CIntegerDatetimeOverride != null ? (int? )new DateTimeOffset(args.CIntegerDatetimeOverride.Value.ToUniversalTime()).ToUnixTimeSeconds() : (object)DBNull.Value); + command.Parameters.AddWithValue("@c_text_noda_instant_override", args.CTextNodaInstantOverride != null ? InstantPattern.CreateWithInvariantCulture("yyyy-MM-dd HH:mm:ss").Format(args.CTextNodaInstantOverride.Value) : (object)DBNull.Value); + command.Parameters.AddWithValue("@c_integer_noda_instant_override", args.CIntegerNodaInstantOverride != null ? (long? )args.CIntegerNodaInstantOverride.Value.ToUnixTimeSeconds() : (object)DBNull.Value); command.Parameters.AddWithValue("@c_text_bool_override", args.CTextBoolOverride != null ? Convert.ToString(args.CTextBoolOverride) : (object)DBNull.Value); command.Parameters.AddWithValue("@c_integer_bool_override", args.CIntegerBoolOverride != null ? (int? )Convert.ToInt32(args.CIntegerBoolOverride) : (object)DBNull.Value); await command.ExecuteNonQueryAsync(); @@ -748,8 +755,8 @@ public async Task InsertSqliteTypesBatch(List args) } } - private const string GetSqliteTypesSql = "SELECT c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_bool_override, c_integer_bool_override FROM types_sqlite LIMIT 1"; - public readonly record struct GetSqliteTypesRow(int? CInteger, decimal? CReal, string? CText, byte[]? CBlob, DateTime? CTextDatetimeOverride, DateTime? CIntegerDatetimeOverride, bool? CTextBoolOverride, bool? CIntegerBoolOverride); + private const string GetSqliteTypesSql = "SELECT c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_noda_instant_override, c_integer_noda_instant_override, c_text_bool_override, c_integer_bool_override FROM types_sqlite LIMIT 1"; + public readonly record struct GetSqliteTypesRow(int? CInteger, decimal? CReal, string? CText, byte[]? CBlob, DateTime? CTextDatetimeOverride, DateTime? CIntegerDatetimeOverride, Instant? CTextNodaInstantOverride, Instant? CIntegerNodaInstantOverride, bool? CTextBoolOverride, bool? CIntegerBoolOverride); public async Task GetSqliteTypes() { if (this.Transaction == null) @@ -771,8 +778,10 @@ public async Task InsertSqliteTypesBatch(List args) CBlob = reader.IsDBNull(3) ? null : reader.GetFieldValue(3), CTextDatetimeOverride = reader.IsDBNull(4) ? null : DateTime.Parse(reader.GetString(4)), CIntegerDatetimeOverride = reader.IsDBNull(5) ? null : DateTimeOffset.FromUnixTimeSeconds(reader.GetInt32(5)).DateTime, - CTextBoolOverride = reader.IsDBNull(6) ? null : Convert.ToBoolean(reader.GetString(6)), - CIntegerBoolOverride = reader.IsDBNull(7) ? null : Convert.ToBoolean(reader.GetInt32(7)) + CTextNodaInstantOverride = reader.IsDBNull(6) ? null : InstantPattern.CreateWithInvariantCulture("yyyy-MM-dd HH:mm:ss").Parse(reader.GetString(6)).Value, + CIntegerNodaInstantOverride = reader.IsDBNull(7) ? null : Instant.FromUnixTimeSeconds(reader.GetInt32(7)), + CTextBoolOverride = reader.IsDBNull(8) ? null : Convert.ToBoolean(reader.GetString(8)), + CIntegerBoolOverride = reader.IsDBNull(9) ? null : Convert.ToBoolean(reader.GetInt32(9)) }; } } @@ -800,8 +809,10 @@ public async Task InsertSqliteTypesBatch(List args) CBlob = reader.IsDBNull(3) ? null : reader.GetFieldValue(3), CTextDatetimeOverride = reader.IsDBNull(4) ? null : DateTime.Parse(reader.GetString(4)), CIntegerDatetimeOverride = reader.IsDBNull(5) ? null : DateTimeOffset.FromUnixTimeSeconds(reader.GetInt32(5)).DateTime, - CTextBoolOverride = reader.IsDBNull(6) ? null : Convert.ToBoolean(reader.GetString(6)), - CIntegerBoolOverride = reader.IsDBNull(7) ? null : Convert.ToBoolean(reader.GetInt32(7)) + CTextNodaInstantOverride = reader.IsDBNull(6) ? null : InstantPattern.CreateWithInvariantCulture("yyyy-MM-dd HH:mm:ss").Parse(reader.GetString(6)).Value, + CIntegerNodaInstantOverride = reader.IsDBNull(7) ? null : Instant.FromUnixTimeSeconds(reader.GetInt32(7)), + CTextBoolOverride = reader.IsDBNull(8) ? null : Convert.ToBoolean(reader.GetString(8)), + CIntegerBoolOverride = reader.IsDBNull(9) ? null : Convert.ToBoolean(reader.GetInt32(9)) }; } } diff --git a/examples/SqliteExample/request.json b/examples/SqliteExample/request.json index d51d592c..9e6de30c 100644 --- a/examples/SqliteExample/request.json +++ b/examples/SqliteExample/request.json @@ -13,7 +13,7 @@ "codegen": { "out": "examples/SqliteExample", "plugin": "csharp", - "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlRXhhbXBsZUdlbiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCJ9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3JlYWwiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiZGVjaW1hbCJ9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIn19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUifX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX1dLCJ0YXJnZXRGcmFtZXdvcmsiOiJuZXQ4LjAiLCJ1c2VEYXBwZXIiOmZhbHNlfQ==", + "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlRXhhbXBsZUdlbiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCJ9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3JlYWwiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiZGVjaW1hbCJ9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIn19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUifX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSW5zdGFudCJ9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX25vZGFfaW5zdGFudF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJJbnN0YW50In19XSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwidXNlRGFwcGVyIjpmYWxzZX0=", "process": { "cmd": "./dist/LocalRunner" } @@ -179,6 +179,26 @@ "name": "INTEGER" } }, + { + "name": "c_text_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "TEXT" + } + }, + { + "name": "c_integer_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "INTEGER" + } + }, { "name": "c_text_bool_override", "length": -1, @@ -1008,7 +1028,7 @@ "filename": "query.sql" }, { - "text": "INSERT INTO types_sqlite \n(\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_bool_override,\n c_integer_bool_override\n) \nVALUES (?, ?, ?, ?, ?, ?, ?, ?)", + "text": "INSERT INTO types_sqlite \n(\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_noda_instant_override,\n c_integer_noda_instant_override,\n c_text_bool_override,\n c_integer_bool_override\n) \nVALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", "name": "InsertSqliteTypes", "cmd": ":exec", "parameters": [ @@ -1104,6 +1124,36 @@ }, { "number": 7, + "column": { + "name": "c_text_noda_instant_override", + "length": -1, + "table": { + "schema": "main", + "name": "types_sqlite" + }, + "type": { + "name": "TEXT" + }, + "originalName": "c_text_noda_instant_override" + } + }, + { + "number": 8, + "column": { + "name": "c_integer_noda_instant_override", + "length": -1, + "table": { + "schema": "main", + "name": "types_sqlite" + }, + "type": { + "name": "INTEGER" + }, + "originalName": "c_integer_noda_instant_override" + } + }, + { + "number": 9, "column": { "name": "c_text_bool_override", "length": -1, @@ -1118,7 +1168,7 @@ } }, { - "number": 8, + "number": 10, "column": { "name": "c_integer_bool_override", "length": -1, @@ -1195,7 +1245,7 @@ } }, { - "text": "SELECT\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_bool_override,\n c_integer_bool_override\nFROM types_sqlite\nLIMIT 1", + "text": "SELECT\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_noda_instant_override,\n c_integer_noda_instant_override,\n c_text_bool_override,\n c_integer_bool_override\nFROM types_sqlite\nLIMIT 1", "name": "GetSqliteTypes", "cmd": ":one", "columns": [ @@ -1265,6 +1315,28 @@ }, "originalName": "c_integer_datetime_override" }, + { + "name": "c_text_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "TEXT" + }, + "originalName": "c_text_noda_instant_override" + }, + { + "name": "c_integer_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "INTEGER" + }, + "originalName": "c_integer_noda_instant_override" + }, { "name": "c_text_bool_override", "length": -1, @@ -1391,5 +1463,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6IlNxbGl0ZUV4YW1wbGVHZW4iLCJ1c2VEYXBwZXIiOmZhbHNlLCJvdmVycmlkZURhcHBlclZlcnNpb24iOiIiLCJ1c2VOb2RhVGltZSI6ZmFsc2UsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3ZhcmNoYXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfcmVhbCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJkZWNpbWFsIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2Jvb2xfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiYm9vbCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wiLCJub3ROdWxsIjpmYWxzZX19XSwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0OC4wIiwibmFtZXNwYWNlTmFtZSI6IlNxbGl0ZUV4YW1wbGVHZW4iLCJ1c2VEYXBwZXIiOmZhbHNlLCJvdmVycmlkZURhcHBlclZlcnNpb24iOiIiLCJ1c2VOb2RhVGltZSI6ZmFsc2UsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3ZhcmNoYXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoic3RyaW5nIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfcmVhbCIsImNzaGFycF90eXBlIjp7InR5cGUiOiJkZWNpbWFsIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2Jvb2xfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiYm9vbCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfbm9kYV9pbnN0YW50X292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6Ikluc3RhbnQiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfbm9kYV9pbnN0YW50X292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6Ikluc3RhbnQiLCJub3ROdWxsIjpmYWxzZX19XSwiZGVidWdSZXF1ZXN0IjpmYWxzZX0=" } \ No newline at end of file diff --git a/examples/SqliteExample/request.message b/examples/SqliteExample/request.message index b6bd22a58c24e4232458554f5824a1ad03982f45..3dbeef067dc920125b2a68dc7e14b8ac9fd44ded 100644 GIT binary patch delta 639 zcmX@&^CEV63AuC0Cj+f3Nli~JLYG#Z{8xf&Ge6rlLDsvRT$`CD*GfxHek|UA>I@wTNmKz} ziKNXdCB89AWpc0!rDC^xqm;2VHb=$hm!%dJWu~NR6>)F~<>7SPMk#HeH^RK!dJ3iAe$1F{0Y1(CNQ0)_>#+E)UT&I3jZk_Hk4ZDDC{B8djG9|S!C z0?GrkUIkA9vpEN~5e2aa3g!Wm^B9?v>>n$W{uv>&B^vMn1z89O5>=C{A|jJr8Wxja z1_zTk9T^1(5?%@ylm8zVlMfvtvyUB(0R^uH3djMIAs>XZ>>u+1v#KJ#0|LPYvuY+P I1CvoI7lRfuF8}}l diff --git a/examples/SqliteLegacyExample/Models.cs b/examples/SqliteLegacyExample/Models.cs index d07f1dc8..e16c16c2 100644 --- a/examples/SqliteLegacyExample/Models.cs +++ b/examples/SqliteLegacyExample/Models.cs @@ -1,6 +1,9 @@ // auto-generated by sqlc - do not edit namespace SqliteLegacyExampleGen { + using NodaTime; + using NodaTime.Extensions; + using NodaTime.Text; using System.Linq; public class Author @@ -24,6 +27,8 @@ public class TypesSqlite public byte[] CBlob { get; set; } public string CTextDatetimeOverride { get; set; } public int? CIntegerDatetimeOverride { get; set; } + public string CTextNodaInstantOverride { get; set; } + public int? CIntegerNodaInstantOverride { get; set; } public string CTextBoolOverride { get; set; } public int? CIntegerBoolOverride { get; set; } }; diff --git a/examples/SqliteLegacyExample/QuerySql.cs b/examples/SqliteLegacyExample/QuerySql.cs index 604e0b1f..628160f0 100644 --- a/examples/SqliteLegacyExample/QuerySql.cs +++ b/examples/SqliteLegacyExample/QuerySql.cs @@ -7,6 +7,9 @@ namespace SqliteLegacyExampleGen { using Microsoft.Data.Sqlite; + using NodaTime; + using NodaTime.Extensions; + using NodaTime.Text; using System; using System.Collections.Generic; using System.Threading.Tasks; @@ -784,7 +787,7 @@ public async Task DeleteAllAuthors() } } - private const string InsertSqliteTypesSql = "INSERT INTO types_sqlite ( c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_bool_override, c_integer_bool_override ) VALUES (@c_integer, @c_real, @c_text, @c_blob, @c_text_datetime_override, @c_integer_datetime_override, @c_text_bool_override, @c_integer_bool_override)"; + private const string InsertSqliteTypesSql = "INSERT INTO types_sqlite ( c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_noda_instant_override, c_integer_noda_instant_override, c_text_bool_override, c_integer_bool_override ) VALUES (@c_integer, @c_real, @c_text, @c_blob, @c_text_datetime_override, @c_integer_datetime_override, @c_text_noda_instant_override, @c_integer_noda_instant_override, @c_text_bool_override, @c_integer_bool_override)"; public class InsertSqliteTypesArgs { public int? CInteger { get; set; } @@ -793,6 +796,8 @@ public class InsertSqliteTypesArgs public byte[] CBlob { get; set; } public DateTime? CTextDatetimeOverride { get; set; } public DateTime? CIntegerDatetimeOverride { get; set; } + public Instant? CTextNodaInstantOverride { get; set; } + public Instant? CIntegerNodaInstantOverride { get; set; } public bool? CTextBoolOverride { get; set; } public bool? CIntegerBoolOverride { get; set; } }; @@ -811,6 +816,8 @@ public async Task InsertSqliteTypes(InsertSqliteTypesArgs args) command.Parameters.AddWithValue("@c_blob", args.CBlob ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_text_datetime_override", args.CTextDatetimeOverride != null ? args.CTextDatetimeOverride.Value.ToString("yyyy-MM-dd HH:mm:ss") : (object)DBNull.Value); command.Parameters.AddWithValue("@c_integer_datetime_override", args.CIntegerDatetimeOverride != null ? (int? )new DateTimeOffset(args.CIntegerDatetimeOverride.Value.ToUniversalTime()).ToUnixTimeSeconds() : (object)DBNull.Value); + command.Parameters.AddWithValue("@c_text_noda_instant_override", args.CTextNodaInstantOverride != null ? InstantPattern.CreateWithInvariantCulture("yyyy-MM-dd HH:mm:ss").Format(args.CTextNodaInstantOverride.Value) : (object)DBNull.Value); + command.Parameters.AddWithValue("@c_integer_noda_instant_override", args.CIntegerNodaInstantOverride != null ? (long? )args.CIntegerNodaInstantOverride.Value.ToUnixTimeSeconds() : (object)DBNull.Value); command.Parameters.AddWithValue("@c_text_bool_override", args.CTextBoolOverride != null ? Convert.ToString(args.CTextBoolOverride) : (object)DBNull.Value); command.Parameters.AddWithValue("@c_integer_bool_override", args.CIntegerBoolOverride != null ? (int? )Convert.ToInt32(args.CIntegerBoolOverride) : (object)DBNull.Value); await command.ExecuteNonQueryAsync(); @@ -832,6 +839,8 @@ public async Task InsertSqliteTypes(InsertSqliteTypesArgs args) command.Parameters.AddWithValue("@c_blob", args.CBlob ?? (object)DBNull.Value); command.Parameters.AddWithValue("@c_text_datetime_override", args.CTextDatetimeOverride != null ? args.CTextDatetimeOverride.Value.ToString("yyyy-MM-dd HH:mm:ss") : (object)DBNull.Value); command.Parameters.AddWithValue("@c_integer_datetime_override", args.CIntegerDatetimeOverride != null ? (int? )new DateTimeOffset(args.CIntegerDatetimeOverride.Value.ToUniversalTime()).ToUnixTimeSeconds() : (object)DBNull.Value); + command.Parameters.AddWithValue("@c_text_noda_instant_override", args.CTextNodaInstantOverride != null ? InstantPattern.CreateWithInvariantCulture("yyyy-MM-dd HH:mm:ss").Format(args.CTextNodaInstantOverride.Value) : (object)DBNull.Value); + command.Parameters.AddWithValue("@c_integer_noda_instant_override", args.CIntegerNodaInstantOverride != null ? (long? )args.CIntegerNodaInstantOverride.Value.ToUnixTimeSeconds() : (object)DBNull.Value); command.Parameters.AddWithValue("@c_text_bool_override", args.CTextBoolOverride != null ? Convert.ToString(args.CTextBoolOverride) : (object)DBNull.Value); command.Parameters.AddWithValue("@c_integer_bool_override", args.CIntegerBoolOverride != null ? (int? )Convert.ToInt32(args.CIntegerBoolOverride) : (object)DBNull.Value); await command.ExecuteNonQueryAsync(); @@ -865,7 +874,7 @@ public async Task InsertSqliteTypesBatch(List args) } } - private const string GetSqliteTypesSql = "SELECT c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_bool_override, c_integer_bool_override FROM types_sqlite LIMIT 1"; + private const string GetSqliteTypesSql = "SELECT c_integer, c_real, c_text, c_blob, c_text_datetime_override, c_integer_datetime_override, c_text_noda_instant_override, c_integer_noda_instant_override, c_text_bool_override, c_integer_bool_override FROM types_sqlite LIMIT 1"; public class GetSqliteTypesRow { public int? CInteger { get; set; } @@ -874,6 +883,8 @@ public class GetSqliteTypesRow public byte[] CBlob { get; set; } public DateTime? CTextDatetimeOverride { get; set; } public DateTime? CIntegerDatetimeOverride { get; set; } + public Instant? CTextNodaInstantOverride { get; set; } + public Instant? CIntegerNodaInstantOverride { get; set; } public bool? CTextBoolOverride { get; set; } public bool? CIntegerBoolOverride { get; set; } }; @@ -898,8 +909,10 @@ public async Task GetSqliteTypes() CBlob = reader.IsDBNull(3) ? null : reader.GetFieldValue(3), CTextDatetimeOverride = reader.IsDBNull(4) ? (DateTime? )null : DateTime.Parse(reader.GetString(4)), CIntegerDatetimeOverride = reader.IsDBNull(5) ? (DateTime? )null : DateTimeOffset.FromUnixTimeSeconds(reader.GetInt32(5)).DateTime, - CTextBoolOverride = reader.IsDBNull(6) ? (bool? )null : Convert.ToBoolean(reader.GetString(6)), - CIntegerBoolOverride = reader.IsDBNull(7) ? (bool? )null : Convert.ToBoolean(reader.GetInt32(7)) + CTextNodaInstantOverride = reader.IsDBNull(6) ? (Instant? )null : InstantPattern.CreateWithInvariantCulture("yyyy-MM-dd HH:mm:ss").Parse(reader.GetString(6)).Value, + CIntegerNodaInstantOverride = reader.IsDBNull(7) ? (Instant? )null : Instant.FromUnixTimeSeconds(reader.GetInt32(7)), + CTextBoolOverride = reader.IsDBNull(8) ? (bool? )null : Convert.ToBoolean(reader.GetString(8)), + CIntegerBoolOverride = reader.IsDBNull(9) ? (bool? )null : Convert.ToBoolean(reader.GetInt32(9)) }; } } @@ -927,8 +940,10 @@ public async Task GetSqliteTypes() CBlob = reader.IsDBNull(3) ? null : reader.GetFieldValue(3), CTextDatetimeOverride = reader.IsDBNull(4) ? (DateTime? )null : DateTime.Parse(reader.GetString(4)), CIntegerDatetimeOverride = reader.IsDBNull(5) ? (DateTime? )null : DateTimeOffset.FromUnixTimeSeconds(reader.GetInt32(5)).DateTime, - CTextBoolOverride = reader.IsDBNull(6) ? (bool? )null : Convert.ToBoolean(reader.GetString(6)), - CIntegerBoolOverride = reader.IsDBNull(7) ? (bool? )null : Convert.ToBoolean(reader.GetInt32(7)) + CTextNodaInstantOverride = reader.IsDBNull(6) ? (Instant? )null : InstantPattern.CreateWithInvariantCulture("yyyy-MM-dd HH:mm:ss").Parse(reader.GetString(6)).Value, + CIntegerNodaInstantOverride = reader.IsDBNull(7) ? (Instant? )null : Instant.FromUnixTimeSeconds(reader.GetInt32(7)), + CTextBoolOverride = reader.IsDBNull(8) ? (bool? )null : Convert.ToBoolean(reader.GetString(8)), + CIntegerBoolOverride = reader.IsDBNull(9) ? (bool? )null : Convert.ToBoolean(reader.GetInt32(9)) }; } } diff --git a/examples/SqliteLegacyExample/request.json b/examples/SqliteLegacyExample/request.json index cb5b7429..9f3ab8f3 100644 --- a/examples/SqliteLegacyExample/request.json +++ b/examples/SqliteLegacyExample/request.json @@ -13,7 +13,7 @@ "codegen": { "out": "examples/SqliteLegacyExample", "plugin": "csharp", - "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlTGVnYWN5RXhhbXBsZUdlbiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCJ9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3JlYWwiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiZGVjaW1hbCJ9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIn19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUifX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX1dLCJ0YXJnZXRGcmFtZXdvcmsiOiJuZXRzdGFuZGFyZDIuMCIsInVzZURhcHBlciI6ZmFsc2V9", + "options": "eyJkZWJ1Z1JlcXVlc3QiOnRydWUsImdlbmVyYXRlQ3Nwcm9qIjp0cnVlLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlTGVnYWN5RXhhbXBsZUdlbiIsIm92ZXJyaWRlcyI6W3siY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9pbnRlZ2VyIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImludCJ9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmcifX0seyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X3JlYWwiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiZGVjaW1hbCJ9fSx7ImNvbHVtbiI6Iio6Y190ZXh0X2RhdGV0aW1lX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6IkRhdGVUaW1lIn19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUifX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ib29sX292ZXJyaWRlIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImJvb2wifX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSW5zdGFudCJ9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX25vZGFfaW5zdGFudF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJJbnN0YW50In19XSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJ1c2VEYXBwZXIiOmZhbHNlfQ==", "process": { "cmd": "./dist/LocalRunner" } @@ -179,6 +179,26 @@ "name": "INTEGER" } }, + { + "name": "c_text_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "TEXT" + } + }, + { + "name": "c_integer_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "INTEGER" + } + }, { "name": "c_text_bool_override", "length": -1, @@ -1008,7 +1028,7 @@ "filename": "query.sql" }, { - "text": "INSERT INTO types_sqlite \n(\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_bool_override,\n c_integer_bool_override\n) \nVALUES (?, ?, ?, ?, ?, ?, ?, ?)", + "text": "INSERT INTO types_sqlite \n(\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_noda_instant_override,\n c_integer_noda_instant_override,\n c_text_bool_override,\n c_integer_bool_override\n) \nVALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", "name": "InsertSqliteTypes", "cmd": ":exec", "parameters": [ @@ -1104,6 +1124,36 @@ }, { "number": 7, + "column": { + "name": "c_text_noda_instant_override", + "length": -1, + "table": { + "schema": "main", + "name": "types_sqlite" + }, + "type": { + "name": "TEXT" + }, + "originalName": "c_text_noda_instant_override" + } + }, + { + "number": 8, + "column": { + "name": "c_integer_noda_instant_override", + "length": -1, + "table": { + "schema": "main", + "name": "types_sqlite" + }, + "type": { + "name": "INTEGER" + }, + "originalName": "c_integer_noda_instant_override" + } + }, + { + "number": 9, "column": { "name": "c_text_bool_override", "length": -1, @@ -1118,7 +1168,7 @@ } }, { - "number": 8, + "number": 10, "column": { "name": "c_integer_bool_override", "length": -1, @@ -1195,7 +1245,7 @@ } }, { - "text": "SELECT\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_bool_override,\n c_integer_bool_override\nFROM types_sqlite\nLIMIT 1", + "text": "SELECT\n c_integer,\n c_real,\n c_text,\n c_blob,\n c_text_datetime_override,\n c_integer_datetime_override,\n c_text_noda_instant_override,\n c_integer_noda_instant_override,\n c_text_bool_override,\n c_integer_bool_override\nFROM types_sqlite\nLIMIT 1", "name": "GetSqliteTypes", "cmd": ":one", "columns": [ @@ -1265,6 +1315,28 @@ }, "originalName": "c_integer_datetime_override" }, + { + "name": "c_text_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "TEXT" + }, + "originalName": "c_text_noda_instant_override" + }, + { + "name": "c_integer_noda_instant_override", + "length": -1, + "table": { + "name": "types_sqlite" + }, + "type": { + "name": "INTEGER" + }, + "originalName": "c_integer_noda_instant_override" + }, { "name": "c_text_bool_override", "length": -1, @@ -1391,5 +1463,5 @@ } ], "sqlc_version": "v1.30.0", - "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlTGVnYWN5RXhhbXBsZUdlbiIsInVzZURhcHBlciI6ZmFsc2UsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsInVzZU5vZGFUaW1lIjpmYWxzZSwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X2ludGVnZXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9yZWFsIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImRlY2ltYWwiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfYm9vbF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJib29sIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX2Jvb2xfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiYm9vbCIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" + "plugin_options": "eyJvdmVycmlkZURyaXZlclZlcnNpb24iOiIiLCJnZW5lcmF0ZUNzcHJvaiI6dHJ1ZSwidGFyZ2V0RnJhbWV3b3JrIjoibmV0c3RhbmRhcmQyLjAiLCJuYW1lc3BhY2VOYW1lIjoiU3FsaXRlTGVnYWN5RXhhbXBsZUdlbiIsInVzZURhcHBlciI6ZmFsc2UsIm92ZXJyaWRlRGFwcGVyVmVyc2lvbiI6IiIsInVzZU5vZGFUaW1lIjpmYWxzZSwib3ZlcnJpZGVzIjpbeyJjb2x1bW4iOiJHZXRTcWxpdGVGdW5jdGlvbnM6bWF4X2ludGVnZXIiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiaW50Iiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6IkdldFNxbGl0ZUZ1bmN0aW9uczptYXhfdmFyY2hhciIsImNzaGFycF90eXBlIjp7InR5cGUiOiJzdHJpbmciLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiR2V0U3FsaXRlRnVuY3Rpb25zOm1heF9yZWFsIiwiY3NoYXJwX3R5cGUiOnsidHlwZSI6ImRlY2ltYWwiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX2ludGVnZXJfZGF0ZXRpbWVfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiRGF0ZVRpbWUiLCJub3ROdWxsIjpmYWxzZX19LHsiY29sdW1uIjoiKjpjX3RleHRfYm9vbF9vdmVycmlkZSIsImNzaGFycF90eXBlIjp7InR5cGUiOiJib29sIiwibm90TnVsbCI6ZmFsc2V9fSx7ImNvbHVtbiI6Iio6Y19pbnRlZ2VyX2Jvb2xfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiYm9vbCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfdGV4dF9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSW5zdGFudCIsIm5vdE51bGwiOmZhbHNlfX0seyJjb2x1bW4iOiIqOmNfaW50ZWdlcl9ub2RhX2luc3RhbnRfb3ZlcnJpZGUiLCJjc2hhcnBfdHlwZSI6eyJ0eXBlIjoiSW5zdGFudCIsIm5vdE51bGwiOmZhbHNlfX1dLCJkZWJ1Z1JlcXVlc3QiOmZhbHNlfQ==" } \ No newline at end of file diff --git a/examples/SqliteLegacyExample/request.message b/examples/SqliteLegacyExample/request.message index cb12db7c6ef36c301587bddd65fc4feed2cf6ba7..9bab458ea1d63e089d9be56a3c35dec3906240ad 100644 GIT binary patch delta 664 zcmaFn(-q3hwS;3L^CqSbY!kPuGi_ws_#l>P@((6~$@)yJJbC#kiSe0v#U+V(C6f=T zD(QJb*h;mvI@L#OHwOJQ1utEsZRbN#V#e}&Lxk-iUKzM&B|=s1X=HL za&2asJW*P5@^|qDRF^wQNTLcPN+fOGEAfp{DwBg6Wi2~yfXyE&|}IV?WEEVZa8 zGbL54h=W5Y52xc2q|7vMI2>U_BnPKZD3{3O0tu1H=cJq%xi$+*pJHS^$idamH2Hx{ z3#!wx_{DK^zw8M{v3TtMfP^83IbMG#W#IG!Fn}ehaCl;~ulxySrXG&X;>s4xlf6~3 Try6(?xTm5lLNJ}!sA&NJ5jpSx delta 158 zcmV;P0Ac@%Rpv|s3Wo=g1F{0s1(CNW0+a=@;9UX%U6ZdSC6WXv3z7yB1Z`nyZX$^W zvoi!e0RqYcvvLJb0kcg9wGjoe2MXo^lLr}@k{~OS5*i`1IU4W*1z89O5>=DGA|jJ7 z9X1095?+%KBPEkB9Tt Date: Sun, 5 Oct 2025 17:34:10 +0200 Subject: [PATCH 6/6] fix: move package references in .csproj to drivers --- CodeGenerator/CodeGenerator.cs | 2 +- CodeGenerator/Generators/CsprojGen.cs | 70 +++--------------- Drivers/DbDriver.cs | 39 ++++++---- Drivers/MySqlConnectorDriver.cs | 17 +++++ Drivers/NpgsqlDriver.cs | 25 +++++++ Drivers/SqliteDriver.cs | 13 +++- Extensions/DictionaryExtensions.cs | 20 +++++ PluginOptions/Options.cs | 3 - PluginOptions/RawOptions.cs | 3 - .../MySqlConnectorDapperExample.csproj | 4 +- .../MySqlConnectorDapperExample/request.json | 2 +- .../request.message | Bin 26353 -> 26333 bytes .../MySqlConnectorDapperLegacyExample.csproj | 8 +- .../request.json | 2 +- .../request.message | Bin 26387 -> 26367 bytes .../MySqlConnectorExample.csproj | 3 +- examples/MySqlConnectorExample/request.json | 2 +- .../MySqlConnectorExample/request.message | Bin 26337 -> 26317 bytes .../MySqlConnectorLegacyExample.csproj | 7 +- .../MySqlConnectorLegacyExample/request.json | 2 +- .../request.message | Bin 26371 -> 26351 bytes .../NpgsqlDapperExample.csproj | 6 +- examples/NpgsqlDapperExample/request.json | 2 +- examples/NpgsqlDapperExample/request.message | 2 +- .../NpgsqlDapperLegacyExample.csproj | 6 +- .../NpgsqlDapperLegacyExample/request.json | 2 +- .../NpgsqlDapperLegacyExample/request.message | 2 +- examples/NpgsqlExample/NpgsqlExample.csproj | 3 +- examples/NpgsqlExample/request.json | 2 +- examples/NpgsqlExample/request.message | 2 +- .../NpgsqlLegacyExample.csproj | 7 +- examples/NpgsqlLegacyExample/request.json | 2 +- examples/NpgsqlLegacyExample/request.message | 2 +- .../SqliteDapperExample.csproj | 6 +- examples/SqliteDapperExample/request.json | 2 +- examples/SqliteDapperExample/request.message | Bin 10872 -> 10852 bytes .../SqliteDapperLegacyExample.csproj | 6 +- .../SqliteDapperLegacyExample/request.json | 2 +- .../SqliteDapperLegacyExample/request.message | Bin 10906 -> 10886 bytes examples/SqliteExample/SqliteExample.csproj | 3 +- examples/SqliteExample/request.json | 2 +- examples/SqliteExample/request.message | Bin 10856 -> 10836 bytes .../SqliteLegacyExample.csproj | 3 +- examples/SqliteLegacyExample/request.json | 2 +- examples/SqliteLegacyExample/request.message | Bin 10890 -> 10870 bytes .../DefaultSchemaEnum/request.json | 2 +- .../DefaultSchemaEnum/request.message | 2 +- .../SchemaScopedEnum/request.json | 2 +- .../SchemaScopedEnum/request.message | 2 +- 49 files changed, 167 insertions(+), 127 deletions(-) create mode 100644 Extensions/DictionaryExtensions.cs diff --git a/CodeGenerator/CodeGenerator.cs b/CodeGenerator/CodeGenerator.cs index 2b239a03..b094a63a 100644 --- a/CodeGenerator/CodeGenerator.cs +++ b/CodeGenerator/CodeGenerator.cs @@ -85,7 +85,7 @@ private void InitGenerators(GenerateRequest generateRequest) DbDriver = InstantiateDriver(); // initialize file generators - CsprojGen = new(outputDirectory, projectName, namespaceName, Options); + CsprojGen = new(DbDriver, outputDirectory, projectName, namespaceName); QueriesGen = new(DbDriver, namespaceName); ModelsGen = new(DbDriver, namespaceName); UtilsGen = new(DbDriver, namespaceName); diff --git a/CodeGenerator/Generators/CsprojGen.cs b/CodeGenerator/Generators/CsprojGen.cs index 99a1c9a4..345503db 100644 --- a/CodeGenerator/Generators/CsprojGen.cs +++ b/CodeGenerator/Generators/CsprojGen.cs @@ -1,20 +1,14 @@ using Google.Protobuf; +using SqlcGenCsharp.Drivers; using System; +using System.Linq; using File = Plugin.File; namespace SqlcGenCsharp.Generators; -internal class CsprojGen(string outputDirectory, string projectName, string namespaceName, Options options) +internal class CsprojGen(DbDriver dbDriver, string outputDirectory, string projectName, string namespaceName) { - // TODO this logic needs to be moved to the Drivers project - private const string DefaultDapperVersion = "2.1.66"; - private const string DefaultNpgsqlVersion = "8.0.6"; - private const string DefaultMysqlConnectorVersion = "2.4.0"; - private const string DefaultSqliteVersion = "9.0.0"; - private const string DefaultCsvHelperVersion = "33.0.1"; - private const string DefaultSystemTextJsonVersion = "9.0.6"; - public File GenerateFile() { var csprojContents = GetFileContents(); @@ -27,7 +21,11 @@ public File GenerateFile() private string GetFileContents() { - var optionalNullableProperty = options.DotnetFramework.IsDotnetCore() ? Environment.NewLine + " enable" : ""; + var optionalNullableProperty = dbDriver.Options.DotnetFramework.IsDotnetCore() ? Environment.NewLine + " enable" : ""; + var referenceItems = dbDriver.GetPackageReferences() + .Select(p => $""" """) + .JoinByNewLine(); + return $"""