Как подключиться к нескольким базам данных, используя одинаковые запросы - PullRequest
0 голосов
/ 24 февраля 2011

Я занимаюсь разработкой крупномасштабного приложения на 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`

И мы будем использовать вышеупомянутый проект в нашем коде, как этотВесь код Мне просто нужен пример кода или статьи для изучения.

Ответы [ 2 ]

1 голос
/ 25 февраля 2011

Ваш вопрос немного двусмысленный. Однако я буду основывать свой ответ на том, что вы хотите, чтобы ваш код имел доступ к одной физической базе данных, которая настраивается для MySQL, PostGres, Oracle и т. Д.

Генерация общих операторов SQL.

Вместо доступа к библиотеке MySQL для вставки записей создайте оператор SQL и позвольте соединителю выполнить оператор. Это сводит интерфейс к одной маленькой точке: разъему. Мои классы Field и Record настроены на использование шаблона Visitor. Я создаю Посетителей для построения операторов SQL. Это позволяет моему компоненту базы данных быть более универсальным.

Аннотация Соединитель БД.

Создайте свой собственный объект Соединитель как Facade вокруг соединителя изготовителя БД. Сделайте методы универсальными, например, передав строку, содержащую текст SQL. Затем измените ваши компоненты так, чтобы они требовали передачи этого фасада во время строительства или при доступе к базе данных. Наконец, создайте экземпляр этого фасад для связи с конкретными приложениями базы данных, прежде чем использовать какие-либо из ваших компонентов.

Предложения

Я обнаружил, что, имея класс Record , содержащий имя таблицы, я мог бы устранить необходимость в классе Table (который моделирует таблицу базы данных). Добавление и загрузка выполняется моим менеджером баз данных. В своем недавнем прогрессе я реализовал функциональность для подготовленных операторов и полей BLOB.

0 голосов
/ 25 февраля 2011

Предположения:

Предположим, у меня есть две таблицы в моей базе данных

  1. Проект
  2. Документы

Документы

И в настоящее время я поддерживаю только следующие две базы данных:

1) Post Gres

2) Oracle

Реализация:

Я реализую эту логикув следующих трех фазах

1) Адаптер базы данных: только этот класс открыт для внешнего мира, и это содержит указатель на каждый QueryBuilder, эти указатели будут инициализированы в конструкторе этого класса на основе типа БД(который передается в качестве аргумента конструктору)

2) Соединитель БД: этот класс будет отвечать за обработку БД (установить соединение, отключить и т. д.)

3) Построитель запросов: этот разделсодержит класс баса для каждой таблицы в БД, а также содержит конкретные значения для каждой конкретной базы данных

Пример кода (только синопсис)

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

------------------------------------------------------------------------------------------
...