How to create an Ephesoft plugin ?

This blog explains how I created my first plugin for Ephesoft. I didn't want to create a very difficult plugin but I wanted to highlight the complexity of creating a new plugin, packaging it and deploying it. The blog will be split in 4 parts: (1) the global structure of the project, (2) the Java code, (3) the plugin description, (4) the packaging, and finally (5) the deploying.

Let's talk about the scope of the plugin. When you create a batch class in Ephesoft, you obviously need to test it. But, it's not possible to use standard testing methodologies or tools like JMeter. So, you need to refresh the list of running batch instances and it can be quite annoying. So, I decided to create a plugin sending a notification on an Android device when a batch instance is on review or validation step. And this plugin can be useful and re-usable. Moreover, Ephesoft is compatible with some tablets. So an operator receives a notification on his Android device, clicks on it and opens directly the web application. To simplify, I decided to use an applcation called PushBullet that you can install in an Android device. PushBullet provides an API to send notification to Android devices.

Structure of the project

The project is created using Maven. As usual, the folder "src/main/java" contains the Java code. In our project, we created 3 different packages. The package "com.bataon.ephesoft.dcma.notification" contains the Java class NotificationProperties  to handle properties configurable in Ephesoft. The class PushBulletHelper is dedicated to manage interactions with the server PushBullet. And the last 2 classes are the real plugin and are the entry point of the plugin. 

The folder "src/main/resources" contains all resources that will be used during the packaging phase, like usual in a Maven project. But, I will spend more time on the file ephesoft-module-notification.xml. This one contains the configuration of the plugin that will be used during the import.

The last interesting piece is the file distribution.xml  is a file that is used during the Maven packaging phase to follow rules and constraints of Ephesoft during the import. The assembly plugin provides the capability to create binary and source distributions. These distributions (assemblies) are defined using an assembly descriptor.

Java code

The first important class is NotificationProperties containing the definition of all properties that will be configurable using the Ephesoft user interface. The important thing is that keys have to match with the name property defined in the file ephesoft-module-notification.xml.

public final class NotificationProperties implements PluginProperty {
	
	private NotificationProperties(String fieldKey) {
		this.key = fieldKey;
	}

	public String getPropertyKey() {
		return key;
	}

	public static final NotificationProperties NOTIFICATION_ACTIVE;
	public static final NotificationProperties NOTIFICATION_API_KEY;
	public static final NotificationProperties NOTIFICATION_DEVICE_IDS;
	public static final NotificationProperties NOTIFICATION_TITLE;
	public static final NotificationProperties NOTIFICATION_BODY;
	public static final NotificationProperties NOTIFICATION_ADD_LINK;
	public static final NotificationProperties NOTIFICATION_URL;

	String key;

	static {
		NOTIFICATION_ACTIVE = new NotificationProperties("notification.active");
		NOTIFICATION_API_KEY = new NotificationProperties("notification.APIKey");
		NOTIFICATION_DEVICE_IDS = new NotificationProperties("notification.deviceIds");
		NOTIFICATION_TITLE = new NotificationProperties("notification.title");
		NOTIFICATION_BODY = new NotificationProperties("notification.body");
		NOTIFICATION_ADD_LINK = new NotificationProperties("notification.addLink");
		NOTIFICATION_URL = new NotificationProperties("notification.url");
	}
}

Next, we define an interface including the method that will be called by Ephesoft. The name of this method has to match with the value in the tag method-name in the file ephesoft-module-notification.xml

public interface NotificationPlugineService {

	void pushNotification(final BatchInstanceID batchInstanceID, final String pluginWorkflow) throws DCMAException;

}

Next, we create the implementation of this interface. You can check the code directly on Github. I just want to highlight the use of the Batch Class Plugin Config Service to retrieve configuration parameters.

The Plugin Description

