Wednesday, May 23, 2012

OSB and JMS Correlation Part 2

continuing...

I import the WSDL of my test service that will validate the order

I then create a Business Service based on the WSDL

I test the Service


If the custID = 1111 and the totalPrice is > 10K then the order is invalid.


Now call this from the request pipeline using a Service Callout action -


The table below explains the different "Configure" options


Now we need to set VO_REQ via an Assign action


The expression is as follows -


Save and Test


Looks good. Now I add the logic to write invalid orders to the Queue-Error.

Firstly, I created a business service to Write to the demoQueue-Error.
I then call it as follows - per default the original payload, in $body, is being written to the error Queue.



IF Expression - 


 Test 


then check the Error Queue in WLS console 








OSB and JMS Correlation example

Simple scenario of using OSB as JMS consumer and producer, leveraging correlation.

To begin with, I create the JMS artifacts via the WLS console -

1. Create a new JMS server


2. Create a new JMS module


3. Add a ConnectionFactory and a couple of Queues to the JMS module



Now we have the required JMS artifacts, on to OSB.

Creating the OSB Project

Create a new project in OSB - the scenario in detail. 
OSB proxy service reads an incoming order from the Queue-In. It calls a web service to validate the order. If the order is invalid, then it is written to the Queue-Error. If the order is valid, then it is written to the Queue-Out.

The incoming order is defined as follows -


4.1. Create the project structure


4.2. Import or Create the XSD


4.3. Create the proxy service for the JMS consumer. I have used the Message service  type.


Here I specify that the input will be an element of type OrderData





4.4. Add a Pipeline pair

4.5. Create a Business Service to write to Queue-Out

So what sort of a service do we require here? According to the official docs - If you want to expose one port to clients for a variety of enterprise applications, use Any SOAP or Any XML service types.

For Any SOAP, you must specify if it is SOAP 1.1 or SOAP 1.2. The SOAP service does not have an explicitly defined, concrete interface, i.e. not based on a WSDL.

For Any XML Service, the payload must be a well-formed XML document. The XML Service does not have an explicitly defined, concrete interface.  

N.B. HTTP GET is only supported for messaging services and this service type.
 
We also can use the following -  

Transport Typed Service - Select this option to create a service that uses the EJB, JEJB, or Flow (Split-Join) transport.

Messaging Service - Select this option to create a service that exchanges messages of different content-types. These exchanges can be either request/response or one-way. They can also have a response with no request when used with the HTTP ‘GET’ option for the HTTP transport. Unlike Web Services, the content-type of the request and response need not be the same.

WSDL Web Service - Select this option to create a business service based on a WSDL. (Split-Join) transport.

The 2 that may come immediately into mind are Any SOAP and Any XML.
I chose Any XML and specified the jms transport/Queue-Out etc.


4.6. Amend the proxy service to route to the business service

Test as follows -
Here is a test input file

Here is a Java Class that writes to the Queue-In




 Run and then look at the out Queue in the WLS console


Now add some correlation.

I add the following to the Java client

     textMsg.setJMSCorrelationID("1234");



Now amend the OSB process so that the Business Service can use this correlationID

Add a Transport Header action as follows-
Open the proxy service message flow and add the following to the Route node.





 Save and re-test

  textMsg.setJMSCorrelationID("1234567");

Login to WLS console and look at the Queue-Out


Add a couple of more messages with different correlationIDs.


 Now we need a JMS client to consume the messages based on the correlationID.


Re-visit WLS console -


One of the value adds of specifying the XSD during proxy service definition, is that $body is set accordingly - useful when doing Assigns etc.


  If I had set the Proxy to -

 then $body is -




 I will continue with this process in the next post.

Monday, May 14, 2012

BPM 11g Human task - Update Priority via API

Scenario - I have a BPM process as follows -


Sales task assigned to jcooper
Legal task assigned to mtwain
ProcessOwner is weblogic

The default priority for the human tasks is set to 3






Now I want to use the Java API to update the task priorities to 1.






