Продолжение статьи Object-relational mapping класс для работы с базой данных – общие сведения. Подробно рассматривается базовый для всех остальных классов TCommonObject , который реализует основные общие методы и свойства объектов.
Как уже было сказано TCommonEngine наследуется от TCommonObject и реализует общие методы для реализации доступа к единичной записи в базе данных. В нем перегружаются виртуальные методы базового класса TCommonObject и добавляются новые методы и свойства необходимые для базового класса доступа к единичной записи в базе данных. По сравнению с родительским классом добавлены следующие методы и свойства:
function GetSelectedFields(AFields: TFields): Boolean; virtual;
function Insert: Boolean; virtual;
function Update: Boolean; virtual;
function FillParamsInsertOrUpdate(AParameters: TParameters): Boolean; virtual;
function FillParametersSelectOrdelete(AParameters: TParameters): Boolean; virtual;
property InsertString: string
property UpDateString: string
property SelectString: string
property DeleteString: string
property TableName: string .
Подробнее об этих свойствах виртуальных и перегруженных методах:
Свойство InsertString ( string ) – содержит SQL – запрос для вставки одной записи в БД. Поле id не надо указывать в запросе, оно будет добавлено при выполнении запроса и заполнено идентификатором вставленной записи, и возвращено в свойство класса ID. Идентификатор вставленной записи определяется по свойству TableName. Данная строка заполняется в конструкторе наследуемого класса.
Свойство UpDateString ( string ) – содержит SQL – запрос для вставки одной записи в БД. Данная строка заполняется в конструкторе наследуемого класса.
Свойство SelectString ( string ) – содержит SQL – запрос для выбора полей единичной записи из базы данных. Данная строка заполняется в конструкторе наследуемого класса.
Свойство DeleteString ( string ) – содержит SQL – запрос для удаления единичной записи из базы данных. Данная строка заполняется в конструкторе наследуемого класса.
Свойство TableName ( string ) – храниться название таблицы, в которой хранятся поля единичной записи. Данная строка заполняется в конструкторе наследуемого класса.
constructor Create;override; – конструктор класса в нем обязательно необходимо вызывать конструктор родителя (inherited Create;), что бы проинициализировать isDeleted:= False; ID:= -1; и заполнить свойства TableName, InsertString, UpDateString, SelectString, DeleteString.
function GetByID: Boolean; override; – выполняет выбор значений из базы данных. Перед вызовом этой функции необходимо заполнить соответствующие ключевые поля. Для реализации выбора данных вызываются функции GetSelectedFields, FillParametersSelectOrdelete. Имеет смысл заполнять в наследуемом классе
Result:= inherited GetByID;
function GetSelectedFields (AFields: TFields): Boolean; virtual; – выполняет заполнение свойств класса значениями из полей, которые возвращаются из базы данных при выполнении запроса SelectString. В качетве парметра функция принимает список полей, которые возвращает запрос. Имеет смысл заполнять в наследуемом классе
Result:= inherited GetSelectedFields(AFields);
После чего явно прописать присвоение советующих полей в соответствующие свойства.
function GetAdditionalInfo: Boolean; override; – выполняет заполнение свойств, которые не выбираются из таблицы, которая записана в свойстве TableName, или же они вычисляются на основе существующих свойств. вызывается не зависимо от GetByID, но не ранее т.к. все остальные свойства могут быть не заполнены. Имеет смысл заполнять в наследуемом классе
Result:= inherited GetAdditionalInfo;
function Insert: Boolean; virtual; – Выполняет вставку в таблицу записи, в ней же происходит дополнение InsertString параметром id и возврат этого параметра в свойство класса id идентификатора вставленной записи. Параметры для вставки берутся из соответствующих свойств наследуемого класса и заполняются они в процедуре FillParamsInsertOrUpdate используя параметр AParameters. Значение id заполнять не нужно, оно будет заполнено автоматически. Если при вставке не требуется делать каких-либо дополнительных действий, то в наследуемом классе имеет смысл заполнять в наследуемом классе
Result:= inherited Insert;
function Update: Boolean; virtual; – выполняет обновление записи в базе данных. Параметры для вставки берутся из соотвествующих свойств наследуемого класса и запонюябтсяони в процедуре FillParamsInsertOrUpdate используя параметр AParameters. Значение id заполнять не нужно, оно будет заполнено автоматически. Если при вставке не требуется делать каких-либо дополнительных действий, то в наследуемом классе имеет смысл заполнять в наследуемом классе
Result:= inherited Update;
function Delete: Boolean; override; – выполняет удаление записи из базы данных вне зависимости от значения свойства isDeleted. Параметры для удаления заполняются в процедуре FillParametersSelectOrdelete. В наследуемом классе имеет смысл заполнить
Result:= inherrited Delete;
function Save(ASaveItems: Boolean = True): Boolean; override; – Выполняет сохранение класс по его параметрам. Если установлено true свойство isDeleted, то вызывается процедура Delete, в противном случае если id > 0, то вызывается процедура Update. В наслеудемо классе имеет смысл заполнить
Result:= inherrited Save;
function FillParamsInsertOrUpdate(AParameters: TParameters): Boolean; virtual; – В наследуемом классе заполняем параметры отличие от id значениями свойств класса при вставке или обновлении записи. В наследуемо классе обазятельно необходимо заполнять
Result:= inherited bFillParamsInsertOrUpdate(AParameters);
function FillParametersSelectOrdelete(AParameters: TParameters): Boolean; virtual; – заполняем параметры отличные от id значениями свойств класса при выборке полей или удаления единичной записи. В наследуемо классе обязательно необходимо заполнять
Result:= inherited bFillParamsInsertOrUpdate(AParameters);
Таким образом, для реализации наследника от TCommonEngine необходимо перегрузить в наследуемом классе следующие функции:
{—- Base function ——————————————————}
constructor Create;override; // *
function GetByID: Boolean; override;
function GetSelectedFields(AFields: TFields): Boolean;override; // *
function GetAdditionalInfo: Boolean; override;
function Insert: Boolean; override;
function Update: Boolean; override;
function Delete: Boolean; override;
function FillParamsInsertOrUpdate(AParameters: TParameters): Boolean; override;// *
function FillParametersSelectOrdelete(AParameters: TParameters): Boolean; override; // *
{—- Additional function ————————————————}
{—- Fields ————————————————————-}
{—- Additional Fields ————————————————–}
Функции, отмеченные звездочкой, обязательно перегружать, и дополнять своим кодом.
Небольшой пример реализации данного класса.
constructor TTemp.Create; begin inherited; TableName:= 'tbl_Temp'; InsertString:= 'INSERT INTO tbl_Temp ' +' (Sid, Name) ' +'VALUES ' +' (:Sid,:Name);'; UpDateString:= 'UPDATE tbl_Temp ' +' SET Name = :Name ' +'WHERE id = :id and sid = :sid'; SelectString:= 'SELECT id, Sid, Name ' +'FROM tbl_Invoices ' +'Where id = :id and Sid = :Sid'; DeleteString:= 'Delete From tbl_Temp where id = :id and sid = :sid'; end; function TTemp.GetSelectedFields(AFields: TFields): Boolean; begin Result:= inherited GetSelectedFields(AFields); with AFields do begin Sid:= FieldByName('Sid').AsInteger; FName:= FieldByName('Name').AsString; end; end; function TTemp.FillParamsInsertOrUpdate(AParameters: TParameters): Boolean; begin Result:= inherited FillParamsInsertOrUpdate(AParameters); with AParameters do begin // 2 ParamByName('Sid').DataType:= ftInteger; ParamByName('Sid').Value:= Sid; // 3 ParamByName('Name').DataType:= ftString; ParamByName('Name').Value:= Name; end; end; function TTemp.FillParametersSelectOrdelete( AParameters: TParameters): Boolean; begin Result:= inherited FillParametersSelectOrdelete(AParameters); with AParameters do begin ParamByName('sid').Value:= Sid; end; end;
Код который реализует данный класс. Скачать его можно здесь uCommonEngine.
{Класс для единичной записи из БД.} TCommonEngine = class(TCommonObject) private FUpDateString: string; FInsertString: string; FTableName: string; FSelectString: string; FDeleteString: string; procedure SetInsertString(const Value: string); procedure SetUpDateString(const Value: string); procedure SetTableName(const Value: string); procedure SetSelectString(const Value: string); procedure SetDeleteString(const Value: string); public {Конструктор, в нем инициализируются isDeleted:= False ID:= -1 Поэтому обязательно писать в наследуемом классе inherited Create; заполняются свойства - TableName - InsertString - UpDateString - SelectString - DeleteString } constructor Create;override; {Выполняет выбор значений из БД. Перед візовом не обходимо заполнять ключевіе поля. Вызывает процедуры - GetSelectedFields - FillParametersSelectOrdelete Имеет смысл заполнять в наследуемом классе Result:= inherited GetByID; } function GetByID: Boolean; override; {Выполняет заполеннеи свойств класса значениями из полей, которые возврщаются из БД при выполнении запроса SelectString. Имеет смысл заполнять в наследуемом классе Result:= inherited GetSelectedFields(AFields) } function GetSelectedFields(AFields: TFields): Boolean; virtual; {Выполняет заполенение свойств , которые не выбираются из таблицы, которая записана в свойстве TableName, или же они вычисляются на основе существующих свойств. вызывается не зависомо от GetByID, но не ранее т.к. все остальные свойства могут быть не заполнены. Имеет смысл заполнять в наследуемом классе Result:= inherited GetAdditionalInfo; } function GetAdditionalInfo: Boolean; override; {Выполняет вставку в таблицу записи, вней же происходит дополнение InsertString параметром id и возврат этого параметра в свойство класса id идентификтаора вставленной записи. Параметры для вставки берутся из соотвествующих свойств наследуемого класса и запонюябтсяони в процедуре FillParamsInsertOrUpdate используя параметр AParameters. Значение id заполнять не нужно, оно будет заполнено автоматически. Если при вставке не требутся делать каких-либо дополниеьтльных действий, то в наслеудемо классе имеет смысл заполнить данную процедуру следующим кодом Result:= inherited Insert; } function Insert: Boolean; virtual; {Выполняет обновление записи в базе данных. Параметры для вставки берутся из соотвествующих свойств наследуемого класса и запонюябтсяони в процедуре FillParamsInsertOrUpdate используя параметр AParameters. Значение id заполнять не нужно, оно будет заполнено автоматически. Если при вставке не требутся делать каких-либо дополнительных действий, то в наслеудемо классе имеет смысл заполнить данную процедуру следующим кодом, если не требуется выполнять никаких дополнительных действий Result:= inherited Update; } function Update: Boolean; virtual; {Выполняет удаление записи из базы данных вне зависимости от значения свойства isDeleted. Параметры для удаления заполняются в процедуре FillParametersSelectOrdelete В наслеудемо классе имеет смысл заполнить данную процедуру следующим кодом, если не требуется выполнять никаких дополнительных действий Result:= inherrited Delete } function Delete: Boolean; override; {Выполняет сохранение класс по его параметрам. Если установлено true свойство isDeleted, то вызывается процедура Delete, в противном случае если id > 0, то вызывается процедура Update. В наслеудемо классе имеет смысл заполнить данную процедуру следующим кодом, если не требуется выполнять никаких дополнительных действий Result:= inherrited Save; } function Save(ASaveItems: Boolean = True): Boolean; override; {Заполняем параметры отличне от id значениями свойтсв класса при вставке или обновлении записи } function FillParamsInsertOrUpdate(AParameters: TParameters): Boolean; virtual; {Заполняем параметры отличне от id значениями свойтсв класса} function FillParametersSelectOrdelete(AParameters: TParameters): Boolean; virtual; {обновляет поля в классе данными из базы} function Refresh: Boolean;override; {строка содержащая SQL - запрос для вставки одной зааписи в БД. Поле id не надо указывать в запросе, оно будет добавлено при выполнении запроса и заполнено идентификатором вставленной записи, и возвращено в свойство класса ID, идентификатор вставленной записи определяется по свойству TableName. Данная строка заполняется в конструкторе наследуемого класса.} property InsertString: string read FInsertString write SetInsertString; {строка содержащая SQL - запрос для обновления одной зааписи в БД. Данная строка заполняется в конструкторе наследуемого класса.} property UpDateString: string read FUpDateString write SetUpDateString; {строка содержащая SQL - запрос для обновления одной зааписи в БД. Данная строка заполняется в конструкторе наследуемого класса.} property SelectString: string read FSelectString write SetSelectString; {строка содержащая SQL - запрос для удаления одной зааписи в БД. Данная строка заполняется в конструкторе наследуемого класса.} property DeleteString: string read FDeleteString write SetDeleteString; {Название табилцы БД, в которой хранятся записи для создаваемого класса. Заполняется в конструкторе класса.} property TableName: string read FTableName write SetTableName; {--------------------------------------------------------------------------} end; { TCommonEngine } constructor TCommonEngine.Create; begin inherited Create; end; function TCommonEngine.Delete: Boolean; begin Result:= inherited Delete; with TADOCommand.Create(nil) do try Connection:= Fconnection; CommandText:= DeleteString; Parameters.ParseSQL(CommandText, True); FillParametersSelectOrdelete(Parameters); Execute; finally Free; end; end; function TCommonEngine.FillParametersSelectOrdelete( AParameters: TParameters): Boolean; begin with AParameters do begin ParamByName('id').DataType:= ftInteger; ParamByName('id').Value:= ID; end; end; function TCommonEngine.FillParamsInsertOrUpdate(AParameters: TParameters): Boolean; begin Result:= True; with AParameters do begin ParamByName('id').DataType:= ftInteger; ParamByName('id').Value:= ID; if ID 0 then Result:= Update else Result:= Insert; end; procedure TCommonEngine.SetDeleteString(const Value: string); begin FDeleteString := Value; end; procedure TCommonEngine.SetInsertString(const Value: string); begin FInsertString := Value; end; procedure TCommonEngine.SetSelectString(const Value: string); begin FSelectString := Value; end; procedure TCommonEngine.SetTableName(const Value: string); begin FTableName := Value; end; procedure TCommonEngine.SetUpDateString(const Value: string); begin FUpDateString := Value; end; function TCommonEngine.Update: Boolean; begin Result:= True; with TADOCommand.Create(nil) do try Connection:= Fconnection; CommandText:= UpDateString; Parameters.ParseSQL(CommandText, True); FillParamsInsertOrUpdate(Parameters); Execute; finally Free; end; end;
Еще интересные записи по данной теме
Tags: Delphi, Model-view-controller, MVC, Object-relational mappin, ORM
[...] были предложены базовые классы: TCommonDocument, TCommonListEngine, TCommonEngine, TCommonObject и рассмотрены общие сведения о [...]