Manipulate an PHP array to match the requirements of an array of function and call function recursively

I am trying to automate updating some records in our SugarCRM system from a CSV file that I receive every month.

Background / Introduction

I use the code below that is provided by Sugar for updating / creating records via REST.

<?php include_once('parsecsv.lib.php'); // Include the parsecsv-for-php library $csv = new parseCSV('myCSV.csv'); // Parse through the CSV and store results in $csv $url = "http://{site_url}/service/v4/rest.php"; $username = "admin"; $password = "password"; //function to make cURL request function call($method, $parameters, $url) { ob_start(); $curl_request = curl_init(); curl_setopt($curl_request, CURLOPT_URL, $url); curl_setopt($curl_request, CURLOPT_POST, 1); curl_setopt($curl_request, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_0); curl_setopt($curl_request, CURLOPT_HEADER, 1); curl_setopt($curl_request, CURLOPT_SSL_VERIFYPEER, 0); curl_setopt($curl_request, CURLOPT_RETURNTRANSFER, 1); curl_setopt($curl_request, CURLOPT_FOLLOWLOCATION, 0); $jsonEncodedData = json_encode($parameters); $post = array( "method" => $method, "input_type" => "JSON", "response_type" => "JSON", "rest_data" => $jsonEncodedData ); curl_setopt($curl_request, CURLOPT_POSTFIELDS, $post); $result = curl_exec($curl_request); curl_close($curl_request); $result = explode("\r\n\r\n", $result, 2); $response = json_decode($result[1]); ob_end_flush(); return $response; } //login ----------------------------------------------- $login_parameters = array( "user_auth"=>array( "user_name"=>$username, "password"=>md5($password), "version"=>"1" ), "application_name"=>"RestTest", "name_value_list"=>array(), ); $login_result = call("login", $login_parameters, $url); /* echo "<pre>"; print_r($login_result); echo "</pre>"; */ //get session id $session_id = $login_result->id; //create contacts --------------------------------------- $set_entries_parameters = array( //session id "session" => $session_id, //The name of the module from which to retrieve records. "module_name" => "Accounts", //Record attributes "name_value_list" => array( array( //to update a record, you will nee to pass in a record id as commented below array("name" => "id", "value" => "111111111"), array("name" => "jan_field_1", "value" => "Sample Value 1"), array("name" => "jan_field_2", "value" => "Sample Value 2"), // more fields could be added here ), array( //to update a record, you will nee to pass in a record id as commented below array("name" => "id", "value" => "222222222"), array("name" => "jan_field_1", "value" => "Sample Value 1"), array("name" => "jan_field_2", "value" => "Sample Value 2"), // more fields could be added here ), ), ); $set_entries_result = call("set_entries", $set_entries_parameters, $url); echo "<pre>"; print_r($set_entries_result); echo "</pre>"; ?> 

Everything works fine if I hardcode the values โ€‹โ€‹in the $ set_entries_parameters array, for example:

 //Record attributes "name_value_list" => array( array( //to update a record, you will need to pass in a record id as commented below array("name" => "id", "value" => "111111111"), array("name" => "jan_field_1", "value" => "Sample Value 1"), array("name" => "jan_field_2", "value" => "Sample Value 2"), ), array( //to update a record, you will need to pass in a record id as commented below array("name" => "id", "value" => "222222222"), array("name" => "jan_field_1", "value" => "Sample Value 1"), array("name" => "jan_field_2", "value" => "Sample Value 2"), ), ), ); 

Below is a print_r($set_entry_parameters['name_value_list']) printout print_r($set_entry_parameters['name_value_list']) , which is ultimately passed to function call($method, $parameters, $url) as $paramaters - everything works fine, and the records of each record are updated correctly.

 Array ( [0] => Array ( [0] => Array ( [name] => id [value] => 111111111 ) [1] => Array ( [name] => jan_field_1 [value] => Sample Value 1 ) [2] => Array ( [name] => jan_field_2 [value] => Sample Value 2 ) ) [1] => Array ( [0] => Array ( [name] => id [value] => 222222222 ) [1] => Array ( [name] => jan_field_1 [value] => Sample Value 1 ) [2] => Array ( [name] => jan_field_2 [value] => Sample Value 2 ) ) ) 

