Tips, Tricks and Code Tips, Tricks and Code

ESB and...

Writing a Custom Content Handler for Integration Server

Created by Liferay Admin, last modified on Tue, 20 Aug 2019, 05:09

by Jonathan Heywood - Manager, Product Management Software AG

Table of Contents [-]

ApplicabilityProduct: Integration Server#

Versions: 6.5, 7.1.x, 8.0

AbstractWhen a document is posted to a port on Integration Server (IS), then a Content Handler is invoked to convert the contentinto an IS pipeline (IData) object for processing by the service being invoked. This document describes what a content handler does, how IS determines which content handler to use and how to write and register your own customer content handler for IS.#

What is a content handler?As the name implies, a content handler is a piece of code that takes a generic input in the form of an InputStream and knows how to parse that content and convert it into a format more easily consumable by the service being invoked. To do this, an appropriate content handler needs to be selected based on the contenttype of the document being received. The method of determining the content-type differs depending on the protocol of the receiving port: #

Port protocol and Method of determining content type

  • HTTP(S)
    • Content-Type HTTP header
  • FTP(S)
    • Two possibilities:
      1) If a content-type is supplied as part of the FTP PUT command, then that content-type is used: put srcFile destFile;text/xml
      2) Otherwise, the filename extension is used to determine the content-type using the mime.types table (see below)
  • File polling
    • Two possibilities:
      1) If a content-type has been specified in the configuration of the file polling port, then that content-type is used for all files received through that port
      2) Otherwise, the filename extension is used to determine the content-type using the mime.types table (see below)
  • Email
    • The content-type specified in the MIME header of the email message. If the option Invoke service for each part of multipart message has been selected, then the content type for each service invocation will be that of the relevant MIME part, otherwise it will be the content-type of the entire message.

A content handler has two parts; one for parsing the received document and converting it to an IData (pipeline) object that the service can process easily, and theother for converting the output pipeline from the service back into a format that the calling client can handle. Most content handlers only implement the input handler, butthe output handler can also be used to custom-format the output of a service, although there are other ways of doing this, such as using pub.flow:setResponse.

mime.typesIn the cases mentioned above where the filename extension determines the contenttype, this is determined based on a file called mime.types, which can be found in the <IntegrationServer>/lib directory. It contains lines like the following: text/plain bas c h txt #

This indicates that any files ending in .bas, .c, .h or .txt will be treated as content type text/plain. If you need to add new file extension mappings, then you can add them to this file. NOTE: Make sure you shut down IS before modifying this file.

Writing a content handlerThe content handler itself consists of two parts:#

  • the content handler class, an implementation of com.wm.app.b2b.server.ContentHandler
  • the content handler factory, an instance of com.wm.app.b2b.server.ContentHandlerFactory

These cannot be written inside webMethods Developer and need to be written an compiled using your favorite Java IDE, or using the JDK from a command-line. The class files can be placed in the <IntegrationServer>/packages/<yourpackage>/code/classes directory for easy access from the register and remove services.

The ContentHandler classThe following is a simple skeleton for this class. This is the class that does all the work.#

NOTE: It is not necessary to implement both getInputValues and putOutputValues. Often the putOutputValues method is left empty if the calling client is merely posting a document and not expecting any specific output.

public class MyContentHandler implements ContentHandler
{
private String contentType;
public MyContentHandler()
{
contentType = “<default_content_type>”;
}
public MyContentHandler (String contentType)
{
this.contentType = contentType;
}
public String getContentType()
{
return contentType;
}
// this service parses the received document and creates// the input pipeline for the service being invoked
public Values getInputValues(java.io.InputStream is,
InvokeState state)
throws IOException
{
// add code here to read from InputStream and create a// Values object representing the data content
}
// this service parses the output pipeline of the service// and converts it to a stream format for delivering to the
// calling clientpublic void putOutputValues(OutputStream os, Values out,InvokeState state)throws IOException{// add code here to read from the Values object and
// write its content in the desired format to the// OutputStream
}
}

The ContentHandlerFactory classThe following is all that is needed in the ContentHandlerFactory class.#

public class MyContentHandlerFactory
extends ContentHandlerFactory
{
private String contentType;
public MyContentHandlerFactory ()
{
contentType = "<default_content_type>";
}
public MyContentHandlerFactory (String contenttype)
{
contentType = contenttype;
}
public ContentHandler create()
{
return new MyContentHandler (contentType);
}
}

Registering content handlersOnce the content-type has been determined using the methods described above, ISwill try to invoke a suitable content handler. IS contains a number of standard contenthandlers, such as for XML or flat files. Others may have been registered by adapters,eStandards modules or by custom code.#

A content handler can be registered at any time while an IS is running by calling

ServerAPI.registerContentHandler(java.lang.String content_type,
ContentHandlerFactory factory)

To this, you provide the content-type (for example application/vnd.ms-excel) and anew instance of com.wm.app.b2b.server.ContentHandlerFactory, like the exampleabove.

NOTE: See the IS Java API documentation for more details on these APIs.

Registering a content handler is best done in a one-line Java service in IS. Then specifythat service as a startup service of that package to ensure that the content handlergets registered each time IS starts up. And to complete the picture you should create asecond Java service that removes the content handler again when the package isunloaded:

ServerAPI.removeContentHandler(java.lang.String content_type)

The information in this document is provided as-is and with no warrantywhatsoever. Software AG cannot be held responsible for the results of anyinaccuracies.


0 Attachments
127752 Views
Average (2 Votes)
Comments