JOLT spec to remove an array element based on string match - json

I have below json as input and I want to write jolt spec to remove element which has "TemplateProcessGroupName": "BBBB" and other elements should be present.
[
{
"TemplateProcessGroupName": "AAAAA",
"Name": "Keytab Credential Service"
},
{
"TemplateProcessGroupName": "BBBB",
"Name": "Keytab Credential Service"
},
{
"TemplateProcessGroupName": "CCCCC",
"Name": "Keytab Credential Service"
}
]
Any help would be appreciated. Thanks in advance
Thanks
Mahendra

If only needed to remove the attribute "TemplateProcessGroupName" whenever its value is "BBBB", then use the following shift transformation spec :
[
{
"operation": "shift",
"spec": {
"*": {
"TemplateProcessGroupName": {
"BBBB": {
"*": "" //display nothing whenever the attribute matches "BBBB"
},
"*": {
"#1": "[&3].&2" // "[&3]" stands for going the tree three levels up and grab the outermost indexes and yielding result of an array
}
},
"*": "[&1].&"
}
}
}
]
If the whole object which contains that attribute should be removed then use shift transformation specs along with a remove transformation spec such as :
[
{
// change the object labels
"operation": "shift",
"spec": {
"*": {
"#": "#(1,TemplateProcessGroupName)"
}
}
},
{
// remove the object with label "BBBB"
"operation": "remove",
"spec": {
"BBBB": ""
}
},
{
// get rid of object labels
"operation": "shift",
"spec": {
"*": ""
}
}
]

Related

JOLT Specification for converting filed value to field name

I am trying to convert the below JSON payload into a JSON that has the field name as the value of the field:
The jolt file that I have is working if field values are different. But if field values are the same then it is giving an array in the response.
Can you please help to provide jolt specifications for this?
Input JSON Payload:
{
"action": {
"Success": true,
"records": [
{
"Id": "Test_abc",
"SubscriptionID": "ID_1"
},
{
"Id": "Test_abc",
"SubscriptionID": "ID_2"
},
{
"Id": "Test_xyz",
"SubscriptionID": "ID_3"
}
],
"type": "update"
}
}
Expected output:
{
"action": {
"Success": true,
"records": {
"Test_abc": {
"SubscriptionID": "ID_1"
},
"Test_abc": {
"SubscriptionID": "ID_2"
},
"Test_xyz": {
"SubscriptionID": "ID_3"
}
},
"type": "update"
}
}
Solution not found yet.
You can use the following shift transformation spec
[
{
"operation": "shift",
"spec": {
"*": {
"*": "&1.&", // &1 replicates the literal "action"
"records": {
"*": {
"S*": "&3.&2.#(1,Id).&" // &3 replicates the literal "action" (by going three level up the tree), &2 for "records", & replicates the current level attribute
}
}
}
}
}
]
presumingly converting one of the Id value from Test_abc to another one such as Test_def, since the desired output is wrong as a JSON value(There cannot be more than one object with the same tag at the same level)
Your output is wrong. You can't have multiple objects with the same keys.
If You want to support all objects of records array, You should bring them into an array like this spec:
[
{
"operation": "shift",
"spec": {
"*": {
"*": "&1.&",
"records": {
"*": {
"S*ID": "&3.&2[].#(1,Id).&"
}
}
}
}
}
]
But, if you want to have an object as your records in the output, You should remove the duplicate ID like this spec:
[
{
"operation": "shift",
"spec": {
"*": {
"*": "&1.&",
"records": {
"*": {
"S*ID": "&3.&2.#(1,Id).&"
}
}
}
}
},
{
"operation": "cardinality",
"spec": {
"*": {
"records": {
"*": {
"*": "ONE"
}
}
}
}
}
]

get jolt json key,i hope transform key ,I have the following dataset that I need to transform:

I don't know how to use jolt's transformations such as shift、default、modify-default-beta.
I have the following JSON value as
input :
{
"report": {
"q": "1",
"b": "2"
}
}
that I need to transform to
the desired output :
{
"report": {
"q": "1",
"b": "2"
},
"q": "1"
}
how can i handle it ?
Edit : I was actually trying to find a way to replicate,now i found :
[
{
"operation": "modify-default-beta",
"spec": {
"q": "#(2,report.&)"
}
}
]
You can use a shift transformation spec like this
[
{
"operation": "shift",
"spec": {
"*": "&",
"#(0,report.q)": "q"
}
},
{
// this spec stands only for sorting to obtain the exact appearance with the desired result
"operation": "shift",
"spec": {
"report": "&",
"q": "&"
}
}
]
where zero in #(0,report.q) represents the value taken from the current level
the demo on the site http://jolt-demo.appspot.com/ is
or another method would be by using shift transformation again :
[
{
"operation": "shift",
"spec": {
"*": {
"#": "&", // replicate the whole content
"q": "&" // replicate only attribute "q" without a node
}
}
}
]

