Search code examples
phparraysobjectsub-array

PHP - add object into subarray


I have incoming data that has order lines, orders may have more than one line. I need to parse this and turn it into a single object with a sub array of the lines.

So what I am doing is looping through the order lines, on the first occurrence of an "order ID" I create and object, then on the each loop through the data I check if I that "order ID" exists, if it does then I want to add the data to the sub array. Because I can't be sure that the order ID might not be repeated in another field (it's just an int) I have created a unique identifier to match.

             foreach ($orderList as $result) {
                // create the unique identifier
                $system_check = md5($result['order_id'] . $result['email']);

                // create a sting to search in, "in_array" not working
                $str = json_encode($parsedOrders);

                // Check if this is this order is already in the parsedOrder onject
                if (strpos($str, $system_check) !== false) {

                    // debug logging
                    $this->ICLogger("info", "parsed order line:", json_encode($parsedOrders[$result['order_id']]['lines']));

                    // trying to array_push the data into the "lines" section
                    $parsedOrders[$result['order_id']]['lines'][] = array(
                        'id' => $result['line_id'],
                        'product_id' => $result['product_id'],
                        'product_variant_id' => $result['product_variant_id'],
                        'quantity' => $result['quantity'],
                        'price' => $result['price']
                    );
                } else {

                    // Create the order "header" and "lines" data
                    $parsedOrders[$result['order_id']] = array
                    (
                        'id' => $result['order_id'],
                        'search_term' => $system_check,
                        'customer' => array(
                            'id' => $result['customer_id'],
                            'email_address' => $result['email'],
                            'opt_in_status' => ((int)$result['newsletter'] === 1)
                        ),
                        'fulfillment_status' => (!empty($order['fulfillment_status']) ? $order['fulfillment_status'] : ''),
                        'financial_status' => (!empty($order['financial_status']) ? $order['financial_status'] : ''),
                        'landing_site' => (!empty($order['landing_site']) ? $order['landing_site'] : ''),
                        'currency_code' => $result['currency_code'],
                        'order_total' => $result['order_total'],
                        'tax_total' => $result['tax_total'],
                        'storeid' => $result['storeid'], // temp storage of store ID
                        'lines' => array(array(
                            'id' => $result['line_id'],
                            'product_id' => $result['product_id'],
                            'product_variant_id' => $result['product_variant_id'],
                            'quantity' => (int)$result['quantity'],
                            'price' => $result['price']
                        ))
                    );
                }

When I do this, the data is just added to the end of the array, not inside the object that I am trying to add to:

JSON encoded output:

    [
      {
        "id":"20007",
        "search_term":"2d8a9bbbbc85d4503b8581bb09d81301",
        "customer":{
        "id":"11",
        "email_address":"test103@test.com",
        "opt_in_status":false
      },
        "fulfillment_status":"",
        "financial_status":"",
        "landing_site":"",
        "currency_code":"GBP",
        "order_total":"4",
        "tax_total":"1.3199999999999998",
        "storeid":"1",
        "lines":[
          {
            "id":"13",
            "product_id":"123",
            "product_variant_id":"750",
            "quantity":1,
            "price":"1"
          }
        ]
      },
      {
        "lines":[
          {
            "id":"14",
            "product_id":"123",
            "product_variant_id":"752",
            "quantity":"1",
            "price":"1"
          }
        ]
      }
    ]

How do I get the "lines" to append to the "lines" array and not just to the end of the object?

Many thanks...


Solution

  • you are almost there you have just gotten confused about your brackets i would suggest simplifying it to something more like

    $parsedOrders = [];
    foreach ($orderList as $result) {
    
        if(isset($parsedOrders[$result['order_id']]))
        {
            //grab the existing order
            $order = $parsedOrders[$result['order_id']];
        }
        else
        {
            //if order doesn't exist create
            $order = [
                'id' => $result['order_id'],
                'search_term' => $system_check,
                'customer' => [
                    'id' => $result['customer_id'],
                    'email_address' => $result['email'],
                    'opt_in_status' => ((int)$result['newsletter'] === 1)
                ],
                'fulfillment_status' => (!empty($order['fulfillment_status']) ? $order['fulfillment_status'] : ''),
                'financial_status' => (!empty($order['financial_status']) ? $order['financial_status'] : ''),
                'landing_site' => (!empty($order['landing_site']) ? $order['landing_site'] : ''),
                'currency_code' => $result['currency_code'],
                'order_total' => $result['order_total'],
                'tax_total' => $result['tax_total'],
                'storeid' => $result['storeid'], // temp storage of store ID
                'lines' => []
            ];
    
        }
    
        $order['lines'][$result['line_id']] = [
            'id' => $result['line_id'],
            'product_id' => $result['product_id'],
            'product_variant_id' => $result['product_variant_id'],
            'quantity' => (int)$result['quantity'],
            'price' => $result['price']
        ]
    
         $parsedOrders[$result['order_id']] = $order;
    }