Dataweave check if a value is contained within a YAML list - mule

I want to check if the value present in the YAML list.
I have product.yaml
intGrp:
- "A"
- "CD"
- "EF"
- "ABC"
- "CDEF"
From transform message I want to check
If (intGrp contains payload.myvalue) this else that
Tried
%dw 2.0
var prop = Mule::p('intGrp')
output application/json
---
{
a: prop contains ("A")
}
But that doesn't solve my problem. Because I want to do an exact string match. i.e if I give
a: prop contains ("AB") I should get a false as there is no product as "AB".
Any help would be highly appreciated.
Thank you

The problem is that the YAML array is interpreted as a comma separated string in the property. The contains() function works differently in strings than in array. In strings it searches for a matching substring, hence 'AB' returns true. You could convert the string it back to an array using the splitBy() DataWeave function. I'm showing both side by side to highlight the difference:
%dw 2.0
var prop = Mule::p('intGrp')
var propArray = Mule::p('intGrp') splitBy ','
output application/json
---
{
raw: prop,
array: propArray,
a: propArray contains ("A"),
ab: propArray contains ("AB")
}
The output is:
{
"raw": "A,CD,EF,ABC,CDEF",
"array": [
"A",
"CD",
"EF",
"ABC",
"CDEF"
],
"a": true,
"ab": false
}
Note that if any of the entries contains a comma it will be split too.

Related

Array in payload is string, need to coerce to array type (DataWeave)

I have a payload I'm receiving from debezium/kafka as
"reasons": "[7,10,9]" with the array as a string.
I need to filter the array to extract when the item is 10 or 11. Since the array is actually a string in the payload I need to coerce it to an array to filter.
This is my current solution, but I feel there has to be a more efficient way:
%dw 2.0
output application/json
var data = payload.payload.after
var reasons = data.reasons replace "[" with "" replace "]" with "" splitBy "," filter ((num, numIndex) -> num != "10" and num != "11")
---
{
"dnsType": if (dnsType[0] == "11") "clinical" else if (dnsType[0] == "10") "non-clinical" else ""
}
If the string content is compatible with a JSON array then you can use the read() function to let DataWeave parse it for you.
Example read(data.reasons,"application/json")

Sorting the string with comma separated numbers and assign sequence

I have a string value coming as "AH-0000006620, AH-0000006619, AH-0000006621", where I need to Remove the Prefix and the remaining numbers "0000006620, 0000006619, 0000006621" to be sorted in Ascending order and I want to store the sequence number for each of them like
for 0000006619 value to be 1
for 0000006620 value to be 2
for 0000006621 value to be 3
So that when I send the info to target system, while iterating the array, for the first element if it is 0000006620 then I will pass the value as 2 for the other sequence tag.
Please let me know how I can achieve this.
You can tweak this though this should serve as a good starting point to what you are looking for:
Script
%dw 2.0
import * from dw::core::Strings
output application/json
var inp = "AH-0000006620,AH-0000006619,AH-0000006621"
---
{((inp replace"AH-" with "") splitBy "," map ($ replace /^0+/ with "") orderBy $ map {
(leftPad($ as String,10,0)) : ($$)
})}
You can do it this way as well.
{((inp replace"AH-" with "") splitBy "," orderBy $ as Number map {
($) : ($$)
})}
**Output**
[
{
"0000006619": 0
},
{
"0000006620": 1
},
{
"0000006621": 2
}
]

remove all the extra lines from the array in mule 4

I want to remove the extra lines or "\n\r" & "\n" from the array but my solution is not working. Please provide the correct function or dataweave for this.
input (json array format):
[{"m":"a\n\r",
"a":"b\n"},
{"m":"a\r\n",
"a":"b\n"}]
expected output(json array format):
[{"m":"a",
"a":"b"},
{"m":"a",
"a":"b"}]
code:
%dw 2.0
var someSpaceJson = write(payload, "application/json", {"indent":false})
output application/json
---
someSpaceJson replace "\n\r" with ""
You need to specify \\ instead of \ to represent the escape char.
%dw 2.0
var someSpaceJson = write(payload, "application/json", {"indent":false})
output application/json
---
read((someSpaceJson replace "\\r" with "" replace "\\n" with ""),"application/json")
This should give you your desired output.
If you want to preserve the new lines between the values and only want to remove the trailing \r's and \n's you can use the following. This will also avoid converting JSON to string and back which generally should be avoided.
%dw 2.0
output application/json
---
payload map ($ mapObject ($$): trim($))
However, you need to make sure that all values are string or null. If that is not the case you can add those conditions in the mapObject function itself.

IF statement into another IF statement DW 2.0

var lnc_id = []
output application/java
---
if (payload.success contains true and payload.accepted contains true)
{
if (lnc_id contains vars.payload_json.data.LNC_ID)
{
lnc_id + lnc_id contains vars.payload_json.data.LNC_ID
}
}
I'm writing and Api with Mulesoft and I need an IF inside another IF, the language is Datawave 2.0.
The error is:
"Invalid input "f ", expected Namespace "
You script has several issues:
{} denotes an object, you need to
use attributes inside an object instead of expressions.
Each if has to have an else clause.
lnc_id will
not preserve values between executions, so it will always start as an
empty array (this might be expected but I wanted to clarify it just in case).
This is a simpler example of how to nest if...else
var list = []
var success = true
output application/java
---
if (success == true )
if (3 > 2)
( list + "something")
else null
else null

Can I decide whether to use the payload that is returned by dataweave lookup?

I am using dataweave lookup to return additional information for a payload message.
Is there a way I can decide whether I can use the payload returned from the flow if the message status is not one I want?
I can't seem to get the syntax correct so far using when and otherwise conditions and cannot see much help online.
The lookup function is being called on the fly if the payload contains an error message and will remove the user record. The lookup returns an object containing 2 fields and I only want to include the result if it status field is "rollback"
Dataweave code:
%dw 1.0
%output application/xml
---
{
(data: {
userId: flowVars.userId,
Message: "User created successfully"
}) when (payload.user?) and
((payload.status == "SUCCESS")),
(Exception: {
userId: flowVars.userId,
Message: payload.exception.message,
("data":lookup("deleteuserfromgroup",payload.userId))
})when (payload.exception?) and
(payload.exception.status != "-1")
}
Thanks
There are many conditional example in DataWeave Reference Documentation. Following is one of the simple examples:
%dw 1.0
%output application/json
%var lookupValue = lookup("flowName", payload)
---
{
//set default when null
default: lookupValue default "defaultValue",
//when or otherwise
when: lookupValue when lookupValue.status == "expectedValue" otherwise "defaultValue",
//display the element only when the expected value is returned
(conditional: lookupValue) when lookupValue.status == "expectedValue"
}
You can combine or chain the expression as needed.