I needed to configure some data mapping in a customers TechnologyOne Property & Rating system for an inbound HTTP request that contained XML in the request body. To retrieve values from the XML, I could create what is called an External Data Control to store a value in, and then map the External Data Control to the relevant field in the object being created/updated.
The following were my requirements:
- When approvalType = ‘DA’:
- set Field1 as relatedCaseNumber
- set Field 2 as NULL
- When approvalType = ‘CDC’
- set Field1 as NULL
- set Field 2 as relatedCaseNumber
To be able to achieve the above requirement, I needed two External Data Controls- one for setting Field1, and another for setting Field2. I
thought that I would be able to setup some simple IF logic for each External Data Control, such as if(A = ‘DA’) then B else NULL and if(A = ‘CDC’) then C else NULL. Unfortunately, I tried many variations of such logic with different syntax I found trawling through stackoverflow posts but none of them were able to provide the result I needed.
XPath Union
I ended up getting creative and used the following inside the External Data Controls to achieve the requirement:
(//attributes/attribute[@type=’field’]/data[@code=’approvalType’][text() = ‘DA’] | //attributes/attribute[@type=’field’]/data[@code=’relatedCaseNumber’])[2]
The above XPath statement uses a Union to return an array of all elements that are found. It is looking for two properties (approvalType = DA and relatedCaseNumber). The statement is selecting the second index of the array (which in XPath needs to be 2, as the first element has index 1, not 0 like in most other languages).
The effect of this is that if approvalType = DA, it will be the first index, and relatedCaseNumber will be the second. As our selector is getting the value of the second index, the XPath statement will only return the relatedCaseNumber value if approvalType = DA. If approvalType is not equal DA, then the relatedCaseNumber will be the first (and only) index, i.e. the second index will be NULL, thus satisfying our requirement.
Noting this, the XPath statements for the two External Data Controls is:
Field 1 = (//attributes/attribute[@type=’field’]/data[@code=’approvalType’][text() = ‘DA’] | //attributes/attribute[@type=’field’]/data[@code=’relatedCaseNumber’])[2]
Field 2 = (//attributes/attribute[@type=’field’]/data[@code=’approvalType’][text() = ‘CDC’] | //attributes/attribute[@type=’field’]/data[@code=’relatedCaseNumber’])[2]
XPather Tool
As I am new to XML and XPath, this online utility really helped me quickly identify the statement and syntax required: http://xpather.com