Shocking Revelation; Do PIM and CIM artifact actions over webservice calls
Hi there “Process Automation” fans,
Welcome to a new installment of “Process Automation” tips.
I had a decent sit with a daily administrator person to conclude that administering the “Process Automation” platform can be a real pain in the ass. Especially when you (as functional admin) can’t access the backend server or the database. In that case you’re limited (or better “crippled”) with the tools/artifacts like the PIM and the CIM…Nice tools, but with massive projects it works against you. Can we do this smarter? Can we do this better? I suppose we can, but for this we require some research where this post is step number one which is figuring out (R&D) the different service calls available for maintaining BPM instances and Case instances (which equal our entity lifecycle instances!).
Let get right into it…
So, it’s service time with lots of Soap messages to research…trying them out requires a small project with a basic implementation for a BPM and an entity ‘Lifecycle’ BB. Let’s spin up the “Process Automation” machine and jump through the hoops to learn the possibilities.
We start with a BPM implementation like this (to trigger some scenario’s):
Some notes:
Make it an eXclusive decision construct (in the ‘General’ tab)
Add an entity layout (you can reuse one of the platform entities) to the top activity (otherwise the BPM won’t stop at the activity!); It will land in the inbox at runtime for the current user.
The fail-scenario (downwards) requires an error-code and an error-value (see the properties for those constructs)
Select the input message in the properties of the green start construct
You can create a new input message from the messagemap tab of the BPM
Save it in the ‘bpms’ folder of the project; Mine is located like this:
Publish the BPM to make it available from the ‘Deployed Process Models’ artifact for later usage!
We’ll just start the BPM instances from the designer <F12> to get them in different states based on the input message; You’ll get a popup…try it yourself until you get different states in the PIM artifact.
With that BPM ready, we continue with a ‘Project’ entity (use just one property), and a ‘Lifecycle’ BB like this (lean and clean):
Again, some notes:
A lifecycle initiates on entity creation in runtime; So, do a publication and create some ‘project’ entity instances in runtime (under ‘/app/start’)
An empty activity (without a layout) like above will land in the inbox of the current user initializing the lifecycle; Yes, that’s a different mindset from the BPM implementation! Don’t shoot the messenger! 🤐
You find instances of these lifecycles in the CIM artifact.
With all this in place, we can now continue our journey…Finally, services time!
Services introduction
In the next section we’ll fire Soap requests against the Gateway of the platform (remember the post from last week!). We’ll keep it simple using the ‘Web Service Interface Explorer’ artifact. Looking at the messages below, you can find them by name, and you can trigger them with the ‘test’-action:
Sometimes you must watch out for the correct naming space which you can see in the messages below; Like for example the space http://schemas.cordys.com/bpm/deployment/1.0. A namespace makes it possible to use similar operation names within the platform without interfering each other; You directly see a good example in the screenshot above!
Finally, in the messages below you’ll find these variables for you (and me) to replace:
{process_name} = nl-bos-general/bpms/bmp_demo1 (watch the project structure image above again or dare to use your own!)
{process_instance_id} = A unique ID per BPM instance you start
{case_model_id} = A unique ID of the case/lifecycle for an entity (not the instance, but the template/model)
{case_instance_id} = A unique ID per case/lifecycle instance you start (equals the creation of a new entity instance!)
Time for some action…AND before I forget; Always put the below messages between the body:
1 2 3 4 5
<SOAP:Envelopexmlns:SOAP="http://schemas.xmlsoap.org/soap/envelope/"> <SOAP:Body> <!--Put the messages from below in here!--> </SOAP:Body> </SOAP:Envelope>
BPM models
These are service calls you can do on a deployed process model. So, there is no need to scroll through endless BPM models in the ‘Deployed Process Models’ artifact to do your tricks.
1 2 3 4 5 6 7 8 9 10 11
<!-- Get BPM models; Be careful on the 'numRows' value. You can search the response on the <configuration> element on "custom" logging levels! --> <GetAllProcessModels xmlns="http://schemas.cordys.com/bpm/deployment/1.0"> <cursorid="0"position="0"numRows="5"maxRows="99999" /> <modelSpace>organization</modelSpace> <detail>false</detail> </GetAllProcessModels>
1 2 3 4 5 6 7 8 9 10 11 12 13
<!--Get BPM models with specific details by xPath!--> <GetAllProcessModels xmlns="http://schemas.cordys.com/bpm/deployment/1.0"> <cursorid="0"position="0"numRows="5"maxRows="99999" /> <modelSpace>organization</modelSpace> <detail>true</detail> <details> <detailid="myRef1" xpath="processinstance/messagemap/instanceProperties/modelID" /> <detailid="myRef2" xpath="processinstance/messagemap/instanceProperties/modelID" /> </details> </GetAllProcessModels>
1 2 3 4 5 6
<!--Get information about a BPM model--> <GetProcessModel xmlns="http://schemas.cordys.com/bpm/deployment/1.0"> <processname>{process_name}</processname> <modelSpace>organization</modelSpace> </GetProcessModel>
1 2 3 4 5 6 7 8 9 10 11 12
<!-- Set the "custom" monitoring level for a BPM model; 13 equals "Process status, input, output messages and message-map" --> <SaveProcessModelConfiguration xmlns="http://schemas.cordys.com/bpm/deployment/1.0"> <configuration> <processName>{process_name}</processName> <monitorLevel>13</monitorLevel> <crashRecovery>0</crashRecovery> </configuration> </SaveProcessModelConfiguration>
1 2 3 4 5
<!--Reset the monitoring level--> <DeleteProcessModelConfiguration xmlns="http://schemas.cordys.com/bpm/deployment/1.0"> <processName>{process_name}</processName> </DeleteProcessModelConfiguration>
BPM instances
Once BPMs are instantiated from runtime, they will pass by in the PIM artifact. On a smaller scale it’s sufficient, but once going next level you start to see its limitation. So, have a look at the below messages to conquer BPM instances via service calls.
<!-- Get a summary of the BPM instances per BPM model by a set of filtered states. --> <GetProcessInstanceSummary xmlns="http://schemas.cordys.com/pim/queryinstancedata/1.0"> <Queryxmlns="http://schemas.cordys.com/cql/1.0"> <Select> <QueryableObject>InstancesSummary</QueryableObject> <Field>ProcessName</Field> <Field>ProcessFolder</Field> <Field>ShortProcessName</Field> <Field>Version</Field> <Field>ModelSpace</Field> <Field>NrTotal</Field> <Field>NrRunning</Field> <Field>NrQueued</Field> <Field>NrWaiting</Field> <Field>NrTerminated</Field> <Field>NrSkipped</Field> <Field>NrReplaced</Field> <Field>NrComplete</Field> <Field>NrAborted</Field> <Field>NrSuspended</Field> <Field>NrDebug</Field> <Field>NrDebugReady</Field> </Select> <Filters> <Infield="STATUS"> <Value>ABORTED</Value> <Value>WAITING</Value> <Value>RUNNING</Value> <Value>QUEUED</Value> </In> </Filters> </Query> </GetProcessInstanceSummary>
<!-- Get BPM instances; Be careful on the 'numRows' value! These are additional field: INSTANCE_ID, DESCRIPTION, IS_ARCHIVED, MODEL_SPACE, PROCESS_TYPE, SOAP_PROCESSOR, RUNTIME_DOCUMENT_ID, WORKSPACE_ID, HAS_INPUT_MESSAGE, HAS_OUTPUT_MESSAGE, HAS_MESSAGE_MAP, PARENT_ID, PARENT_TYPE, ROOT_TYPE, CRASH_RECOVERY, ORIGINAL_ID, SUBSTITUTE_ID, HAS_ERROR Optionally a filter to show only aborted and duration greater than 5 min. for a specific process. --> <GetProcessInstances xmlns="http://schemas.cordys.com/pim/queryinstancedata/1.0"> <Queryxmlns="http://schemas.cordys.com/cql/1.0"> <Select> <QueryableObject>PROCESS_INSTANCE</QueryableObject> <Field>START_TIME</Field> <Field>PROCESS_NAME</Field> <Field>STATUS</Field> <Field>END_TIME</Field> <Field>USER_NAME</Field> <Field>TYPE</Field> <Field>ROOT_ID</Field> <!-- Add this from the below IDENTIFIER_ID result! <Field alias="IDENTIFIER_VALUE1">BusinessIdentifierID:{IDENTIFIER_ID}</Field> --> </Select> <Filters> <And> <EQfield="PROCESS_NAME"> <Value>{process_name}</Value> </EQ> <GTfield="DURATION"> <Value>300000</Value> </GT> <Infield="STATUS"> <Value>ABORTED</Value> <Value>WAITING</Value> <Value>RUNNING</Value> </In> <!-- Add this from the below IDENTIFIER_NAME result! <EQ field="BusinessIdentifier:{IDENTIFIER_NAME}"> <Value>{your_value}</Value> </EQ> --> </And> </Filters> <CursornumRows="10"position="0"/> <OrderBy> <Propertydirection="desc">START_TIME</Property> </OrderBy> </Query> </GetProcessInstances>
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
<!--Get the business identifiers which you can use in the above message! --> <GetBusinessIdentifierDefinitions xmlns="http://schemas.cordys.com/pim/queryinstancedata/1.0"> <Queryxmlns="http://schemas.cordys.com/cql/1.0"> <Select> <QueryableObject>BusinessIdentifierDefinition</QueryableObject> <Field>IDENTIFIER_ID</Field> <Field>IDENTIFIER_NAME</Field> <Field>IDENTIFIER_DESCRIPTION</Field> <Field>IDENTIFIER_TYPE</Field> <Field>IDENTIFIER_PRECISION</Field> <Field>MODEL_SPACE</Field> <Field>ORGANIZATION</Field> </Select> </Query> </GetBusinessIdentifierDefinitions>
<!--Restart process instances; <receiver> is repeating!--> <RestartProcessxmlns="http://schemas.cordys.com/bpm/monitoring/1.0"> <receiver>{process_instance_id}</receiver> <activityID/> <batch>true</batch> </RestartProcess> <!--Suspend process instances --> <SuspendProcessxmlns="http://schemas.cordys.com/bpm/monitoring/1.0"> <receiver>{process_instance_id}</receiver> <batch>true</batch> </SuspendProcess> <!--Resume process instances --> <ResumeProcessxmlns="http://schemas.cordys.com/bpm/monitoring/1.0"> <receiver>{process_instance_id}</receiver> <batch>true</batch> </ResumeProcess> <!--Terminate process instances --> <TerminateProcessxmlns="http://schemas.cordys.com/bpm/monitoring/1.0"> <receiver>{process_instance_id}</receiver> <batch>true</batch> </TerminateProcess>
1 2 3 4 5 6 7
<!-- Remove a "completed" from the PIM; Keep in mind there are cleaning tools available too! --> <DeleteInstanceDataxmlns="http://schemas.cordys.com/bpm/monitoring/1.0"> <transaction_id>{process_instance_id}</transaction_id> </DeleteInstanceData>
Finally, what we can do for the BPM instances in the PIM is also possible for the Lifecycle/Case instances in the CIM!
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
<!--Get a summary of different type of cases/lifecycles (aka your entities!)--> <GetCaseInstanceSummary xmlns="http://schemas.cordys.com/casemanagement/instanceadministration/1.0"> <Queryxmlns="http://schemas.cordys.com/cql/1.0"> <Select> <QueryableObject>BPM_MODEL</QueryableObject> <Field>MODEL_ID</Field> <Field>MODEL_NAME</Field> <Field>CURRENT_REVISION</Field> <Fieldalias="CASE_MODEL_STATUS">STATUS</Field> <Field>CASE_INSTANCE_STATUS</Field> <Field>COUNT</Field> </Select> </Query> </GetCaseInstanceSummary>
<!--Action you can do on a case; Depends on the current state!--> <!--Restart (an aborted) case instance--> <RestartCaseInstance xmlns="http://schemas.cordys.com/casemanagement/instanceadministration/1.0"> <caseinstanceid>{case_instance_id}</caseinstanceid> </RestartCaseInstance> <!--Suspend a case instance--> <SuspendCaseInstance xmlns="http://schemas.cordys.com/casemanagement/instanceadministration/1.0"> <caseinstanceid>{case_instance_id}</caseinstanceid> </SuspendCaseInstance> <!--Resume a case instance--> <ResumeCaseInstance xmlns="http://schemas.cordys.com/casemanagement/instanceadministration/1.0"> <caseinstanceid>{case_instance_id}</caseinstanceid> </ResumeCaseInstance> <!--Terminate a case instance--> <TerminateCaseInstance xmlns="http://schemas.cordys.com/casemanagement/instanceadministration/1.0"> <caseinstanceid>{case_instance_id}</caseinstanceid> </TerminateCaseInstance> <!--Delete a case instance--> <DeleteCaseInstance xmlns="http://schemas.cordys.com/casemanagement/instanceadministration/1.0"> <caseinstanceid>{case_instance_id}</caseinstanceid> </DeleteCaseInstance> <!--Close a case instance--> <CloseCaseInstance xmlns="http://schemas.cordys.com/casemanagement/instanceadministration/1.0"> <caseinstanceid>{case_instance_id}</caseinstanceid> </CloseCaseInstance>
That’s it for this nice overview…
A great “DONE” where we now have a great overview of the possible service calls that we can execute on BPM instance and Lifecycle instances. This gives brilliant input for our next step on crafting our own artifact showing details “the new way”! Keep it locked here as we’ll expose greatness to benefit from. Have a good weekend and I see you next week!
Don’t forget to subscribe to get updates on the activities happening on this site. Have you noticed the quiz where you find out if you are also “The Process Automation guy”?