Active Server Components with Borland Delphi3
By Venkat
Introduction
Even though Delphi is been around for quite sometime, it has not become as popular as it should have become for building Active Server components. This is remarkable considering Delphi抯 good support for building COM objects. The examples in this article use Delphi 3.02.
In this article we will look into Delphi抯 support for building Active Server components. Since any automation server can be used as an ASP component, the same methods that are used to develop an automation server can be used to develop the components. Delphi makes creation of these components very easy, almost trivial. It provides a good IDE where you can add methods and properties to your objects. You can also do the registration of the components within the IDE itself. Internally, it will create the required IDL files and generates TLB files for you. We will not look into how Delphi provides this support. For instance, we won抰 examine the intricacies of Delphi抯 implementation of automation servers. Rather, we will concentrate on the steps that are required to develop a simple ASP component that can be used to add additional functionality to your ASP page. Specifically, we will be looking into developing an inproc ASP component.
The simple component that we are going to has four properties, and one method which will display these properties on the browser in a neat table.
Creating an Active Server Component in Delphi can be accomplished in the following steps.
Create the ActiveX library project.
Add an automation object to the project library.
Add the required methods and properties to the object.
Implement the methods inside a unit that Delphi creates for you.
Compile and register your component.
We will look into each of the above steps in detail. In Step 1 you抣l learn how to create an ActiveX library using Delphi.
Step 1 : Creating the library
Open Delphi IDE
Select File| New. Select the ActiveX tab
Figure 1 : New Items Property Sheet
Select the ActiveX Library Option and click on it. That will create the project file for you. The unit contains the following code.
library Project1;
uses
ComServ;
exports
DllGetClassObject,
DllCanUnloadNow,
DllRegisterServer,
DllUnregisterServer;
{$R *.RES}
begin
end.
This is the file where Delphi implements the required functions that are to be exported from all COM servers. The implementation of these functions is done in the ComServ unit. If you want, you can override the default implementations of these functions. But, for this example, you can use these defaults.
Step 2 : Add an Object to the Library
Select File | New and click the ActiveX tab and select the Automation object and click it. This will display the Automation Object Wizard.
Figure 2 : New Items Property Sheet
Enter the name of the object as SimpleObject and Select Multiple Instance option. This will bring up the Type Library editor
Figure 3 : Automation Object Wizard
Figure 4 : Project Type Library
The above steps will create two units. You can see them by pressing Ctrl+F12 and selecting the unit. One unit (Project1_TLB.pas) is the Delphi version of the type library created for the server and the other unit(unit1.pas) is the unit where you will implement your object抯 methods and properties. Open the unit1.pas file. At the end of this unit you can find the following piece of code:
initialization
TAutoObjectFactory.Create(ComServer, TSimpleObject,
Class_SimpleObject, ciMultiInstance);
end.
This is where the ClassFactory implementation for your object is done.
Step 3 : Adding Methods and Properties to the Object
Click on the method button on the toolbar and type the name of the method. Similarly, click on the property button on the toolbar and type the name of the property. You can change the type of the property to any of the Automation compatible datatypes. For this component we are going to use all WideString type properties. Refer to Delphi抯 documentation for a description of all of the Automation compatible datatypes. In the status bar of the Type library editor Delphi displays the error information about what you are typing in the editor. Add the following properties to your object. Name, Address, State, Country. Give the data type as WideString to all the properties. Similarly, add a method named WriteInfo.
And finally add the following two methods to the component.
OnStartPage(unk:IUnknown)
OnEndPage.
We use these two methods to get the IScriptingContext interface. When IIS creates a component instance, it looks for the OnStartPage and OnEndPage methods associated with that component. If the component has implemented these methods, the server will automatically call the OnStartPage method during script processing before the component is used, and call the OnEndPage method when all scripts on the ASP page have been processed.
Your TypeLibrary editor should look like this.
Figure 5 : Project Type Library
These operations added three methods and four properties to your object. You can see the changes in the two units that are created. You don抰 have to worry about the IDL that is required for this. Delphi will manage the process of converting it to the required IDL format. A default skeleton code for the implementation of these methods and properties is also added in the unit(unit1.pas). Whenever you add a new method or property, Delphi will automatically add an empty function implementation code in the unit. But when you remove a method or property it won抰 remove them from the unit. You have to manually remove them. Observe that Delphi automatically assigns the dispatch IDs for all of the properties and methods
Step 4 : Implementation of the Components Methods and Properties
Open the unit1.pas. Add the ASPTypeLibrary_TLB to your uses clause of the interface section. Your Uses section should look like this.
unit unit1;
interface
uses
ComObj,
ActiveX,
Delphi_TLB,
ASPTypeLibrary_TLB,
SysUtils;
Now go to the definition of the class that implements your interface. You can see that your class is inherited from TAutoObject and ISimpleObject. ISimpleObject is the interface where your methods and properties of the component are defined. This interface is created for you by Delphi.You can see the definition of this interface in the Project_TLB.pas file.TAutoObject provides the implementation required for an Automation Object.
Add the m_scriptContext, m_Name, m_Address, m_State, m_Country member variables to your class as shown in the code segment below.
type
TSimpleObject = class(TAutoObject, IExample)
protected
m_scriptContext : IScriptingContext;
m_Name,
m_Address,
m_State,
m_Country : String;
procedure WriteInfo
safecall;
procedure OnEndPage
safecall;
procedure OnStartPage(unk: IUnknown)
safecall;
function Get_Name: WideString
safecall;
procedure Set_Name(const Value: WideString)
safecall;
function Get_Address: WideString
safecall;
function Get_Country: WideString
safecall;
procedure Set_Address(const Value: WideString)
safecall;
procedure Set_Country(const Value: WideString)
safecall;
function Get_State: WideString
safecall;
procedure Set_State(const Value: WideString)
safecall;
end;
Now go to the place in the unit1.pas file where the code for implementation is given. Change the implementation to look like the code segment given below
procedure TExample.OnStartPage(unk: IUnknown);
begin
m_scriptContext := unk as IScriptingContext;
end;
procedure TExample.OnEndPage;
begin
m_scriptContext := nil;
end;
By now you must have observed that Delphi creates corresponding get_property and set_property functions for each property you add to the component in the TypeLibrary editor. Now go to the place where the code for implementing these methods is written. Change the code to look like this. I have given an example for just one property implementation.
procedure TExample.Set_Address(const Value: WideString);
begin
m_Address := Value;
end;
function TExample.Get_Address: WideString;
begin
Result := m_Address;
end;
On these same lines you can implement the rest of the property access. You can download the complete source.
Finally, go to the place where the implementation for the WriteInfo method is located and change it to look like the code segment below. The code simply takes all of the property values and using the IScriptingContext interface writes to the browser using the Response object.
procedure TExample.WriteInfo;
begin
m_scriptContext.Response.Write('<TABLE>');
m_scriptContext.Response.Write('<TR><TD>UserName</TD>');
m_scriptContext.Response.Write('<TD>'+m_Name+'</TD></TR>');
m_scriptContext.Response.Write('<TR><TD>Address</TD>');
m_scriptContext.Response.Write('<TD>'+m_Address+'</TD></TR>');
m_scriptContext.Response.Write('<TR><TD>State</TD>');
m_scriptContext.Response.Write('<TD>'+m_State+'</TD></TR>');
m_scriptContext.Response.Write('<TR><TD>Country</TD>');
m_scriptContext.Response.Write('<TD>'+m_Country+'</TD></TR>');
m_scriptContext.Response.Write('<TABLE>');
end;
Save the Project as Delphi.dpr and save the unit as SimpleObject.pas. From the Project menu select the BuildAll option to compile and build the DLL for the component. If you get an error during this stage it will likely happen because of the ASP type library that we are using in the application. So go to the Project menu and select the import type library. This will list out all the type libraries present in your system. Select the Microsoft Active Server Pages Type library and click on OK. This will bring up the Delphi equivalent of the ASP type library. Then rebuild the component.(Project|Build All). If it compiles without any errors go to the next step
Figure 6 : Import Type Library
Step 5 : Registering the Server
Go to Run | RegisterActiveX Server. This will register the component.
Now you can use the component with the ProgramID Delphi.SimpleObject.
You can call the component in an ASP page using
Set ObjDelphi = Server.CreateObject(揇elphi.SimpleObject?
You can use this component just like any other component. A sample HTML and ASP file that uses this component can be downloaded here.
Conclusion
We have looked into the steps for creating a simple ASP component from Delphi and the implementation of its methods and properties. You can extend the same procedure to create more complicated and functional components. Delphi manages all the hard work of writing the IDL files and generating the skeleton code for implementing the methods and properties. Therefore, you can concentrate on implementing your business logic in the component. I have shown how to access the ASP type library from Delphi. Likewise, if you want to add the database interaction for your components, you can import the Active Data Objects type library and use it.
Download
The source presented in this article is available for download.
[Code Source Download]
About the Author
Venkat is currently working at Icode Software Private Ltd (http://www.icode.com). Venkat has been working in ASP, Delphi from the past one and half years. His interests as far as software is concerned revolves around component based technologies and eCommerce based applications. He was educated at Nizam College, Hyderabad and later obtained a MCA from KREC Surathkal both in India.
Copyright 1999-2000 internet.com Corp. All RIGHTS RESERVED.