This XML file is very important to describe the behavior and the configuration of the plugin. A lot of rules exists for this XML file. I'm not going to explain all rules that applies to this file, but only important ones:

  • The value of the tag plugin-service-instance has to match the bean identifier.
  • The value of the tag method-name has to match the name of the method that has to be called by Ephesoft.
  • The value of the tag application-context-path has to match the name of the context file in your Maven project.
<?xml version="1.0" encoding="UTF-8"?>
<plugin>
	<jar-name>${project.artifactId}.jar</jar-name>
	<plugin-name>${plugin.name}</plugin-name>
	<plugin-desc>${plugin.description}</plugin-desc>
	<plugin-workflow-name>${plugin.workflow.name}</plugin-workflow-name>
	<plugin-service-instance>notificationPluginService</plugin-service-instance>
	<method-name>pushNotification</method-name>
	<is-scripting>FALSE</is-scripting>
	<back-up-file-name>N/A</back-up-file-name>
	<script-name>N/A</script-name>
	<application-context-path>applicationContext-notification-plugin.xml</application-context-path>
	<plugin-properties>
		<plugin-property>
			<name>notification.active</name>
			<type>BOOLEAN</type>
			<description>Active ?</description>
			<is-mandatory>TRUE</is-mandatory>
			<is-multivalue>FALSE</is-multivalue>
		</plugin-property>
		<plugin-property>
			<name>notification.APIKey</name>
			<type>STRING</type>
			<description>API Key</description>
			<is-mandatory>TRUE</is-mandatory>
			<is-multivalue>FALSE</is-multivalue>
		</plugin-property>
		<plugin-property>
			<name>notification.deviceIds</name>
			<type>STRING</type>
			<description>Device IDs</description>
			<is-mandatory>TRUE</is-mandatory>
			<is-multivalue>FALSE</is-multivalue>
		</plugin-property>
		<plugin-property>
			<name>notification.title</name>
			<type>STRING</type>
			<description>Title</description>
			<is-mandatory>TRUE</is-mandatory>
			<is-multivalue>FALSE</is-multivalue>
		</plugin-property>
		<plugin-property>
			<name>notification.body</name>
			<type>STRING</type>
			<description>Body</description>
			<is-mandatory>FALSE</is-mandatory>
			<is-multivalue>FALSE</is-multivalue>
		</plugin-property>
		<plugin-property>
			<name>notification.addLink</name>
			<type>BOOLEAN</type>
			<description>Add link ?</description>
			<is-mandatory>TRUE</is-mandatory>
			<is-multivalue>FALSE</is-multivalue>
		</plugin-property>
		<plugin-property>
			<name>notification.url</name>
			<type>STRING</type>
			<description>Link URL ?</description>
			<is-mandatory>FALSE</is-mandatory>
			<is-multivalue>FALSE</is-multivalue>
		</plugin-property>
	</plugin-properties>
	<dependencies>
	</dependencies>
</plugin>

 The assembly configuration

To import a plugin in Ephesoft, you have to provide a ZIP file containing two files: (1) The XML file ephesoft-module-notification.xml that contains the definition of the plugin and (2) a JAR file using the same, i.e. ephesoft-module-notification.jar. So, I decided to use the assembly plugin to match these constraints. First, you need to configure your POM file with this piece of XML code:

	<build>
		<plugins>
			<plugin>
				<artifactId>maven-assembly-plugin</artifactId>
				<version>2.4</version>
				<configuration>
					<finalName>${project.artifactId}</finalName>
					<filters>
						<filter>plugin.properties</filter>
					</filters>
					<descriptors>
						<descriptor>distribution.xml</descriptor>
					</descriptors>
				</configuration>
				<executions>
					<execution>
						<id>make-assembly</id> <!-- this is used for inheritance merges -->
						<phase>package</phase> <!-- bind to the packaging phase -->
						<goals>
							<goal>single</goal>
						</goals>
						<configuration>
							<appendAssemblyId>false</appendAssemblyId>
						</configuration>
					</execution>
				</executions>
			</plugin>
		</plugins>
	</build>

The next thing is to define the distribution:

<assembly xmlns="http://maven.apache.org/plugins/maven-assembly-plugin/assembly/1.1.2" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://maven.apache.org/plugins/maven-assembly-plugin/assembly/1.1.2 http://maven.apache.org/xsd/assembly-1.1.2.xsd">
	<id>distribution</id>
	<formats>
		<format>zip</format>
	</formats>
	<includeBaseDirectory>false</includeBaseDirectory>
	<dependencySets>
		<dependencySet>
			<outputDirectory>/</outputDirectory>
			<useProjectArtifact>true</useProjectArtifact>
			<includes>
				<include>com.ephesoft:ephesoft-module-notification</include>
			</includes>
			<outputFileNameMapping>${artifact.artifactId}.${artifact.extension}</outputFileNameMapping>
		</dependencySet>
	</dependencySets>
	<files>
		<file>
			<source>src/main/resources/ephesoft-module-notification.xml</source>
			<outputDirectory>/</outputDirectory>
			<filtered>true</filtered>
		</file>
	</files>
</assembly>

The deploying phase

After building the ZIP file, you need:

  • Open the Workflow Magement page on http://<EPHESOFT_URL>/dcma/CustomWorkflowManagement.html
  • Click on the button Add New Plug-in and upload the ZIP file.
  • After uploading the ZIP file, you need to re-start your Ephesoft server.
  • When your server is successfully restarted, you need to open the batch class management page and edit the batch class that you want.
  • Click on the module where you want to add the plugin. In our case, it will be the Validate Document module.
  • Click on the button Configure and add the Android Notification plugin just before the Validate plugin.

  • Next, click on the button OK
  • After, you need to deploy the workflow. To accomplish that, you need to click on the button Validate.
  • And next Deploy Workflow and the button Normal Workflow.
  • Now, the plugin is imported and deployed but you still need to configure it. You just need to double-click on the plugin ANDROID_NOTIFICATION_PLUGIN and fill all parameters.

Your plugin is ready to use and you can just test it.

Conclusion

It needs me a bit of time to develop my plugin following instructions on the Ephesoft wiki: http://www.ephesoft.com/wiki/index.php?title=Developers_Guide#Creating_Sample_Plugin. But, there is not a lot of information to do that. After this learning step, it becomes now easy to create new plugins. You can find all the code in GitHub: https://github.com/bchevallereau/ephesoft-extension/tree/master/ephesoft-module-notification.

Comments

Great review. I wanted to let you and your readers know that the ability to update and delete the plugins will be available in v3.2 (late spring/early summer).

Thanks, and I'm really excited to see this new version and play with it :)!

Thank you for sharing this. I have been beginner to Ephesoft custom Plugin development and this article will surely help me. However, I would like to know if there is a possibility to get information about Batch Class level field inside plugin implementation class. For instance, in your example, you have access to Batch ID via BatchInstanceID batchInstanceID parameter. I have created new Batch Class level field called "BatchType". I want to write custom logic around value of this field which is selected by user at the time of scanning. Any help/guideline would be appreciated. Thank you once again.

Hi,
I think that you can use the batch instance service for that (com.ephesoft.dcma.da.service.BatchInstanceService). I don't know an easy way to do that, but what I would recommend is to get the batchInstance object; using this one, try to get the location of the ZIP file containing the XML file describing your batch instance; and finally open it using an XML reader to navigate in this XML file and read batch class fields.

Hello again. While I posted a question about this subject yesterday, I was playing with available Ephesoft services. Then I came across com.ephesoft.dcma.batch.service.BatchSchemaService and that did work. Just like BatchClassPluginConfigService, I added BatchSchemaService to Plugin implementation class. And using its getBatch(batchInstanceID.getID()) method, I got entire Batch.xml schema as com.ephesoft.dcma.batch.schema.Batch object. By this way, I was able to get value of Batch Class level field. Thank you once again and hope this helps.

Add new comment