The CSV file I'm working with is presented in the following form, where id is the identifier of the entry in the CRM, and each additional column heading is what field will be updated along with what value should be set:

 id,field_1,field_2,field_3,field_4,field_5,field_6 111111111,21,10,8,0,1,1 222222222,32,8,7,0,0,1 333333333,17,11,7,0,0,4 

Over time, several new columns / headers will be added to the table for each new month.

I am currently using the parsecsv-for-php library from http://code.google.com/p/parsecsv-for-php/ to parse the CSV file. The library creates the following array in $csv->data' via $csv = new parseCSV('myCSV.csv'); :

 Array ( [0] => Array ( [id] => 111111111 [field_1] => 21 [field_2] => 10 [field_3] => 8 [field_4] => 0 [field_5] => 1 [field_6] => 1 ) [1] => Array ( [id] => 222222222 [field_1] => 32 [field_2] => 8 [field_3] => 7 [field_4] => 0 [field_5] => 0 [field_6] => 1 ) ) 

Question / Problem

Finally, the problem I'm struggling with.

I need to find a way to take an array created from parsecsv-for-php libary and do that $ set_entry_paramaters ['name_value_list'], which is ultimately passed to a function that updates all records.

In my example above, everything works fine if I rigidly bind each auxiliary array that needs to be updated with the record identifier and each field that needs to be updated.

But the $csv->data array will change every month with new new updates that need to be updated, as well as new fields that need to be updated.

I assume that I need to somehow recursively add everything that is in the $csv->data array to $set_entry_parameters['name_value_list'] , but the key / index $csv->data does not match what needs to be sent.

As you can (hopefully) see, each account that needs to be updated is its own array: the identifier of the updated record is a submatrix, and each field that needs to be updated is a submatrix as well, but my parsed CSV array is not close to this .

So, it seems to me that I have two problems that I need to solve:

  • The array containing the analyzed CSV must correspond to the structure of the array, which function call($method, $parameters, $url) accepts as $paramaters .
  • function call($method, $parameters, $url) needs to be called once for each record that needs to be updated.

I tried using the array_walk or call_user_func_array in PHP, but I'm not sure if this is correct or how I will do it.

I am still learning PHP, but I think it really is not in my understanding at the moment, but I hope that I can learn this. I hope that I have provided enough information, and I hope there is some kind soul who can help me. I will be happy to provide any additional information if this helps.

Thank you so much in advance!

+4
source share
1 answer

First of all, the props for writing such a beautifully presented first question!

You are right that the answer to your problem is to convert the $csv->data array to the desired format, but it does not have to be recursive, because you know its depth and thatโ€™s it. You probably just want to create your own array next to it, since basically you need to convert the $name => $value pairs from your $csv->data to your own arrays.

Here's an example of how you can do this, bring me here, as my php syntax skills are just as rusty as they can get, so take a grain of pseudocode with you if necessary:

 $params = array(); foreach ($csv->data as $i => $pairs) { $csvline = array(); foreach ($pairs as $name => $value) { $csvline[] = array('name' => $name, 'value' => $value) } $params[$i] = $csvline; // in your case you may also do $params[] =... } $set_entry_parameters['name_value_list'] = $params; 

voilรก, $params is in the expected format :)

Edit:

For your additional functionality from the comment below, an easy way to do this is to put the above code in a function that receives the $start parameter, so you can limit the number of lines to be analyzed, and where is the Start. For instance:

 function parse($start) { $params = array(); foreach ($csv->data as $i => $pairs) { if($i < $start) continue; // skip it if($i == $start+10000) break; // we reached our limit, stop here $csvline = ... ... } return $params; // has at most 10000 entries } 

and then you should use a loop like

 for($i = 0; $i < (total_lines); $i = $i + 10000) { $set_entry_parameters['name_value_list'] = parse($i); // call update } 

However, if in fact your initial parsing of the CSV file has been exhausted, it may be easier for you to simply manually (or programmatically) split the data into several files. Or increase the memory limit that you allow to use PHP!

+1
source

Source: https://habr.com/ru/post/1481843/


All Articles