«Любой дурак может написать программу, которую поймет компилятор. Хорошие программисты пишут программы, которые смогут понять другие программисты»
53. Алгоритм взаимодействия клиент-сервер
Описание класса COM объекта.
type
TSmpCOM = class(TTypedComObject, ISmpCOM, ISmpCOM2)
protected
{Declare ISmpCOM methods here}
function Cube(AValue: Double): Single; stdcall;
function Summa(X, Y: Integer): Integer; stdcall;
function Tangent(Angle: Double): Double; stdcall;
end;
Иерархия класса TSimpleCOM.
TSimpleCOM |
TTypedComObject |
ISmpCOM |
ISmpCOM2 |
TComObject |
TObject |
IUnknown |
Интерфейсы ISmpCOM и ISmpCOM2 объединяют функциональные методы класса СОМ объекта.
Описание сокласса CoSmpCOM.
Этот класс описан в библиотеке типов и предоставляет два альтернативных метода (конструктора), предназначенных для создания СОМ объекта сервером.
CoSmpCOM = class
class function Create: ISmpCOM;
class function CreateRemote(const MachineName: string): ISmpCOM;
end;
Обе функции возвращают указатель на первый интерфейс ISmpCOM, который считается интерфейсом по умолчанию (default interface).
Последовательность выполнения функций при вызове клиентским приложением метода CoSmpCOM.Create следующая:
CoSmpCOM.Create |
Вызывается клиентским приложением и возвращает указатель на первый интерфейс ISmpCOM |
CreateComObject |
CreateComObject(CLASS_SmpCOM) as ISmpCOM. Параметр CLASS_SmpCOM этого метода является идентификатором (GUID) сокласса |
CoCreateInstance |
Эта функция COM API создает экземпляр класса СОМ объекта. Вызов этого метода на самом деле выглядит как OleCheck(CoCreateInstance(ClassID, nil, CLSCTX_INPROC_SERVER or CLSCTX_LOCAL_SERVER, Iunknown, Result)) Параметр ClassID – все та же константа CLASS_SmpCOM. Функция-оболочка OleCheck просто проверяет результат вызова метода CoCreateInstance и вызывает исключительную ситуацию при возникновении ошибки |
При вызове CoCreateInstance библиотека СОМ перехватывает управление и выполняет загрузку DLL библиотеки или приложения, содержащего реализацию сервера и СОМ объекта(ов). Эта библиотека всегда экспортирует четыре метода:
Ø DllGetClassObject;
Ø DllCanUnloadNow;
Ø DllRegisterServer;
Ø DllUnregisterServer.
Функция DllGetClassObject вызывается библиотекой СОМ (OLE engine) первой для создания экземпляра объекта фабрика класса, который в свою очередь создаст экземпляр СОМ класса. Экземпляр фабрики класса создается путем вызова метода (процедуры) TTypedComObjectFactory.Create, который в нашем случае выглядит так:
TTypedComObjectFactory.Create(ComServer, TSmpCOM, Class_SmpCOM,
ciMultiInstance, tmApartment);
Вызов этого метода помещен в секцию инициализации модуля, содержащего СОМ объект. Этот модуль в свою очередь должен подключать модуль ComServ. В модуле ComServ описана переменная ComServer, которая инициализируется автоматически (очевидно, в секции инициализации модуля ComServ). Переменная ComServer представляет собой экземпляр класса TComServer, описанного в модуле ComServ. (В справочной системе Delphi эта переменная называется ComServ, что, по-видимому, является ошибкой).
Таким образом, вызов метода CoCreateInstance инициирует вызов конструктора TTypedComObjectFactory.Create и заканчивается в конце концов тем, что клиентское приложение в результате выполнения приведенного выше оператора
Interface1:=CoSmpCOM.Create;
получает ссылку на первый интерфейс СОМ объекта, с помощью которого уже может осуществляться вызов функциональных методов объекта.
Методы, экспортируемые библиотекой сервера.
Библиотека DLL, которая инкапсулирует внутрипроцессный сервер, экспортирует четыре функции:
Ø DllGetClassObject;
Ø DllCanUnloadNow;
Ø DllRegisterServer;
Ø DllUnregisterServer.
Первая из них – DllGetClassObject – вызывается автоматически СОМ библиотеками, когда клиентское приложение обращается к серверу за получением интерфейса. Эта функция инициирует создание экземпляра фабрики класса, который в свою очередь создает СОМ объект. Эта функция не должна вызываться клиентским приложением непосредственно.
Функция DllCanUnloadNow может также вызывается СОМ библиотеками для того, чтобы определить, можно ли выгрузить библиотеку, т.е. сервер, в настоящий момент времени. Возвращаемые этой функцией значения следующие:
S_OK – библиотека может быть выгружена;
S_FALSE – библиотека не может быть выгружена.
Библиотека может быть выгружена, если число ссылок на инкапсулированные СОМ объекты равно нулю.
«52. Импорт библиотеки типов»
54. Разработка и использование локального сервера