Custom Content Handler Walkthrough

Custom Content Handler Walkthrough

Creating Custom Content Handlers

Using content handlers you can redirect a request to a TContentBase descendant class. This class is responsible for providing the actual content of the response. Content handlers are not components. They are lightweight classes and should be created at runtime.

Creating a new TContentHandler

Creating a new TContentHandler class is very simple. This how-to will show you how to create a new content handler to respond with a XML document.

1) Create a new IntraWeb Stand Alone server using the IntraWeb project wizard. Then create a new unit, name it IW.Content.XML and add this code to it:

unit IW.Content.XML;

interface

uses 
  Classes, IW.Content.Base, HTTPApp, IWApplication, IW.HTTP.Request, 
  IW.HTTP.Reply;

type 
  TContentXML = class(TContentBase) 
  protected 
    function Execute(aRequest: THttpRequest; aReply: THttpReply; const aPathname: string; aSession: TIWApplication): boolean; override; 
  public 
    constructor Create; override; 
  end;

implementation

uses 
  IW.Content.Handlers, IWMimeTypes;

constructor TContentXML.Create;
begin 
  inherited; 
  mFileMustExist := False;
end;

function TContentXML.Execute(aRequest: THttpRequest; aReply: THttpReply; const aPathname: string; aSession: TIWApplication): boolean;
begin 
  Result := True; 
  if Assigned(aReply) then 
  begin 
    aReply.ContentType := MIME_XML; 
    aReply.WriteString('<xml>My xml content here</xml>'); 
  end;
end;

initialization
end.

3) Still in your ServerController unit, add this code to the initialization section:

initialization 
  THandlers.Add('', 'GiveMeSomeXML', TContentXML.Create);

4) Now build and run your application. Open your browser and type this URL: http://127.0.0.1:8888/GiveMeSomeXML (note that the port may differ). You will see something like that:

ContentXML

How-To explained

First, we created a new TContentBase descendant class. Every custom content handler must descend from this class. Inside the Create() method, we must set mFileMustExist to FALSE. When TRUE, the TContentBase.Execute() method will search for this file and if it is not found, will reply with HTTP code 404.

Then, all we have to do here is override the TContentBase.Execute() method, and write directly to the aReply object instance. The first thing we did was setting the aReply.ContentType property. This actually changes the Content-Type HTTP header field in our response. In this case, we want to reply with a real XML (and not a XML string inside a HTML), so we use one of the predefined constants in IWMimeTypes unit.

Then, we write a XML directly to the aReply instance, using one of its methods, and we are done.

More…

How powerful is that? You can create TContentBase descendants to handle any kind of request. You can also create an Indy client to post requests to your IntraWeb application implementing a custom protocol and messaging system. The possibilities are infinite.

Starting in IntraWeb 14.0.13, you can also use content handlers to respond to Search Engine requests. If you have an IntraWeb application visible to the internet, web crawlers like googlebot will certainly visit your application. When a web crawler posts a request to your IntraWeb application, you may use a content handler to respond with the content you want to be indexed. In this case, you should set the following ServerController properties:

procedure TIWServerController.IWServerControllerBaseConfig(Sender: TObject);
begin 
  // Tell IntraWeb to redirect SearchEngine requests to some ContentHandler 
  SearchEngineOptions.RedirectToContentHandler := True; 

  // in this case, you must create a TContentBase descendant and add it to THandlers 
  // using 'SearchEngineRequest' as the document path 
  SearchEngineOptions.ContentHandlerPath := 'SearchEngineRequest';
end;

Demo

A fully functional demo containing this code can be found in our GitHub repository.