From 8735356b6962c2d4922b5af2594569a337741fbe Mon Sep 17 00:00:00 2001 From: Chris Donnelly Date: Tue, 21 Aug 2018 18:01:53 -0500 Subject: [PATCH] Modifying Insert/Update calls to not use result sets. --- Dapper.Database/Adapters/OracleAdapter.cs | 82 +++++++++++------------ 1 file changed, 40 insertions(+), 42 deletions(-) diff --git a/Dapper.Database/Adapters/OracleAdapter.cs b/Dapper.Database/Adapters/OracleAdapter.cs index 602f0af..337d1f6 100644 --- a/Dapper.Database/Adapters/OracleAdapter.cs +++ b/Dapper.Database/Adapters/OracleAdapter.cs @@ -30,17 +30,19 @@ public override bool Insert(IDbConnection connection, IDbTransaction transaction { cmd.Append($" RETURNING {EscapeColumnList(tableInfo.GeneratedColumns)} INTO {EscapeParameters(tableInfo.GeneratedColumns)}"); - var vals = connection.Query(cmd.ToString(), entityToInsert, transaction, commandTimeout: commandTimeout).ToList(); + // Oracle does not return RETURNING values in a result set; rather, it returns them as InputOutput parameters. + // We need to wrap the incoming object in a DynamicParameters collection to get at the values. + var parameters = new DynamicParameters(entityToInsert); + var count = connection.Execute(cmd.ToString(), parameters, transaction, commandTimeout: commandTimeout); - if (!vals.Any()) return false; + if (count == 0) return false; - var rvals = ((IDictionary)vals[0]); - - foreach (var key in rvals.Keys) + foreach (var column in tableInfo.GeneratedColumns) { - var rval = rvals[key]; - var p = tableInfo.GeneratedColumns.Single(gp => gp.ColumnName.Equals(key, StringComparison.OrdinalIgnoreCase)).Property; - p.SetValue(entityToInsert, Convert.ChangeType(rval, p.PropertyType), null); + var property = column.Property; + var paramName = parameters.ParameterNames.Single(p => column.ColumnName.Equals(p, StringComparison.OrdinalIgnoreCase)); + + property.SetValue(entityToInsert, Convert.ChangeType(parameters.Get(paramName), property.PropertyType), null); } return true; @@ -70,17 +72,19 @@ public override bool Update(IDbConnection connection, IDbTransaction transaction { cmd.Append($" RETURNING {EscapeColumnList(tableInfo.GeneratedColumns)} INTO {EscapeParameters(tableInfo.GeneratedColumns)}"); - var vals = connection.Query(cmd.ToString(), entityToUpdate, transaction, commandTimeout: commandTimeout).ToList(); + // Oracle does not return RETURNING values in a result set; rather, it returns them as InputOutput parameters. + // We need to wrap the incoming object in a DynamicParameters collection to get at the values. + var parameters = new DynamicParameters(entityToUpdate); + var count = connection.Execute(cmd.ToString(), parameters, transaction, commandTimeout: commandTimeout); - if (!vals.Any()) return false; + if (count == 0) return false; - var rvals = ((IDictionary)vals[0]); - - foreach (var key in rvals.Keys) + foreach (var column in tableInfo.GeneratedColumns) { - var rval = rvals[key]; - var p = tableInfo.GeneratedColumns.Single(gp => gp.ColumnName.Equals(key, StringComparison.OrdinalIgnoreCase)).Property; - p.SetValue(entityToUpdate, Convert.ChangeType(rval, p.PropertyType), null); + var property = column.Property; + var paramName = parameters.ParameterNames.Single(p => column.ColumnName.Equals(p, StringComparison.OrdinalIgnoreCase)); + + property.SetValue(entityToUpdate, Convert.ChangeType(parameters.Get(paramName), property.PropertyType), null); } return true; @@ -108,19 +112,19 @@ public override async Task InsertAsync(IDbConnection connection, IDbTransa { cmd.Append($" RETURNING {EscapeColumnList(tableInfo.GeneratedColumns)} INTO {EscapeParameters(tableInfo.GeneratedColumns)}"); - var rslt = await connection.QueryAsync(cmd.ToString(), entityToInsert, transaction, commandTimeout: commandTimeout); + // Oracle does not return RETURNING values in a result set; rather, it returns them as InputOutput parameters. + // We need to wrap the incoming object in a DynamicParameters collection to get at the values. + var parameters = new DynamicParameters(entityToInsert); + var count = await connection.ExecuteAsync(cmd.ToString(), parameters, transaction, commandTimeout: commandTimeout); - var vals = rslt.ToList(); + if (count == 0) return false; - if (!vals.Any()) return false; - - var rvals = ((IDictionary)vals[0]); - - foreach (var key in rvals.Keys) + foreach (var column in tableInfo.GeneratedColumns) { - var rval = rvals[key]; - var p = tableInfo.GeneratedColumns.Single(gp => gp.ColumnName.Equals(key, StringComparison.OrdinalIgnoreCase)).Property; - p.SetValue(entityToInsert, Convert.ChangeType(rval, p.PropertyType), null); + var property = column.Property; + var paramName = parameters.ParameterNames.Single(p => column.ColumnName.Equals(p, StringComparison.OrdinalIgnoreCase)); + + property.SetValue(entityToInsert, Convert.ChangeType(parameters.Get(paramName), property.PropertyType), null); } return true; @@ -150,19 +154,19 @@ public override async Task UpdateAsync(IDbConnection connection, IDbTransa { cmd.Append($" RETURNING {EscapeColumnList(tableInfo.GeneratedColumns)} INTO {EscapeParameters(tableInfo.GeneratedColumns)}"); - var rslt = await connection.QueryAsync(cmd.ToString(), entityToUpdate, transaction, commandTimeout: commandTimeout); + // Oracle does not return RETURNING values in a result set; rather, it returns them as InputOutput parameters. + // We need to wrap the incoming object in a DynamicParameters collection to get at the values. + var parameters = new DynamicParameters(entityToUpdate); + var count = await connection.ExecuteAsync(cmd.ToString(), parameters, transaction, commandTimeout: commandTimeout); - var vals = rslt.ToList(); + if (count == 0) return false; - if (!vals.Any()) return false; - - var rvals = ((IDictionary)vals[0]); - - foreach (var key in rvals.Keys) + foreach (var column in tableInfo.GeneratedColumns) { - var rval = rvals[key]; - var p = tableInfo.GeneratedColumns.Single(gp => gp.ColumnName.Equals(key, StringComparison.OrdinalIgnoreCase)).Property; - p.SetValue(entityToUpdate, Convert.ChangeType(rval, p.PropertyType), null); + var property = column.Property; + var paramName = parameters.ParameterNames.Single(p => column.ColumnName.Equals(p, StringComparison.OrdinalIgnoreCase)); + + property.SetValue(entityToUpdate, Convert.ChangeType(parameters.Get(paramName), property.PropertyType), null); } return true; @@ -195,11 +199,5 @@ public override string EscapeTableName(TableInfo tableInfo) => /// Returns the format for parameter /// public override string EscapeParameter(string value) => $":{value}"; - - public override string DeleteQuery(TableInfo tableInfo, string sql) - { - var x = base.DeleteQuery(tableInfo, sql); - return x; - } } }