我正在用C ++开发一个大型应用程序。该应用程序还维护一个数据库(目前我正在使用MySQL),我使用OTL进行数据库连接。现在我想做的是为使用来自多个供应商的数据库提供支持。例如,用户A使用MySQL,用户B使用PostGres。我认为在C ++中实现它但由于缺乏经验而没有提出任何可能的解决方案。
我想要达到的目标是:
会有一个单独的VC项目处理数据库,并假设它包含以下文件:
DataAccessLayer.cpp //This will main entry point of the project
Product.cpp //This deals with product table
Customer.cpp // This deals with Customer table
Orders.cpp //This deals with Orders table
. . . and many more // I want to have one cpp file per Database table`
我们将在我们的代码中使用上述项目
DataAccessLayer oDataAccessLayer;
oDataAccessLayer.Connect(); // This will connect to specified database, it might b some abstract class and have concrete class for each supported DB
oDataAccessLayer.Products.Search(//Some parameters here e.g prod id to b search);//I don't want to write search query again again for each database, This function will execute the query in specific database
oDataAccessLayer.Customers.Add(//Parameter)//Same is the case here I don't want to write ADd query for each supported database
oDataAccessLayer.Disconnect();
我不想要整个代码我只需要一些示例代码或相关文章来研究。
答案 0 :(得分:1)
你的问题有点含糊不清。但是,我的答案基于您希望代码访问一个物理数据库,可以配置为MySQL,PostGres,Oracle等。
不是访问MySQL库来插入记录,而是构建一个SQL语句并让连接器执行该语句。这将界面缩小到一个小点:连接器。我已将Field
和Record
类设置为使用Visitor
模式。我创建了 Visitors 来构建SQL语句。这使我的数据库组件更通用。
在数据库制造商的连接器周围创建一个自己的Connector对象Facade
。使方法通用,例如传递包含SQL文本的字符串。接下来,更改组件以在构造期间或访问数据库时要求传递此 facade 。最后,在使用任何组件之前,创建此 facade 的实例以与特定数据库应用程序进行通信。
我发现让 Record 类包含表名,我可以省去Table类(它为数据库表建模)。附加和加载由我的数据库管理器类处理。在我最近的进展中,我实现了预处理语句和BLOB字段的功能。
答案 1 :(得分:0)
假设我在数据库中有两个表
文档
目前我只支持关注两个数据库:
1)发布Gres
2)Oracle
我在以下三个阶段实施这个逻辑
1)数据库适配器:只有这个类暴露给外部世界并且它包含指向每个QueryBuilder的指针,这些指针将在DB类型的基础上在该类的构造函数中初始化(作为参数传递)到构造函数)
2)DB Connector:此类将负责DB处理(建立连接,断开连接等)
3)查询生成器:此部分包含DB中每个表的基础类,并且还包含每个特定数据库的具体calss
DBAdapter.h
DBAdapter(enum DBType, string ConnectionString);//constructor
IntializeDBConnectAndQueryBuilder();
Project *pProject;
Docs *pDocs;
//----------------------------------------------------------------------------------------
DBAdapter.cpp
DBAdapter(enum DBType, string ConnectionString)//constructor
{
swithc (DBType)
{
case enPostGres:
pProject = new Project_PostGres();
pDocs = new Docs_PostGres();
break;
};
}
DBConnector.h
virtual Connect()=0; //pure virtual
IsConnected()=0;//pure virtual
Disconnect()=0; //pure virtual
//------------------------------------------------------------------------------------------
DBConnector_PostGres.cpp: DBConnector
Connect()
{ //Implementation specific to postgres goes here}
IsConnected()
{ //Implementation specific to postgres goes here}
Disconnect()
{ //Implementation specific to postgres goes here}
//------------------------------------------------------------------------------------------
DBConnector_OracleGres.cpp: DBConnector
Connect()
{ //Implementation specific to oracle goes here}
IsConnected()
{ //Implementation specific to oracle goes here}
Disconnect()
{ //Implementation specific to oracle goes here}
//------------------------------------------------------------------------------------------
Project.h
virtual int AddProject();
virtual int DeleteProject();
virtual int IsProjectTableExist();
DBConnector *pDBConnector; // This pointer will be initalized in all concrete classes
//------------------------------------------------------------------------------------------
Project.cpp
int AddProject()
{
//Query for adding Project is same for all databases
}
int DeleteProject()
{
//Query for deleting Project is same for all databases
}
//------------------------------------------------------------------------------------------
Project_PostGres.cpp : Project
Project_PostGres() // Constructor
{
pDBConnector = new DBConnector_PostGres();
}
int IsProjectTableExist()
{
//Query specific to postgres goes here
}
Project
//------------------------------------------------------------------------------------------
Project_Oracle.cpp : Project
{
//Query specific to oracle goes here
}
//. . . and so on for other databases
//------------------------------------------------------------------------------------------
//Same number of files with same logic will also be created for Docs Table
------------------------------------------------------------------------------------------