Writing a distributed application on AWS

Amazon Simple Workflow Service (SWF) is a workflow service offering that supports building, running, and scaling asynchronous jobs that have parallel or sequential steps as part of their process executions. Amazon SWF can be considered a completely managed state tracker and task coordinator for cloud applications.

An important offering of Amazon SWF for distributed applications is that it enables applications to run as numerous processes, which could be distributed between the number of systems, including Amazon EC2 instances, client computers, and private data centers, that might have different operating systems on each machine. As an example, we can deploy a workflow worker on an Amazon EC2 platform, a workflow starter on a data center system, and the activities on a client desktop system. We could also deploy different activities on different systems.

The following diagram represents a sample workflow setup with Amazon SWF for the program we will review in this section:

Workflow activities can be denoted as asynchronous methods that get executed and that return a response to permit the workflow to perform further tasks, which are waiting for the activity to get completed.

Workflow starters communicate with workflow workers through an HTTP request, with Amazon SWF helping them to interact. Workflow workers communicate with the activities and workers through an HTTP request, with Amazon SWF helping them to interact.

The AWS Flow Framework for Java and Amazon SWF holds the responsibility of this workflow to work efficiently, which helps developers concentrate on building business logic.

Let's review a sample program to develop an instance of Amazon SWF based on a distributed application. Let's start with a workflow activity interface with the following three methods:

package amazonswf;

import com.amazonaws.services.simpleworkflow.flow.annotations.Activities;
import com.amazonaws.services.simpleworkflow.flow.annotations.ActivityRegistrationOptions;

@ActivityRegistrationOptions(defaultTaskScheduleToStartTimeoutSeconds = 300,
defaultTaskStartToCloseTimeoutSeconds = 10)
@Activities(version="1.0")
public interface SWFActivities {

public String getName();
public String getMessage(String name);
public void printMessage(String message);
}

An implementation of this SWFActivities interface, which acts as the workflow activity's implementation, is as follows. It has methods that were implemented after they were defined in the interface:

package amazonswf;

public class SWFActivitiesImpl implements SWFActivities {

@Override
public String getName() {
return "Raja";
}

@Override
public String getMessage(String name) {
return "Hello " + name;
}

@Override
public void printMessage(String message) {
System.out.println(message);
}

}

Now, let's define the next component, which is a workflow interface, with a method declaration:

package amazonswf;

import com.amazonaws.services.simpleworkflow.flow.annotations.Execute;
import com.amazonaws.services.simpleworkflow.flow.annotations.Workflow;
import com.amazonaws.services.simpleworkflow.flow.annotations.WorkflowRegistrationOptions;

@Workflow
@WorkflowRegistrationOptions(defaultExecutionStartToCloseTimeoutSeconds = 3600)
public interface SWFWorkflow {

@Execute(version = "1.0")
public void message();

}

The following is the implementation of SWFWorkflow that implements the message() method that interacts with the workflow activities:

package amazonswf;

import com.amazonaws.services.simpleworkflow.flow.core.Promise;

public class SWFWorkflowImpl implements SWFWorkflow {

private SWFActivities activites = new SWFActivitiesImpl();

@Override
public void message() {
Promise<String> name = activites.getName();
Promise<String> greeting = activites.getGreeting(name);
activites.say(greeting);
}

}

Now we can define a worker component that would run the workflow worker component and make it available to the main component that wants to invoke the worker component and activities built, as follows:

package amazonswf;

import com.amazonaws.ClientConfiguration;
import com.amazonaws.auth.AWSCredentials;
import com.amazonaws.auth.BasicAWSCredentials;
import com.amazonaws.services.simpleworkflow.AmazonSimpleWorkflow;
import com.amazonaws.services.simpleworkflow.AmazonSimpleWorkflowClient;
import com.amazonaws.services.simpleworkflow.flow.ActivityWorker;
import com.amazonaws.services.simpleworkflow.flow.WorkflowWorker;

public class SWFWorker {

public static void main(String[] args) throws Exception {
ClientConfiguration config =
new ClientConfiguration().withSocketTimeout(70*1000);
String swfAccessId = System.getenv("AWS_ACCESS_KEY_ID");
String swfSecretKey = System.getenv("AWS_SECRET_KEY");
AWSCredentials awsCredentials =
new BasicAWSCredentials(swfAccessId, swfSecretKey);
AmazonSimpleWorkflow service =
new AmazonSimpleWorkflowClient(awsCredentials, config);
service.setEndpoint("https://swf.sampleworkflow.com");
String domain = "helloWorldWalkthrough";
String taskListToPoll = "HelloWorldList";

ActivityWorker aw =
new ActivityWorker(service, domain, taskListToPoll);
aw.addActivitiesImplementation(new SWFActivitiesImpl());
aw.start();
WorkflowWorker wfw =
new WorkflowWorker(service, domain, taskListToPoll);
wfw.addWorkflowImplementationType(SWFWorkflowImpl.class);
wfw.start();
}

}

Finally, you can build and deploy the following main component that will interact with the workflow methods:

package amazonswf;