Here is the code snippet -

    public String updatePriority4AllTasks(String user,
                                          String password) throws Exception {
        System.out.println("updatePriority4AllTasks() for " + user);
        Map properties = new HashMap();
        properties.put(IWorkflowServiceClientConstants.CONNECTION_PROPERTY.EJB_PROVIDER_URL,
                       "t3://localhost:7001");
        properties.put(IWorkflowServiceClientConstants.CONNECTION_PROPERTY.EJB_SECURITY_CREDENTIALS,
                       "welcome1");
        properties.put(IWorkflowServiceClientConstants.CONNECTION_PROPERTY.EJB_SECURITY_PRINCIPAL,
                       "weblogic");


        //Create JAVA WorkflowServiceClient
        IWorkflowServiceClient wfSvcClient =
            WorkflowServiceClientFactory.getWorkflowServiceClient(WorkflowServiceClientFactory.REMOTE_CLIENT,
                                                                  properties,
                                                                  null);

        //Get the task query service
        ITaskQueryService querySvc = wfSvcClient.getTaskQueryService();

        //Login as user specified
        IWorkflowContext ctx =
            querySvc.authenticate(user, password.toCharArray(), null);

        //Set up list of columns to query
        List queryColumns = new ArrayList();
        queryColumns.add("TASKID");
        queryColumns.add("TASKNUMBER");
        queryColumns.add("TITLE");
        queryColumns.add("OUTCOME");

        /*
     * Query a list of tasks owned by the user
     * Note setting of AssignmentFilter.OWNER
    */

        List tasks =
            querySvc.queryTasks(ctx, queryColumns, null, //Do not query additional info
                ITaskQueryService.AssignmentFilter.OWNER, null, //No keywords
                null, //No custom predicate
                null, //No special ordering
                0, //Do not page the query result
                0);

        //Get the task service
        ITaskService taskSvc = wfSvcClient.getTaskService();
        ITaskQueryService itqs = wfSvcClient.getTaskQueryService();

        //Loop over the tasks, outputting task information,
        System.out.println("You are the owner of the following live tasks:");

        for (int i = 0; i < tasks.size(); i++) {


            Task task = (Task)tasks.get(i);

            int taskNumber = task.getSystemAttributes().getTaskNumber();
            String title = task.getTitle();
            String taskId = task.getSystemAttributes().getTaskId();
            String outcome = task.getSystemAttributes().getOutcome();
            String state = task.getSystemAttributes().getState();
            if (state.equalsIgnoreCase("ASSIGNED")) {
               /*
                * Build up the assignee list
                */
                List l = task.getSystemAttributes().getAssignees();
                String assignees = "";
                IdentityTypeImpl iti;
          
                for (int j = 0; j < l.size(); j++) {
                    iti = (IdentityTypeImpl)l.get(j);
                    assignees = assignees + " " + iti.getId();
                }

                System.out.println("Task ID#" + taskId + "Task Nr#" +
                                   taskNumber + " " + "(" + title + ")" +
                                   ". State is " + state + ". Assignees:" +
                                   assignees);

                Task t = itqs.getTaskDetailsById(ctx, taskId);
                //

                System.out.println("updating priority for taskNr " +
                                   taskNumber);
         
                t.setPriority(1);
                taskSvc.updateTask(ctx, t);

            }

        }


        return "done";
    }

Imports
---------------------

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Hashtable;
import java.util.List;

import java.util.Map;

import oracle.bpel.services.workflow.client.IWorkflowServiceClient;
import oracle.bpel.services.workflow.client.IWorkflowServiceClientConstants;
import oracle.bpel.services.workflow.client.WorkflowServiceClientFactory;
import oracle.bpel.services.workflow.query.ITaskQueryService;

import oracle.bpel.services.workflow.repos.TableConstants;
import oracle.bpel.services.workflow.task.ITaskService;
import oracle.bpel.services.workflow.task.model.Task;
import oracle.bpel.services.workflow.verification.IWorkflowContext;

import oracle.bpel.services.workflow.repos.Predicate;
import oracle.bpel.services.workflow.task.ITaskAssignee;
import oracle.bpel.services.workflow.task.model.IdentityTypeImpl;

---------------------------

Friday, May 4, 2012

OEG and SAML Authorization

Next variation on the theme - SAML Authorization. I have a web service deployed to WLS -


I register it with OEG -

I create the following policy -

Now let's look at the first filter -


Note the following -
SOAP Actor/Role set to Current Actor/Role only
Resource set to http://localhost:8082/SAMLAuthoriseDemo
   This will be the OEG URL.
   /SAMLAuthoriseDemo being the relative path I'll create later.


For Trusted Issuer:
I just selected one from the list offered, after pressing the Add button.
The Web Service filter simply calls the FraudCheckService


I create the relative path


I deploy and test


As expected, it throws an error -


Back in Service Explorer - add a SAML Authorization token


Configure as follows -
Choose the same TrustedIssuer as specified in the policy as the policy filter only accepts assertions that have been issued by the selected SAML Authorities.

Set the Resource value to http://localhost:8082/SAMLAuthoriseDemo
Set the Action value to Read


View the token generated


Re-Test


We can also encrypt the token in Service Explorer



re-test