# Create a Java-based Transformer Service blade

Here we explain how to create a simple [Service blade](cdf-blade-types.md) for [Transformer](../transformer/index.md), where the blade is written as a Transformer modulein the Java programming language. The core of Transformer is written in C, so to create a module in Java, you use Transformer’s [Java Module API,opts="nofollow"](https://docs.caplin.com/developer/api/transformer_java_sdk/6/).

**📌 NOTE**\
If you’ve already read How Can I... [Create a Lua-based Transformer Service blade](cdf-create-a-lua-based-transformer-service-blade.md), you’ll notice that the Lua blade described there does exactly the same thing as the blade we create here. This is entirely deliberate, and should allow you to see the differences and similarities between using Java and Lua for creating Transformer Service blades.

## Before you start

This example shows how to create a Java-based Service blade called **SpreadJavaBlade** that calculates the spread between Bid and Ask prices. At run time, the Transformer receives the prices from a Pricing Adapter (an [Integration Adapter](../platform-architecture/putting-data-into-the-platform.md)), and passes them on to the SpreadJavaBlade Transformer module, which calculates the price spread from the Bid and Ask prices. The Transformer sends the prices, including the new `spread` field, on to a Liberator, which forwards them to subscribing client applications, as shown in this diagram:

![CDF_Java_based_Transformer_Service_blade_Platform_Architecture_02](../../../images/CDF_Java_based_Transformer_Service_blade_Platform_Architecture_02.png)

You’ll need a Transformer and [Liberator](../liberator/index.md) to help test your Service blade while you develop it, and a Pricing Adapter that can supply the Bid and Ask prices. In this example we’ve assumed that the corresponding record fields are called `bidPrice` and `askPrice` respectively.

If you don’t have Transformer and Liberator already deployed on a machine for this purpose, you’ll need to deploy one or both of these components to the Deployment Framework on your development machine. To do this, follow the instructions in How can I... [Deploy Platform components to the Framework](cdf-deploy-platform-components-to-the-framework.md). You won’t need to set up HTTPS connections or KeyMaster while you’re developing the blade, so you can ignore the topics about those things.

If you need to develop a suitable Pricing Adapter first, see How can I... [Create a Java-based Adapter blade](cdf-create-a-java-based-adapter-blade.md).

<dl><dt><strong>💡 TIP</strong></dt><dd>

In the following steps you’ll be using the `dfw` command of the Deployment Framework. Before entering any `dfw` command as `./dfw <command-name>`, make sure your current (working) directory is set to the Deployment Framework’s topmost directory.

For a list of `dfw` commands, [click here](cdf-the-deployment-framework-command-utility-dfw.md).
</dd></dl>

### Blade structure

What’s in a Java Service blade? Assuming the blade is located in in the Deployment Framework at _&lt;Framework-root>/kits/&lt;blade_name>/&lt;blade_name>/_, relative to this path:

* the blade type and blade compatibility information are in the _control_ file
* the blade’s [field definitions](../datasource/datasource-field-definitions.md) are in _blade_config/fields.conf_
* Liberator related configuration for the blade is in _Liberator/etc/rttpd.conf_
* Transformer related configuration for the blade is in _Transformer/etc/java.conf_ and _Transformer/etc/spreadjava.conf_
* the Transformer module’s Java JAR file compiled from the Java source file is in _Transformer/lib/java_

## Summary

In brief, you create the blade using the following steps, which are given in more detail further down the page:

1. [Create the blade’s directory structure](#create-the-blades-directory-structure).
2. [Define the new fields](#define-the-new-fields).
3. [Update the core component configuration](#update-the-core-component-configuration): 
   1. [Define additional Liberator configuration](#define-additional-liberator-configuration).
   2. [Define the Java module configuration in Transformer](#define-the-java-module-configuration-in-transformer).
4. [Add the blade control file](#add-the-blade-control-file).
5. [Integrate the initial core component configuration with the Deployment Framework](#integrate-the-initial-core-component-configuration-with-the-deployment-framework).
6. [Write the Java module](#write-the-java-module).
7. [Start the new Transformer Service blade](#start-the-new-transformer-service-blade).
8. [Package the new blade](#package-the-new-blade).

## Create the blade’s directory structure

In a directory that’s _outside_ the Deployment Framework (say _Temp_Java_blade_), create the following directory structure:

![CDF_Java_based_Transformer_Service_blade_directory_struc_01](../../../images/CDF_Java_based_Transformer_Service_blade_directory_struc_01.png)

At this stage, you don’t need to create the _control_ file and the _.conf_ and _.jar_ files that are also shown in the structure - you’ll do that in subsequent steps.

## Define the new fields

The blade must define any new fields that it will use, which in this instance means our new `Spread` field.

* Create a text file called **_fields.conf_** in _Temp_Java_blade/SpreadJavaBlade/blade_config/_
* Using a suitable text editor, add the following configuration to _fields.conf_

  ```
  #
  # Field definitions for the Transformer SpreadJavaBlade
  #
  add-field Spread 45036
  ```

  **💡 TIP**\
  You don’t have to use the field number we’ve shown here; you can choose your own value as long as it’s unique within your particular Caplin Platform installation.

You don’t have to list in the _fields.conf_ file all the fields belonging to the incoming records that the blade will receive, because they’re already defined in the Pricing Adapter’s _fields.conf_ file. For example, The `BidPrice` and `AskPrice` fields used in the code samples further down this page would have been defined there. When you deploy your new SpreadJavaBlade blade, the Deployment Framework will make the Pricing Adapter’s field definitions available to it (since the Pricing Adapter will also have been deployed as a blade).

For more about defining fields, see [Field definitions](../datasource/datasource-field-definitions.md) in the [DataSource](../datasource/index.md) Features and Concepts, and [Field definition format](../datasource/datasource-field-definition-format.md).

## Update the core component configuration

The new blade has to include configuration for the core Platform components that it interacts with. In this case, the core components are: Liberator, which will subscribe to data supplied by the Transformer module, and Transformer, which houses the module.

### Define additional Liberator configuration

Configuration details for the Liberator are stored in the _rttpd.conf_ file

1. Create a text file called _rttpd.conf_ in _Temp_Java_blade/SpreadLuaBlade/Liberator/etc/_
2. Using a suitable text editor, add the following configuration to _rttpd.conf_

   ```
   #
   # Liberator configuration for data from
   # the SpreadJavaBlade Java-based Transformer Service blade.
   #
   add-data-service
      service-name SpreadJavaBlade${THIS_LEG}
      include-pattern ^/FX/
      add-source-group
         required true
         add-priority
            remote-label transformer${THIS_LEG}
         end-priority
         if "${FAILOVER}" == "ENABLED"
            add-priority
               remote-label transformer${OTHER_LEG}
            end-priority
         endif
      end-source-group
   end-data-service
   ```

   This configuration defines a [data service](../datasource/datasource-data-services.md) through which the Liberator requests the data supplied by the SpreadJavaBlade. It also defines, through the `add-source-group ... end-source-group` block, how the Liberator should fail the data service over to an alternate Liberator (this only applies if failover has been enabled for the deployment - see How can I... [Set up server failover capability](cdf-set-up-server-failover-capability.md)).

This is fairly standard configuration. The important points to note are:

* The `**service-name**` configuration item defines the name of the data service, which in this case is (by convention) the name of the blade, **SpreadJavaBlade**, that supplies the data.
* The `**include-pattern**` item specifies that the data service is to supply data for all [subscriptions](../datasource/datasource-subscriptions.md) whose [subjects](../datasource/datasource-subjects-symbols-and-fields.md) start with the string `/FX/`
* The macros `THIS_LEG` and `OTHER_LEG` are used to differentiate the configuration of [primary and secondary failover legs](cdf-set-up-server-failover-capability.md).

### Define the Java module configuration in Transformer

Configuring Transformer for a Java module is a bit more involved than [doing so for a Lua module](cdf-create-a-lua-based-transformer-service-blade.md#define-the-lua-pipeline-configuration-in-transformer), as the Transformer has to know the location of the [Java Virtual Machine](https://docs.oracle.com/javase/specs/jvms/se7/html/index.html) (JVM) in order to start it.

1. Create a _java.conf_ file in _Temp_Java_blade/SpreadJavaBlade/Transformer/etc/_
2. Using a suitable text editor, add the following configuration to _java.conf_:

   ```
   #
   # Java module configuration for the
   # SpreadJavaBlade Java-based Transformer Service blade.
   #
   jvm-location       "${JVM_LOCATION}"

   jvm-global-classpath    %r/lib/java/transformermodule.jar

   modules-dir ${ccd}/../lib
   add-module SpreadJavaBlade

   add-javaclass
       class-name example.spreadmodule.SpreadModule
       class-id   SpreadJavaBlade
       classpath  "${ccd}/../lib/java/SpreadModule.jar"
   end-javaclass
   ```

   The important points to note about this configuration are:

   * `jvm-location` defines the path of the JVM. It refers to the master definition through the macro `JVM_LOCATION`, which is defined in _&lt;Framework-root>/global_config/environment-defaults.conf_
   * `jvm-global-classpath` defines the classpath of the Java library underlying Transformer’s Java Module API.
   * `modules-dir` defines the directory path to the _java_ directory, which contains the Java module’s JAR file.

     (The `ccd` macro in the path name defines the current directory path of the file in which it is referenced. So in this example, because the `ccd` reference is in the file _SpreadLuaBlade/Transformer/etc/java.conf_, the macro defines the path _SpreadLuaBlade/Transformer/etc/_ The directory path for the Java Module is therefore _SpreadLuaBlade/Transformer/lib_)
   * `add-module` defines an identifier for the Transformer Java module. This must be the blade name, so in this example it’s `SpreadJavaBlade`.
   * `add-javaclass` defines: 
     * The fully qualified name of the Java class that implements the Java module (`class-name example.spreadmodule.SpreadModule`).
     * `class-id` - a short identifier of the Java class. For blade implementations this must be the blade name, so in this example it’s set to `SpreadJavaBlade`.
     * The classpath on which the module’s JAR file can be found (`classpath "${ccd}/../lib/java/SpreadModule.jar"` ). You generate the JAR from the _SpreadModule.java_ file where the Java source code for the module resides.
3. Create a configuration file _spreadjava.conf_ in _Temp_Java_blade/SpreadJavaBlade/Transformer/etc/_ and add the following lines:

   ```
   include-file ${ENV:CONFIG_BASE}bootstrap.conf
   module-logfile spreadjava.log
   module-classid spreadjava
   include-file ${BASE}/global_config/overrides/SpreadJavaBlade/Transformer/etc/spreadjava.conf
   ```
   * `include-file ${ENV:CONFIG_BASE}bootstrap.conf` allows access to some common definitions that the blade requires.
   * `module-logfile` specifies the name of the log file in _Transformer/var_ that the spreadjava module writes errror and information messages to at run time.
   * `module-classid` specifies the class ID of the Java Module. This must match the `class-id` defined in _java.conf_.
   * The final `include-file` item allows you to override the blade’s standard configuration after it has been deployed, by putting a different _spreadjava.conf_ configuration file in the Deployment Framework’s _overrides_ directory for the blade.

## Add the blade control file

The Deployment Framework needs to take some specific actions to allow a Java Transformer module blade to work correctly. So the Framework needs to have a way of knowing the blade is a Java Transformer module. This is done through a [blade control file](cdf-the-blade-control-file.md) located in the root directory of the blade.

1. Create a text file called _control_ in _Temp_Java_blade/SpreadJavaBlade/_

   This is the blade control file
2. Add the following single line to the blade control file:

   ```
   Type: JTMBlade
   ```
3. You would normally also record any blade compatibility information in the control file as well (for details, see the [Reference information](cdf-the-blade-control-file.md) about the blade control file), but for this simple example there’s nothing to record.

That’s all the configuration changes you need for the time being.

### Integrate the initial core component configuration with the Deployment Framework

Now you’ve created the initial configuration for the core components that use your Transformer Service blade, you can deploy this configuration in your development environment.

1. Zip up the blade directory structure in your temporary work area into a skeleton blade kit. The name of the _.zip_ file must be of the form _&lt;blade_name>-&lt;version_number>.zip_, and the topmost directory in the _.zip_ file must be the top level directory of the blade.

   So in our example, the _.zip_ filename is _SpreadJavaBlade-&lt;version_number>.zip_ (say _SpreadJavaBlade-000001.zip_), and the topmost directory in the _.zip_ file is _SpreadJavaBlade_.
2. Navigate to _&lt;Framework-root>_ and deploy the skeleton blade kit:

   ```
   ./dfw deploy ../Temp_Java_blade/SpreadJavaBlade-000001.zip
   ```

   The `./dfw deploy` command should respond with:

   ```
   Boot-strapping the Deployment Framework

      Unpacking SpreadJavaBlade kit SpreadJavaBlade-000001.zip
      SpreadJavaBlade-000001.zip successfully unpacked and stored in kits/archive

      Activating SpreadJavaBlade

      Blades ok
   ```

   And then `./dfw versions` should show the new blade:

   ```
   Deployment Framework           6.0.4-267113

      Core components                Version
      -----------------------------------------------------------
      Liberator                      6.1.0-275608
      Transformer                    6.1.0-275716

      Deployed blades                Version            State
      -----------------------------------------------------------
      PricingAdapter                 2013.09.27.1138    Active
      SpreadJavalade                                    Active

      Built-in blades                                   State
      -----------------------------------------------------------
      BlotterExport                                     Inactive
      DemoDataSource                                    Inactive
      DirectConnection                                  Active
      HTTP                                              Active
      HTTPS                                             Inactive
      JavaOpenPermissioning                             Inactive
      LiberatorJMX                                      Active
      LiberatorWebsite                                  Active
      MinimalLiberatorWebsite                           Inactive
      OpenPermissioning                                 Active
      ServerIdentification                              Active
      TransformerJMX                                    Active
   ```

   Note that deploying the skeleton SpreadJavaBlade has automatically put it in the [active](cdf-active-and-inactive-blades.md) state.
3. Start the deployed core components and the SpreadJavaBlade blade: `./dfw start`

At this stage the Liberator and Transformer are running with the new configuration. The new blade won’t run of course, because no executable code has been written for the Java module.

In a Web browser, navigate to the [Liberator’s status page](../liberator/liberator-liberator-status-web-page.md), where you should see the **SpreadJavaBlade** data service:

![CDF_Java_based_Transformer_Service_blade_data_service](../../../images/CDF_Java_based_Transformer_Service_blade_data_service.png)

<dl><dt><strong>💡 TIP</strong></dt><dd>

The URL of the Liberator is of the form <span>http://</span>&lt;URL_of_liberator_server>:&lt;liberator_port>. You can find the _&lt;URL_of_liberator_server>_ and _&lt;liberator_port>_ by entering the command `./dfw info`. In a development enviroment, the URL would typically be <span>http://</span>localhost:18080.

When the Liberator home page is displayed, select the View Status button.
</dd></dl>

## Write the Java module

This is the functional part of the Java module that defines the actions you need it to perform. In this example, the Java source is in a single file called _SpreadModule.java_. Create this file in a suitable place within your development environment.

The example code is quite long, so we’ll break it up into sections in order to explain it. It uses Transformer’s [Java Module API,opts="nofollow"](https://docs.caplin.com/developer/api/transformer_java_sdk/6/).

**Section 1:**

```java
package example.spreadmodule;

import com.caplin.transformer.module.*;

public class SpreadModule  implements TransformerModule, SubscriptionListener
{
   private int bidFieldNumber;
   private int askFieldNumber;
   private int spreadFieldNumber;

   @Override
   public void initialise(String moduleName, TransformerAccessor transformerAccessor)
   {
       bidFieldNumber = transformerAccessor.getFieldManager().getFieldByName("BidPrice").getNumber();
       askFieldNumber = transformerAccessor.getFieldManager().getFieldByName("AskPrice").getNumber();
       spreadFieldNumber = transformerAccessor.getFieldManager().getFieldByName("Spread").getNumber();

       transformerAccessor.getSubscriber().addSubscriptionListener("/FX/*", this);
   }
```

This first section identifies defines the `SpreadModule` class which implements the `TransformerModule` and `SubscriptionListener` interfaces of the Transformer Java Module API. It defines three integers to contain the numbers of the relevant record fields, and, in the `initialise()` method, populates these integers using the `getFieldByName()` method. `initialise()` also creates a subscription listener, to listen for messages from the Pricing Adapter that have subjects in the "/FX/" namespace.

**Section 2:**

```java
@Override
   public void setFileReading(boolean b) {
   }

   @Override
   public void shutdown() {
   }

   @Override
   public String getLoggerName() {
      return "example.spreadmodule.SpreadModule";
   }

   @Override 
   public void objectDeleted(String objectName) {
   }

   @Override
   public void status(String objectName, ObjectStatus objectStatus) {
   }
```

The above method implementations just define the default settings for some methods of the `TransformerModule` and `SubscriptionListener` interfaces.

**Section 3:**

```java
@Override
   public void update(DataSourceUpdateEvent dataSourceUpdateEvent) {
      String bidValue = 
         dataSourceUpdateEvent.getTransformerData().getFieldByFieldNumber(bidFieldNumber).getValue();
      String askValue = 
         dataSourceUpdateEvent.getTransformerData().getFieldByFieldNumber(askFieldNumber).getValue();
```

This implementation of the `SubscriptionListener` interface’s `update()` method obtains the `AskPrice` and `BidPrice` field values from an incoming record message with a subject that begins with "/FX/". It uses the field numbers obtained when the module was initialised (see section 1 of the example).

**Section 4:**

```
if ( askValue != null && bidValue != null ) {
         double spreadValue = 
            Double.parseDouble(askValue) - Double.parseDouble(bidValue);
         dataSourceUpdateEvent.getTransformerData().addData(spreadFieldNumber, spreadValue);
      }
   }
}
```

Having retrieved the `AskPrice` and `BidPrice` field values, the subscription listener’s `update()` method checks that neither of them are null, calculates `spreadValue`, by subtracting one value from the other, and uses the `addData()` method to add this calculated spread value to the `Spread` field that was defined earlier.

* When you’ve completed the code in the _SpreadModule.java_ file, compile it into a JAR file (_SpreadModule.jar_).

  Ensure that the JAR containing the Transformer’s Java Module API is in the compilation classpath. This JAR is called _transformermodule.jar_ and it’s located in the _lib/java_ directory of the deployed Transformer in the Deployment Framework.
* Put the JAR in the directory _&lt;Framework-root>/kits/SpreadJavaBlade/SpreadJavaBlade/Transformer/lib/java/_

## Start the new Transformer Service blade

1. If you have exclusive use of the Pricing Adapter in your development environment, restart the whole system on your development server machine:

   ```
   ./dfw start
   ```

   This stops the deployed core components and the Pricing Adapter blade and restarts them; in this case the Liberator, Transformer and the new Integration Adapter. (The command works out from the configured hostname settings which components it needs to start on the machine where the command is running.)
2. Alternatively, if you share Pricing Adapter with other developers, so you don’t want to shut it down just to get your new Integration Adapter running:
   1. Make sure the Pricing Adapter is running:

      ```
      ./dfw status
      ```
   2. Then start the Liberator and Transformer:

      ```
      ./dfw start Liberator
      ```

      ```
      ./dfw start Transformer
      ```
3. When the everything is running:
   1. Look at the Liberator’s status page to check that the Liberator is connected to the Transformer and can see the data service (`SpreadJavaBlade` in our example) for which the new Java-based Transformer Service blade supplies data.
   2. Use the Liberator’s [Liberator Explorer](../liberator/liberator-liberator-explorer.md) to request data for the relevant subjects supplied by the Transformer Service blade, and check that the data is returned (via Transformer) as expected, with a correctly calculated `Spread` field included.

      ![CDF_Lua_based_Transformer_Service_blade_Lib_Explorer](../../../images/CDF_Lua_based_Transformer_Service_blade_Lib_Explorer.png)

## Package the new blade

When you’ve developed and tested the new blade to your satisfaction, you’ll need to package it up so it can be deployed on your production system - see How can I... [Package a custom blade](cdf-package-a-custom-blade.md).

---

**See also:**

* [Package a custom blade](cdf-package-a-custom-blade.md)
* [Set up server failover capability](cdf-set-up-server-failover-capability.md)
* [Deploy Platform components to the Framework](cdf-deploy-platform-components-to-the-framework.md)
* [Create a Lua-based Transformer Service blade](cdf-create-a-lua-based-transformer-service-blade.md)
* [Start and stop components and blades](cdf-start-and-stop-components-and-blades.md)
* [Transformer’s Java Module API,opts="nofollow"](https://docs.caplin.com/developer/api/transformer_java_sdk/6/)