import com.amazonaws.ClientConfiguration;
import com.amazonaws.auth.AWSCredentials;
import com.amazonaws.auth.BasicAWSCredentials;
import com.amazonaws.services.simpleworkflow.AmazonSimpleWorkflow;
import com.amazonaws.services.simpleworkflow.AmazonSimpleWorkflowClient;

public class SWFMain {

public static void main(String[] args) throws Exception {
ClientConfiguration config =
new ClientConfiguration().withSocketTimeout(70*1000);
String swfAccessId = System.getenv("AWS_ACCESS_KEY_ID");
String swfSecretKey = System.getenv("AWS_SECRET_KEY");
AWSCredentials awsCredentials =
new BasicAWSCredentials(swfAccessId, swfSecretKey);
AmazonSimpleWorkflow service =
new AmazonSimpleWorkflowClient(awsCredentials, config);
service.setEndpoint("https://swf.sampleworkflow.com");
String domain = "helloWorldWalkthrough";
SWFWorkflowClientExternalFactory factory =
new SWFWorkflowClientExternalFactoryImpl(service, domain);
SWFWorkflow workflow = factory.getClient("clientID");
workflow.message();
}

}

By deploying the preceding application using Amazon SWF, you will notice that each workflow instance has its own unique run ID for the execution. The same execution ID can be used for other workflow instances, executing one active flow run at a time.

In the preceding example, SWFWorker has the workflow and activity hosted in the same application. For the following approach, we need to run the workflow and activity implementations on separate systems as follows by replacing the just defined SWFWorker with two new components, namely SWFWorkflowWorker and SWFActivitiesWorker:

package amazonswf;

import com.amazonaws.ClientConfiguration;
import com.amazonaws.auth.AWSCredentials;
import com.amazonaws.auth.BasicAWSCredentials;
import com.amazonaws.services.simpleworkflow.AmazonSimpleWorkflow;
import com.amazonaws.services.simpleworkflow.AmazonSimpleWorkflowClient;
import com.amazonaws.services.simpleworkflow.flow.WorkflowWorker;

public class SWFWorkflowWorker {
public static void main(String[] args) throws Exception {
ClientConfiguration config =
new ClientConfiguration().withSocketTimeout(70*1000);
String swfAccessId = System.getenv("AWS_ACCESS_KEY_ID");
String swfSecretKey = System.getenv("AWS_SECRET_KEY");
AWSCredentials awsCredentials =
new BasicAWSCredentials(swfAccessId, swfSecretKey);
AmazonSimpleWorkflow service =
new AmazonSimpleWorkflowClient(awsCredentials, config);
service.setEndpoint("https://swf.sampleworkflow.com");
String domain = "helloWorldExamples";
String taskListToPoll = "HelloWorldAsyncList";
WorkflowWorker wfw =
new WorkflowWorker(service, domain, taskListToPoll);
wfw.addWorkflowImplementationType(SWFWorkflowImpl.class);
wfw.start();
}

}

While the earlier SWFWorkflowWorker component handles the workflow worker, the following SWFActivitiesWorker component takes care of the activity worker:

package amazonswf;

import com.amazonaws.ClientConfiguration;
import com.amazonaws.auth.AWSCredentials;
import com.amazonaws.auth.BasicAWSCredentials;
import com.amazonaws.services.simpleworkflow.AmazonSimpleWorkflow;
import com.amazonaws.services.simpleworkflow.AmazonSimpleWorkflowClient;
import com.amazonaws.services.simpleworkflow.flow.ActivityWorker;

public class SWFActivitiesWorker {
public static void main(String[] args) throws Exception {
ClientConfiguration config =
new ClientConfiguration().withSocketTimeout(70*1000);
String swfAccessId = System.getenv("AWS_ACCESS_KEY_ID");
String swfSecretKey = System.getenv("AWS_SECRET_KEY");
AWSCredentials awsCredentials =
new BasicAWSCredentials(swfAccessId, swfSecretKey);
AmazonSimpleWorkflow service =
new AmazonSimpleWorkflowClient(awsCredentials, config);
service.setEndpoint("https://swf.sampleworkflow.com");
String domain = "helloWorldExamples";
String taskListToPoll = "HelloWorldAsyncList";
ActivityWorker aw = new ActivityWorker(service,
domain, taskListToPoll);
aw.addActivitiesImplementation(new SWFActivitiesImpl());
aw.start();
}

}

The following are the steps you need to follow to execute the workflow:

  1. Create a runnable JAR file with SWFActivitiesWorker as the execution starting point of the runnable JAR.
  2. Copy the just-defined JAR file to another system, which may be working on another operating system with support for Java.
  3. Ensure that the AWS credentials that have access to your Amazon SWF domain are accessible on this second system.
  4. Execute the JAR file to start the workflow.
  5. From the development machine, execute SWFWorkflowWorker and SWFMain, which starts the main workflow and invokes the worker.

Similarly, other cloud providers, such as Red Hat OpenShift and Google App Engine, support the distributed application running on a cloud platform.

Now, let's review the latest CaaS offering from Docker and its features along with the steps to deploy a Java application with Docker CaaS.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset