Search code examples
arraysjsonapache-nifitransformationjolt

JOLT transformation split object in array to two objects


I have array of objects and I want to split each object from this array into two objects my input looks like this:

[
  {
    "amount": 30,
    "currency": "USD",
    "status": "Approved",
    "timestamp": "1660117356314",
    "user_id": 123,
    "balance_after": 30.03,
    "transaction_id": 123
  },
  {
    "amount": 10,
    "currency": "USD",
    "status": "Approved",
    "timestamp": "1660117356314",
    "user_id": 124,
    "balance_after": 70.03,
    "transaction_id": 124
  }
]

I am trying Jolt Spec like this:

[
  {
    "operation": "shift",
    "spec": {
      "*": "[0].&",
      "@(1,timestamp)": "[1].timestamp",
      "@(1,user_id)": "[1].user_id",
      "@(1,balance_after)": "[1].balances.[0].balance",
      "@(1,currency)": "[1].balances.[0].currency",
      "#real_money": "[1].balances.[0].key",
      "#0": "[2].balances.[1].balance",
      "@(1,currency)": "[2].balances.[1].currency",
      "#bonus_money": "[2].balances.[1].key"
    }
  }
]

My expected result is

[
  {
    "amount": 30,
    "currency": "USD",
    "status": "Approved",
    "timestamp": "1660117356314",
    "user_id": 123,
    "balance_after": 30.03,
    "transaction_id": 123
  },
  {
    "timestamp": "1660117356314",
    "user_id": 123,
    "balances": [
      {
        "balance": 30.03,
        "currency": "USD",
        "key": "real_money"
      },
      {
        "balance": 0,
        "currency": "USD",
        "key": "bonus_money"
      }
    ]
  },
  {
    "amount": 10,
    "currency": "USD",
    "status": "Approved",
    "timestamp": "1660117356314",
    "user_id": 124,
    "balance_after": 70.03,
    "transaction_id": 124
  },
  {
    "timestamp": "1660117356314",
    "user_id": 124,
    "balances": [
      {
        "balance": 70.03,
        "currency": "USD",
        "key": "real_money"
      },
      {
        "balance": 0,
        "currency": "USD",
        "key": "bonus_money"
      }
    ]
  }
]

but I am receiving quite different result, this specification works correctly for this input:

{
  "amount": 30,
  "currency": "USD",
  "status": "Approved",
  "timestamp": "1660117356314",
  "user_id": 123,
  "balance_after": 30.03,
  "transaction_id": 123
}

and I am receiving:

[
  {
    "amount": 30,
    "currency": "USD",
    "status": "Approved",
    "timestamp": "1660117356314",
    "user_id": 123,
    "balance_after": 30.03,
    "transaction_id": 123
  },
  {
    "timestamp": "1660117356314",
    "user_id": 123,
    "balances": [
      {
        "balance": 30.03,
        "key": "real_money"
      },
      {
        "currency": "USD",
        "balance": "0",
        "key": "bonus_money"
      }
    ]
  }
]

But currency does not appear for REAL_MONEY balance

Does anyone here have a solution how to achieve goal?


Solution

  • You can use this when your input is a array.

    [
      {
        "operation": "shift",
        "spec": {
          "*": {
            "*": "[#2].first.&",
            "timestamp": [
              "[#2].first.&",
              "[#2].second.timestamp"
            ],
            "user_id": [
              "[#2].first.&",
              "[#2].second..user_id"
            ],
            "balance_after": [
              "[#2].first.&",
              "[#2].second.balances[0].balance"
            ],
            "1,currency": [
              "[#2].first.&",
              "[#2].second.balances[0].currency"
            ],
            "#real_money": "[#2].second.balances[0].key",
            "#0": "[#2].second.balances[1].balance",
            "currency": [
              "[#2].first.&",
              "[#2].second.balances[1].currency"
            ],
            "#bonus_money": "[#2].second.balances[1].key"
          }
        }
      },
      {
        "operation": "sort"
      },
      {
        "operation": "shift",
        "spec": {
          "*": {
            "first|second": ""
          }
        }
      }
    ]
    

    https://jolt-demo.appspot.com/#inception enter image description here