Jolt Transform filter values using another value of the json

I have this JSON:
{
"mapTrue": "true",
"code": [
"X",
"Y",
"Z"
],
"expired": [
"true",
"false",
"true"
]
}
I want to use the "mapTrue" value in order to filter the "code" array.
If "mapTrue": "true", I'll take the 0 and 2 values in "expired" array, therefore I need to output
"code": ["X", "Z"].
Using the same logic, for "mapTrue: "false" I'll return "code": ["Y"].
This specification returns the right "code" array but it doesn't use the "mapTrue" value.
[
{
"operation": "shift",
"spec": {
"expired": {
"*": {
"true": {
"#(3,code[&1])": "code"
}
}
}
}
}
]
That's where my problem is.
This works:
[
{
"operation": "shift",
"spec": {
"expired": "#(1,mapTrue)",
"code": "code"
}
},
{
"operation": "shift",
"spec": {
"*": {
"*": {
"&1": {
"#(3,code[&1])": "code[]"
}
}
}
}
}
]
An alternative option would be using the following specs
[
{
// separate the values for "true", "false" while match "code" with the value of "mapTrue"
"operation": "shift",
"spec": {
"c*": {
"*": "#(2,expired[&])", // walk through the indexes(0,1,2) of "expired" array while matching with the components of "code"
"#(1,mapTrue)": "&1"
}
}
},
{
"operation": "shift",
"spec": {
"c*": {
"*": {
"#(2,&)": "&2" // grab the value going tree up two levels by using "#(2,&)", and copy the main object's label "code" by grabbing it after going tree two levels again
}
}
}
}
]
the demo on the site http://jolt-demo.appspot.com/ is

JOLT transformation filter a list about the first string element

I would like to search a list for the first real string element (which could be not a number) and output this.
Input :
{
"firstString": [
"0.20",
"test",
"0.30"
]
}
or
{
"firstString": [
"0.20",
"0,30",
"test"
]
}
Expected Output :
{
"readingS": "test"
}
The order of the element can change, either it comes to 2nd or 3rd placeholder. The list is maximum 3 elements long.
My thought was to go over either the last or middle element, however this does not work. The list is generated just before with the modify-overwrite-beta.
You can still use modify-overwrite-beta transformation along with toInteger conversion such as
[
//Determine the elements whether toInteger conversion is applicable for them
{
"operation": "modify-overwrite-beta",
"spec": {
"arr": "=(#(1,firstString))",
"0": "=toInteger(#(1,arr[0]))",
"1": "=toInteger(#(1,arr[1]))",
"2": "=toInteger(#(1,arr[2]))"
}
},
//The arrays are generated from the elements which are eligible to
//conversion, while not for the others
{
"operation": "shift",
"spec": {
"*": "&",
"arr": { "*": "&" }
}
},
//The arrays are removed, so all numeric ones by reversing
//key-value pairs
{
"operation": "shift",
"spec": {
"*": {
"$": "#(0)"
}
}
},
//Reverse back the pairs
{
"operation": "shift",
"spec": {
"*": {
"$": "readingS[#2]"
}
}
},
//and pick the leftmost element
{
"operation": "cardinality",
"spec": {
"*": "ONE"
}
}
]
You have some values that ended with numbers. So we can match all values that ended with the number, and we have a real string in the last.
[
{
"operation": "shift",
"spec": {
"firstString": {
"*": {
"*0": "",
"*1": "",
"*2": "",
"*3": "",
"*4": "",
"*5": "",
"*6": "",
"*7": "",
"*8": "",
"*9": "",
"*": {
"$": "readingS"
}
}
}
}
}, {
"operation": "shift",
"spec": {
"*": {
"*": "&"
}
}
}
]

Json transformation from key value to nested array

I was trying to have a key value pair mapped to an array, distinguishing each value as a type using jolt transform spec
Input json
{
"testurl": "someurl",
"website": "someurl2"
}
tried this spec
[
{
"operation": "shift",
"spec": {
"testurl": "Urls[].testurl",
"website": "Urls[].website"
}
},
{
"operation": "shift",
"spec": {
"Urls": {
"*": {
"$": "Urls[&1].val"
}
}
}
}
]
Expected result is like this
{
"Urls": [{
"url": "someurl",
"val": "testurl"
}, {
"url": "someurl2",
"val": "website"
}]
}
Yes you can turn a set of Json key,value pair into an array.
It requires 2 shifts to be safe.
1st shift isolates all the properties you want to turn into an array.
2nd shift is able to use a "*" to then match all those items and place them an array.
Spec
[
{
"operation": "shift",
"spec": {
"testurl": "temp.testurl",
"website": "temp.website"
}
},
{
"operation": "shift",
"spec": {
"temp": {
"*": {
"$": "Urls[#2].val",
"#": "Urls[#2].url"
}
}
}
}
]