skip to Main Content

I’ve been writing a jolt for json transformation and I’m halfway through there. Need to modify json object in array if it is present in array and need to create new if it is not present at all. The object can appear at any position in json.

{

  "id": "id_1",
  "targetId": "targetId42",
  "externalId": "1extid",
  "textArray": [
    {
      "name": "attribute1",
      "value": "value1",
      "status": null
    },
    {
      "name": "attribute2",
      "value": "value2",
      "status": null
    },
    {
      "name": "attribute3",
      "value": "to be modified",
      "status": null
    }
  ]
  "createdDate": "2020-09-10",
  "description": "Value Pack",
  "id": "20020",
  "state": "Complete",
  "requestedCompletionDate": "2022-09-13"
}

Expected output

{
  "id": "id_1",
  "targetId": "targetId42",
  "externalId": "1extid",
  "textArray": [
    {
      "name": "attribute1",
      "value": "value1",
      "status": null
    },
    {
      "name": "attribute2",
      "value": "value2",
      "status": null
    },
    {
      "name": "attribute3",
      "value": "modified value",
      "status": null
    }
  ]
  "createdDate": "2020-09-10",
  "description": "Value Pack",
  "id": "20020",
  "state": "Complete",
  "requestedCompletionDate": "2022-09-13"
}

And if the block attribute3 is not present we create it with value that can be passed through custom attributes.
Note – the attribute3 object can appear at any position in textArray array.

Tried following different jolt but none desired output.

My current approach is to remove the "attribute3" block completely and then add new "attribute3" block with updated value.

[
  {
    "operation": "shift",
    "spec": {
      "textArray": {
        "*": {
          "@": "@(1,name)"
        }
      }
    }
  },
  {
    "operation": "remove",
    "spec": {
      "attribute3": ""
    }
  },
  {
    "operation": "modify-overwrite-beta",
    "spec": {
      "textArray": {
        "*": "=toList(@(1,&))"
      }
    }
  }
]

and after removing this perform another jolt transform which adds the ‘attribute3’ object with updated value.

[
  {
    "operation": "default",
    "spec": {
      "temp": {
        "name": "attribute3",
        "value": "${updatedValue}",
        "status": null
      }
    }
  },
  {
    "operation": "shift",
    "spec": {
      "*": "&",
      "textArray": "textArray",
      "temp": "textArray",
      "status": null
    }
  }
]

2

Answers


  1. You can use the following shift transformation spec

    [
      {
        "operation": "shift",
        "spec": {
          "*": "&", // all elements other than "textArray"
          "textArray": {
            "*": {
              "name": {
                "@": "&3[&2].&", // replicate the value of the upper node, eg. "name"
                "attribute3": { // conditional comparison starts here
                  "#modified value": "&4[&3].value"
                },
                "*": {
                  "@2,value": "&4[&3].value" // transfer value from 2 upper level
                }
              }
            }
          }
        }
      }
    ]
    

    the demo on the site https://jolt-demo.appspot.com/ is :

    enter image description here

    Login or Signup to reply.
  2. There’s probably a better way:

    [
      {
        "operation": "shift",
        "spec": {
          "*": "&", // all elements other than "textArray"
          "textArray": {
            "*": {
              "name": {
                "@": "&3[&2].&", // replicate the value of the upper node, eg. "name"
                "attribute3": { // conditional comparison starts here
                  "#modified value": "&4[&3].value",
                  "#true": "isPresentAttribute3"
                },
                "*": {
                  "@2,value": "&4[&3].value" // transfer value from 2 upper level
                }
              }
            }
          }
        }
      },
      { // if several attribute3
        "operation": "modify-overwrite-beta",
        "spec": {
          "isPresentAttribute3": "=firstElement(@(1,&))"
        }
      },
      { // initialize value if attribute3 is not present
        "operation": "modify-default-beta",
        "spec": {
          "isPresentAttribute3": "false"
        }
      },
      {
        "operation": "default",
        "spec": {
          "temp": {
            "name": "attribute3",
            "value": "${updatedValue}",
            "status": null
          }
        }
      },
      {
        "operation": "shift",
        "spec": {
          "isPresentAttribute3": {
            "false": {
              "@3": {
                  "*": "&",
                  "temp": "textArray[]"
              }
            },
            "*": {
              "@3": {
                  "*": "&"
              }
            }
          }
        }
      },
      {
        "operation": "remove",
        "spec": {
          "isPresentAttribute3": "",
          "temp": ""
        }
      }
    ]
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search