数据层抽象工厂
本文关键字:工厂 抽象 数据 | 更新日期: 2023-09-27 17:55:07
我是开发抽象工厂模式的新手,并希望在数据层创建一个抽象工厂,以帮助我将该层链接到任何其他数据库,例如sql和oracle。你能帮我开发这个任务吗?请注意,数据库的连接字符串将在此层中找到,而不是在演示文稿中找到。
谢谢
编辑
public abstract class Database
{
public string connectionString;
#region Abstract Functions
public abstract IDbConnection CreateConnection();
public abstract IDbCommand CreateCommand();
public abstract IDbConnection CreateOpenConnection();
public abstract IDbCommand CreateCommand(string commandText, IDbConnection connection);
public abstract IDbCommand CreateStoredProcCommand(string procName, IDbConnection connection);
public abstract IDataParameter CreateParameter(string parameterName, object parameterValue);
#endregion
}
public class SQLDatabase : Database
{
public override IDbConnection CreateConnection()
{
return new SqlConnection(connectionString);
}
public override IDbCommand CreateCommand()
{
return new SqlCommand();
}
public override IDbConnection CreateOpenConnection()
{
SqlConnection connection = (SqlConnection)CreateConnection();
connection.Open();
return connection;
}
public override IDbCommand CreateCommand(string commandText, IDbConnection connection)
{
SqlCommand command = (SqlCommand)CreateCommand();
command.CommandText = commandText;
command.Connection = (SqlConnection)connection;
command.CommandType = CommandType.Text;
return command;
}
public override IDbCommand CreateStoredProcCommand(string procName, IDbConnection connection)
{
SqlCommand command = (SqlCommand)CreateCommand();
command.CommandText = procName;
command.Connection = (SqlConnection)connection;
command.CommandType = CommandType.StoredProcedure;
return command;
}
public override IDataParameter CreateParameter(string parameterName, object parameterValue)
{
return new SqlParameter(parameterName, parameterValue);
}
}
这是我创建的两个类。
该功能已存在。
将连接字符串添加到 app/webb.config:
<connectionStrings>
<add name="TheDatabase" providerName="System.Data.OleDb" connectionString="Provider=OraOLEDB.Oracle.1;Persist Security Info=False;User Id=xxx;Password=yyy;Data Source=zzzz;Extended Properties="/>
</connectionStrings>
使用工厂构建连接:
var connectionString = ConfigurationManager.ConnectionStrings["TheDatabase"];
var providerName = connectionString.ProviderName;
var factory = DbProviderFactories.GetFactory(providerName);
获取连接:
var connection = factory.CreateConnection();
获取命令:
var command == connection.CreateCommand();
您唯一需要做的就是在app/web.config中切换驱动程序。无需进行其他更改。
更新
public class Database
{
public static IDbConnection CreateOpenConnection()
{
var connectionString = ConfigurationManager.ConnectionStrings["TheDatabase"];
var providerName = connectionString.ProviderName;
var factory = DbProviderFactories.GetFactory(providerName);
var connection = factory.CreateConnection();
connection.Open();
return connection;
}
}
class FlowerManager : DataWorker
{
public static void GetFlowers()
{
using (IDbConnection connection = Database.CreateOpenConnection())
{
using (IDbCommand command = connection.CreateCommand("SELECT * FROM FLOWERS", connection))
{
using (IDataReader reader = command.ExecuteReader())
{
// ...
}
}
}
}
}
许多必需的功能可以从以下位置获得
System.Data.Common.DbProviderFactories
您可以在其中获取由大多数 dotnet 数据库提供程序实现的System.Data.Common.DbProviderFactory
项。
更新:
如果你正在寻找工作数据库工厂的例子,请参阅源代码
- queryexpress一个工作数据库查询GUI,
- QueryExplus QueryExpress 的一个分支
- mygeneration是一个代码生成器,可以连接到许多不同的数据库
- NHibernate与复杂的驱动程序模式,适用于许多数据库
我不会有"createcommand"或"createconnection"方法。
更好的方法是让每个访问方法(如"GetAccounts")处理自己的连接/命令实例化。
连接和命令对象实现 IDisposable。 因此,最好使用使用语句,在其中根据需要创建和处置这些语句。 你现在拥有它的方式可能会导致大量的内存问题。
此外,与在需要创建这些参数的代码中仅调用"new SqlParameter"相比,CreateParameter 方法似乎没有提供任何真正的好处。
我会做以下几点:
public interface IDbAccess {
String ConnectionString;
Collection<Account> GetAccountsById(Int32 id);
Boolean StoreAccount(Account acct);
}
public class SqlDatabase : IDbAccess {
public String ConnectionString {get; set;}
public SqlDatabase(String connection) {
ConnectionString = connection;
}
public Collection<Account> GetAccountsById(Int32 id) {
using (SqlConnection connect = new SqlConnection(ConnectionString)) {
using (SqlCommand cmd = new SqlCommand(connect)) {
/// etc.
}
}
}
}
这样,您的数据层就特定于您提供的功能。 已经有很好的数据库访问包装器,如企业库。 您正在采取的方法不会增加任何内容并引入错误。
此外,这种方法意味着您可以实现非数据库提供程序,如 XML、Web 服务等,而无需更改代码。
人们,我知道这是旧帖子,但我想与您分享一些东西。
企业库和 OleDb 有一些问题,当您想插入大于 32k 的图像时,它会抛出异常,所以 de 解决这个问题我已经完成了:
创建一个可以调用的项目CustomProvider
创建一个类,您将调用该类数据库
public abstract class Database
{
public string ConnectionString { get; set; } // Preciso uma variavel para guardar o ConnectionString
public IDbConnection Connection { get; set; }
//public abstract string ProviderName { get; } // Preciso uma variavel para guardar o ConnectionString
//public abstract IDbConnection CreateConnection(string ConnectionString);
public abstract IDbConnection CreateConnection(); // Preciso um Metodo Abstract para CreateConnection Para Tratar da Connection
public abstract IDbCommand CreateCommand();
}
}
- 创建 Seccond 类
OracleDatabase.cs
创建三类
SQLDatabase.cs
public class OracleDatabase : Database { public override IDbConnection CreateConnection() { return new OracleConnection(ConnectionString); } public override IDbCommand CreateCommand() { return new OracleCommand(); } public override IDbConnection CreateOpenConnection() { OracleConnection connection = (OracleConnection)CreateConnection(); connection.Open(); return connection; } public override IDbCommand CreateCommand(string commandText, IDbConnection connection) { OracleCommand command = (OracleCommand)CreateCommand(); command.CommandText = commandText; command.Connection = (OracleConnection)connection; command.CommandType = CommandType.Text; return command; } }
公共类 SQLDatabase : 数据库 {
public override IDbConnection CreateConnection() { return new SqlConnection(ConnectionString); } public override IDbCommand CreateCommand() { return new SqlCommand(); } public override IDbConnection CreateOpenConnection() { SqlConnection connection = (SqlConnection)CreateConnection(); connection.Open(); return connection; } public override IDbCommand CreateCommand(string commandText, IDbConnection connection) { SqlCommand command = (SqlCommand)CreateCommand(); command.CommandText = commandText; command.Connection = (SqlConnection)connection; command.CommandType = CommandType.Text; return command; } public override IDbCommand CreateStoredProcCommand(string procName, IDbConnection connection) { SqlCommand command = (SqlCommand)CreateCommand(); command.CommandText = procName; command.Connection = (SqlConnection)connection; command.CommandType = CommandType.StoredProcedure; return command; } }
然后在节目中
Database db = Factory.CreateDatabase("ConnectionString"); try { using (IDbConnection w_connection = db.Connection) { w_connection.Open(); IDbTransaction transation = w_connection.BeginTransaction(); IDbCommand dbcomand = db.CreateStoredProcCommand("INSERTTEST"); db.AddInParameter(dbcomand, "@ATTCH", DbType.Binary, bytes); db.ExecuteNonQuery(dbcomand, transation); transation.Commit(); } } catch (Exception) { } }
必须重写主类中所有定义的方法
创建
Factory.cs
public static Database CreateDatabase(string ConnectionString) { //var Conn = ConfigurationManager.ConnectionStrings[ConnectionString].ToString(); if (string.IsNullOrEmpty(ConnectionString)) throw new Exception("Connectionstring Not Found" + ConnectionString); Database db = null; if (ConfigurationManager.ConnectionStrings[ConnectionString].ProviderName.Contains("Oracle")) { db = new OracleDatabase(); db.ConnectionString = GetConnectionString(ConnectionString); db.Connection = db.CreateConnection(); } else { db = new SQLDatabase(); db.ConnectionString = GetConnectionString(ConnectionString); db.Connection = db.CreateConnection(); } return db; }