Compare and Combine Objects of same array - jolt

I want to iterate each object and map system.myStringValue with value.myStringValue
Can you provide spec for the same ?
I have provided the following input and output json. If any other things require form my side , let me know. I have tried with another spec but its not working for me as I want to combine email and phone in one object
Input :
[
{
"telecom": [
{
"system": {
"myStringValue": "email"
},
"value": {
"myStringValue": "mobqa#tester.com"
}
},
{
"system": {
"myStringValue": "phone"
},
"value": {
"myStringValue": "123"
}
}
]
},
{
"telecom": [
{
"system": {
"myStringValue": "email"
},
"value": {
"myStringValue": "john.doe#tester.com"
}
}
]
},
{
"telecom": [
{
"system": {
"myStringValue": "email"
},
"value": {
"myStringValue": "Gayle55#tester.com"
}
}
]
}
]
Output:
{
"users": [
{
"email":"mobqa#tester.com",
"phone":"123"
},
{
"email":"john.doe#tester.com"
},
{
"email":"Gayle55#tester.com"
}
]
}

[
{
"operation": "shift",
"spec": {
"*": {
"telecom": {
"*": {
"value": {
"myStringValue": {
// # takes value of 'value.myStringValue' and puts it into 'users[&5]' occurence
// #(3,system.myStringValue) go up four levels and then go to 'system.myStringValue'
// value and grab it and put as key value to appropriate occurence of 'users'
"#": "users[&5].#(3,system.myStringValue)"
}
}
}
}
}
}
}
]

Related

Facing issue with JOLT transformation with nested array

I have a JSON input :
{
"id": "Root_ID",
"Item": [
{
"id": "ID_1",
"characteristic": [
{
"name": "char1",
"value": "PRE1"
},
{
"name": "char2",
"value": "2050-01-01"
}
]
},
{
"id": "ID_2",
"characteristic": [
{
"name": "char1",
"value": "PRE2"
},
{
"name": "char2",
"value": "2050-01-02"
}
]
}
]
}
which needs to be converted by using a Jolt transformation spec to the following output :
{
"id": "Root_ID",
"Item": [
{
"id": "ID_1",
"char1": "PRE1",
"char2": "2050-01-01"
},
{
"id": "ID_2",
"char1": "PRE2",
"char2": "2050-01-02"
}
]
}
Currently, I'm using this spec :
[
{
"operation": "shift",
"spec": {
"id": "id",
"Item": {
"*": {
"characteristic": {
"*": {
"name": {
"char1": {
"#(2,value)": "item[#3].char1"
},
"char2": {
"#(2,value)": "item[#3].char2"
}
}
}
}
}
}
}
}
]
which does not produce the desired result.
Can you please help me prepare a correct spec to handle this issue ?
Edit : What if I'd like to get the following JSON result ?
{
"id": "Root_ID",
"Item": [
{
"id": "ID_1",
"char1": "PRE1"
},
{
"id": "ID_2",
"char1": "PRE2",
"char2": "2050-01-02"
}
]
}
You can use the following shift transformation spec in which #value and #name are matched reciprocally such as
[
{
"operation": "shift",
"spec": {
"id": "&",
"Item": {
"*": {
"id": "&2[&1].&",// you can reduce two levels based on the inner identifier 4,3 -> 2,1
"char*": {
"*": {
"#value": "&4[&3].#name" // &4 copies the literal "Item" after going four levels up the tree, [&3] generates array-wise result(array of objects) after going three levels up the tree to reach the level of the indexes of the "Item" array
}
}
}
}
}
}
]
Edit : You can alternatively use the following spec for the case in which you need to return char2 within the all objects but the first :
[
{
"operation": "shift",
"spec": {
"id": "&",
"Item": {
"0": {// stands for the first index
"id": "&2[&1].&",
"char*": {
"*": {
"name": {
"char1": {
"#2,value": "&6[&5].#3,name"
}
}
}
}
},
"*": {
"id": "&2[&1].&",
"char*": {
"*": {
"#value": "&4[&3].#name"
}
}
}
}
}
}
]

Having issue when adding a common value to every elements in array using Jolt

