DbCommand 和参数化 SQL、ORACLE 与 SQL Server
我有一个应用程序,除其他外,它将各种数据存储到数据库中。 数据库可能是 ORACLE 或 SQL Server。 SQL 是根据配置和执行期间获取的值动态创建的。
通过使用 DbProviderFactory,我的数据库方法能够与 ORACLE 或 SQL Server 一起使用,而无需为任何数据库编写自定义代码,除了一件事;参数/绑定变量。对于 ORACLE,我需要使用 ":ParameterName"
,而对于 SQL Server,我需要使用 "@ParameterName"
。有什么办法让这个通用吗?
示例代码:
public class DbOperations
{
private DbProviderFactory m_factory;
private DbConnection m_CN;
...
private void InsertToDb(ValueType[] values, ColumnType[] columns)
{
DbCommand Cmd = m_factory.CreateCommand();
Cmd.Connection = m_CN;
StringBuilder sql = new StringBuilder();
sql.Append("INSERT INTO ");
sql.Append(DestinationTable);
sql.Append(" (");
for (int i = 0; i < columns.Length; i++)
{
sql.Append(columns[i].ColumnName);
if (i < columns.Length - 1)
sql.Append(", ");
}
sql.Append(") VALUES (");
for (int i = 0; i < values.Length; i++)
{
//sql.Append(String.Format(":{0}", columns[i].ColumnName)); //ORACLE
sql.Append(String.Format("@{0}", columns[i].ColumnName)); // SQL Server
}
DbParameter param = m_factory.CreateParameter();
param.Direction = ParameterDirection.Input;
param.ParameterName = columns[i].ColumnName;
param.Value = values[i];
Cmd.Parameters.Add(param);
if (i < columns.Length - 1)
sql.Append(", ");
}
sql.Append(")");
Cmd.CommandText = sql.ToString();
Cmd.ExecuteNonQuery();
}
I have an application that will, among other things, store various data into a database.
The database might be ORACLE or SQL Server. The SQL is created dynamically based on configuration and values picked up during execution.
By using DbProviderFactory my db methods are able to work with either ORACLE or SQL Server without writing custom code for any of the databases, except from one thing; parameters/bind variables. For ORACLE I need to use ":ParameterName"
whereas for SQL Server I need to use "@ParameterName"
. Is there any way to make this generic?
Sample code:
public class DbOperations
{
private DbProviderFactory m_factory;
private DbConnection m_CN;
...
private void InsertToDb(ValueType[] values, ColumnType[] columns)
{
DbCommand Cmd = m_factory.CreateCommand();
Cmd.Connection = m_CN;
StringBuilder sql = new StringBuilder();
sql.Append("INSERT INTO ");
sql.Append(DestinationTable);
sql.Append(" (");
for (int i = 0; i < columns.Length; i++)
{
sql.Append(columns[i].ColumnName);
if (i < columns.Length - 1)
sql.Append(", ");
}
sql.Append(") VALUES (");
for (int i = 0; i < values.Length; i++)
{
//sql.Append(String.Format(":{0}", columns[i].ColumnName)); //ORACLE
sql.Append(String.Format("@{0}", columns[i].ColumnName)); // SQL Server
}
DbParameter param = m_factory.CreateParameter();
param.Direction = ParameterDirection.Input;
param.ParameterName = columns[i].ColumnName;
param.Value = values[i];
Cmd.Parameters.Add(param);
if (i < columns.Length - 1)
sql.Append(", ");
}
sql.Append(")");
Cmd.CommandText = sql.ToString();
Cmd.ExecuteNonQuery();
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
我很久以前就接受了这个问题的答案,但由于某种原因,答案不再在这里......所以我想我需要回答我自己的问题。
我所做的是创建一个parambuilder类:
我创建一个ParamBuilder类型的成员变量:
然后在我使用参数的方法中,我使用它如下:
I accepted an answer for this question long ago, but for some reason that answer is no longer here... So I guess I need to answer my own question.
What I did was to create a parambuilder class:
I create a member variable of the ParamBuilder type:
Then in the method where I use parameters, I use it as follows:
创建一个抽象属性来获取“values”循环中使用的格式字符串。
Make an abstract property to get the format string used in the "values" loop.
如果你想要快速而肮脏的话,只需添加另一个选项即可。
Just throwing in another option if you want quick and dirty.