I am currently using Jolt to work on this input:
{
"banking_account": {
"accounts": [
{
"accountId": "account1"
},
{
"accountId": "account2",
"nickname": "nickname2"
}
]
},
"account_balance": {
"total_value": {
"currency_code": "USD",
"value": "100.00"
},
"balance_accounts": [
{
"id": "id1"
},
{
"id": "id2"
}
]
}
}
And the expected output is:
{
"Data": {
"Accounts": [
{
"AccountId": "account1",
"Account": {
"Identification": [
"id1",
"id2"
]
},
"Currency": "USD"
},
{
"AccountId": "account2",
"NickName": "nickname2",
"Account": {
"Identification": [
"id1",
"id2"
]
},
"Currency": "USD"
}
]
}
}
And here is my current spec:
[
{
"operation": "shift",
"spec": {
"banking_account": {
"accounts": {
"*": {
"accountId": "Data.Accounts.[&1].AccountId",
"nickname": "Data.Accounts.[&1].NickName"
}
}
},
"account_balance": {
"total_value": {
"currency_code": "Data.Accounts.[&1].Currency"
},
"balance_accounts": {
"*": {
"id": "Data.Accounts.[&1].Account.Identification"
}
}
}
}
}
]
And here is my current output:
{
"Data": {
"Accounts": [
{
"AccountId": "account1",
"Account": {
"Identification": "id1"
}
},
{
"AccountId": "account2",
"NickName": "nickname2",
"Account": {
"Identification": "id2"
}
}
]
}
}
So I am having two questions:
Why is the "Currency" value missing? Even if I added something like
"account_balance": {
"total_value": {
"currency_code": "Data.Accounts.[&1].Currency"
}
}
How to map both two balances accounts to both two accounts? Now it seems like an 1->1 mapping; and I wish to have a 2*2 mapping.
Thanks a lot for your help in advance!
You can use this spec for your solution but point 2 is not covered in this and I have added reason for 2nd:
[
{
"operation": "shift",
"spec": {
"banking_account": {
"accounts": {
"*": {
"accountId": "Data.Accounts.[&1].AccountId",
"nickname": "Data.Accounts.[&1].NickName"
}
}
},
"account_balance": {
"total_value": {
"currency_code": "Data.Currency"
},
"balance_accounts": {
"*": {
"id": "Data.Identification"
}
}
}
}
}, {
"operation": "shift",
"spec": {
"Data": {
"Accounts": {
"*": {
"*": "Data.Accounts.[&1].&",
"#(2,Currency)": {
"USD": {
"#USD": "Data.Accounts.[&2].Currency"
}
}
}
},
"Identification": "Data.Identification"
}
}
}
]
& This will answer your two questions :
1 : Why is the "Currency" value missing? Even if I added something like
So you are basically populating a single field element as multiple fields in an array with [&1] which is not possible that's why its not populating.
To do such a case you need to create new elements that will be populating in the Accounts array if you see my spec I am adding a new Current field in every object of Accounts array ->
"Accounts": {
"*": {
"*": "Data.Accounts.[&1].&",
"#(2,Currency)": { //Going 2 levels up to get to currency
"USD": { //If else to check Currency is USD
"#USD": "Data.Accounts.[&2].Currency" //Adding the field in each object of Accounts array.
}
}
}
How to map both two balances accounts to both two accounts? Now it seems like an 1->1 mapping; and I wish to have a 2*2 mapping.
--> This can be achieved in the similar way I have done for 1 but this will again require alot of hardcoding in JOlt.
So my suggestion is to keep both Currency and Identification outside Accounts Array in Data as single object.

JOLT - filtering array based on object value

how can I do this?
This is the array....
Can you please help me?
Can you please give me the answer???? Thanks a lot
{
"results": {
"data": [
{
"name": "xx",
"typeRelationship": [
{
"relationship": "parent",
"type": {
"id": "yyyyy",
}
}
],
"id": "xxxxxxxx"
},
{
"name": "yy",
"typeRelationship": [
{
"relationshipType": "parent",
"type": {
"id": "CCCC"
}
},
{
"relationshipType": "child",
"service": {
"id": "DDDD"
}
},
{
"relationshipType": "child",
"service": {
"id": "xxxxxxxx"
}
}
],
"id": "yyyyy"
}
]
}}
expected:
This is expected:
{
"data" : [ {
"id" : "xxxx",
"href" : "xxxxxx",
"relation":"parent"
} ]
}
For some reason I need to type so it does let me update!!!
This works.
[
{
"operation": "shift",
"spec": {
"data": {
"*": {
"type": {
"id": {
"xxxx": {
"#3": "data[]"
}
}
}
}
}
}
}
]
Edit 1
The below spec moves all the values which as id=xxxxx to the data array.
[
{
"operation": "shift",
"spec": {
"data": {
"*": {
"type": {
"*": {
"id": {
"xxxx": {
"#(2)": "data[]",
"#(4,relation)": "data[&3].relation"
}
}
}
}
}
}
}
}
]
This totally works.
Thanks.
Can you please let me know what is 2? 3? 4?
Because my array is a bit different and I want to fix those numbers but does not work....
{
"results": {
"data": [
{
"name": "xx",
"typeRelationship": [
{
"relationship": "parent",
"type": {
"id": "yyyyy",
}
}
],
"id": "xxxxxxxx"
},
{
"name": "yy",
"typeRelationship": [
{
"relationshipType": "parent",
"type": {
"id": "CCCC"
}
},
{
"relationshipType": "child",
"service": {
"id": "DDDD"
}
},
{
"relationshipType": "child",
"service": {
"id": "xxxxxxxx"
}
}
],
"id": "yyyyy"
}
]
}
}
expected:
{
"rows" : [ {
"rowdata" : {
"relationshipType" : "child",
"Name" : "yy",
"id" : "yyyyy"
}
} ]
}

Set null if value is not exists, otherwise return existing value if exists in jolt

As shown in sample input, I have array of extension in each object. When extension doesn't consists subscription-type then output should be null as shown in output or else should consist existing value. Same should be applicable for language-type. Order of subscription-type and language-type is random in nature.
I have tried with spec but its not working
{
"operation": "modify-define-beta",
"spec": {
"*": {
"subscriptionType": {
"url": {
"myCoercedValue": "subscription-type",
"myStringValue": "subscription-type"
},
"value": {
"myCoercedValue": null,
"myStringValue": null
}
},
"languageType": {
"url": {
"myCoercedValue": "language-type",
"myStringValue": "language-type"
},
"value": {
"myCoercedValue": null,
"myStringValue": null
}
}
}
}
},
{
"operation": "shift",
"spec": {
"*": {
"extension": "[&1].extension",
"subscriptionType": "[&1].extension[]",
"languageType": "[&1].extension[]"
}
}
},
{
"operation": "shift",
"spec": {
"*": {
"extension": {
"*": {
"#url": {
"myStringValue": {
"subscription-type": {
"#(3,value.myStringValue)": "[&3].subscriptionType[]"
}
}
}
}
}
}
}
},
{
"operation": "shift",
"spec": {
"0": "[]"
}
}
]
Input:
[
{
"extension": []
},
{
"extension": [
{
"url": {
"myCoercedValue": "subscription-type",
"myStringValue": "subscription-type"
},
"value": {
"myCoercedValue": "free",
"myStringValue": "free"
},
"extension": []
}
]
},
{
"extension": [
{
"url": {
"myCoercedValue": "language-type",
"myStringValue": "language-type"
},
"value": {
"myCoercedValue": "en-us",
"myStringValue": "en-us"
}
},
{
"url": {
"myCoercedValue": "subscription-type",
"myStringValue": "subscription-type"
},
"value": {
"myCoercedValue": "free",
"myStringValue": "free"
}
}
]
}
]
Output:
[ {
"subscriptionType" : [ null, "free", "free" ],
"language":[null,null,"en-US"]
} ]
Perhaps you want to get such a result? Please, try those spec and say what you want to modify.
[
{
"operation": "shift",
"spec": {
"*": {
"extension": {
"*": {
"url": {
"myCoercedValue": {
"subscription-type": {
"#(3,value)": {
"myCoercedValue": "subscriptionType[#8]"
}
},
"language-type": {
"#(3,value)": {
"myCoercedValue": "language[#8]"
}
}
}
}
}
}
}
}
}
]

Implicit array creating in jolt

Input:
{
"categories": {
"1": {
"name": "Books"
},
"2": {
"name": "Games"
}
}
}
Spec:
[
{
"operation": "shift",
"spec": {
"categories": {
"*": {
"#": "categories"
}
}
}
}
]
Output (array of categories):
{
"categories" : [ {
"name" : "Books"
}, {
"name" : "Games"
} ]
}
Another Input with just one element
{
"categories": {
"1": {
"name": "Books"
}
}
}
Output:
{
"categories" : {
"name" : "Books"
}
}
I expected the output to be a categories array containing just one element. Why does this spec not create an array when there is a single element?
I managed this problem with following transformation:
[
{
"operation": "shift",
"spec": {
"*": {
"*": "categories[#1]"
}
}
}
]