Dropping data in foreach loop - php

Using this array:
$arr=array(
array('project','ProjectId','62c1553d'),
array('project','ProjectName','TEST JSON'),
array('Vendors','PrimeSpec','Fabspec'),
array('Vendors','VendorId','dd759c7f'),
array('Vendors','PrimeSpec','Vendor2'),
array('Vendors','VendorId','Vendor2ID'),
);
The desired result is:
INSERT INTO project (ProjectId,ProjectName) VALUES (62c1553d,'TEST JSON');
INSERT INTO Vendors (PrimeSpec,VendorId) VALUES ('Fabspec',dd759c7f);
INSERT INTO Vendors (PrimeSpec,VendorId) VALUES ('Vendor2',Vendor2ID);
But I'm losing PrimeSpec, Fabspec in the foreach loop - the output I'm getting is:
INSERT INTO project (ProjectId,ProjectName) VALUES (62c1553d,TEST JSON);
INSERT INTO Vendors (VendorId) VALUES (dd759c7f);
Here is my code:
function array2sql($arr){
$sql = '';
$fields = '';
$values = '';
$extable = $arr[0][0];
foreach( $arr as $line ) {
if ($extable == $line[0]) {
$fields .= $line[1].',';
$values .= $line[2].',';
} else {
$sql .= 'INSERT INTO ' . $extable . ' (' . rtrim($fields, ',') . ') VALUES (' . rtrim($values, ',') . ');';
$fields = '';
$values = '';
$extable = $line[0];
}
}
$sql .= 'INSERT INTO ' . $extable . ' (' . rtrim($fields, ',') . ') VALUES (' . rtrim($values, ',') . ');';
echo $sql;
return $arr;
}
array2sql($arr);
I don't understand why it's dropping the first set of data. Thanks for looking at this.

Consider the following simplified version of your array2sql function(using array_walk and array_column functions):
function array2sql($arr) {
$query_data = [];
$sql = "";
array_walk($arr, function($v) use(&$query_data) {
$query_data[$v[0]][$v[1]][] = $v[2];
});
foreach ($query_data as $table => $data) {
$keys = array_keys($data);
$key_string = implode(",", $keys);
$count = count($data[$keys[0]]); // number of values for a certain column
while ($count--) {
$value_string = "'". implode("','", array_column($data, $count)). "'";
$sql .= "INSERT INTO $table($key_string) VALUES($value_string);". PHP_EOL;
}
}
return $sql;
}
print_r(array2sql($arr));
The output:
INSERT INTO project(ProjectId,ProjectName) VALUES('62c1553d','TEST JSON');
INSERT INTO Vendors(PrimeSpec,VendorId) VALUES('Vendor2','Vendor2ID');
INSERT INTO Vendors(PrimeSpec,VendorId) VALUES('Fabspec','dd759c7f');

Seems to be resolved by changing the else statement to
$fields = $line[1].',';
$values = $line[2].',';

Try This
function array2sql($arr){
$sql = '';
$newArr = array();
foreach( $arr as $line ) {
$newArr[$line[0]][$line[1]] = $line[2];
}
foreach($newArr as $tblNam=>$value) {
$sql .= "INSERT INTO ".$tblNam." (`" . implode('`,`', array_keys($value)) . "`) VALUES ('" . implode("','", array_values($value)) . "') ";
}
echo $sql;
}

Because your tables are only receiving two columns of data each, array_chunk() can help to merge and prepare and compose the queries.
$arr=array(
array('project','ProjectId','62c1553d'),
array('project','ProjectName','TEST JSON'),
array('Vendors','PrimeSpec','Fabspec'),
array('Vendors','VendorId','dd759c7f'),
array('Vendors','PrimeSpec','Vendor2'),
array('Vendors','VendorId','Vendor2ID'),
);
// merge and prepare
foreach(array_chunk($arr,2) as $pair){
if(!isset($queries[$pair[0][0]]['columns'])){
$merge[$pair[0][0]]['columns']='`'.implode('`,`',array_column($pair,1)).'`';
}
$merge[$pair[0][0]]['values'][]="'".implode("','",array_column($pair,2))."'";
}
// compose queries
foreach($merge as $table=>$a){
$queries[$table]="INSERT INTO $table ({$a['columns']}) VALUES (".implode('),(',$a['values']).")";
}
print_r($queries);
/*
Array(
[project] => INSERT INTO project (`ProjectId`,`ProjectName`) VALUES ('62c1553d','TEST JSON')
[Vendors] => INSERT INTO Vendors (`PrimeSpec`,`VendorId`) VALUES ('Fabspec','dd759c7f'),('Vendor2','Vendor2ID')
)
*/
$mysqli->multi_query(implode(';',$queries));
while ($mysqli->next_result()) {;} // flush multi_queries
This method performs no escaping or security measures. If you want to use prepared statements and placeholders, a few modifications will be necessary.
For more details on how to write a full mysqli_multi_query() INSERT block, see this link: Strict Standards: mysqli_next_result() error with mysqli_multi_query

Related

WordPress Insert MySQL conversion

I've been working on a simple website heatmap using jQuery & PHP. I've managed to make it work but I would now like to use it in WordPress and I was woundering how to covert the Insert MYSQL function to work with WordPress. See example below:
global $wpdb;
//$clicks = $_POST["clicks"];
$clicks = '.testimonial;1119;316;1663;608;#header;723;66;1663;608';
$keys = array('identifier_name', 'pos_x', 'pos_y','window_width','window_height');
$arr = explode(';', $clicks);
$data = array_chunk($arr, 5);
//Create an array of values for the insert statement
$values = array();
foreach ($data as $rec) {
$values[] = "(1, '" . join("', '", $rec) . "', 'ok')";
}
//Create a single insert statement with all the values
//I am trying to convert this Insert Function
$sql = "INSERT INTO data (user_id, " . join(', ', $keys) . ", status)";
$sql .= "VALUES " . implode(", ", $values);
echo $sql . '<br>';
I am struggeling with the array bit here:
$wpdb->insert(
$table,
array(
/* This is where I struggle */
)
);
Any help much appreceated.
foreach ($data as $rec) {
$wpdb->insert(
$table,
array(
'identifier_name'=> $rec[0],
'pos_x'=>$rec[1],
'pos_y'=>$rec[2],
'window_width'=>$rec[3],
'window_height'=>$rec[4])
);
}
or
$wpdb->query($sql);

Array to string conversion in Error

$keyNames = array();
$keyVals = array();
foreach ($varArray as $key => $name) {
$keyNames .= $key . ', ';
}
foreach ($varArray as $key => $val) {
$keyVals .= '\'' . $val. '\', ';
}
// build query
$sql = "INSERT INTO Organizations (";
$sql .= rtrim($keyNames, ", ");
$sql .= ") VALUES (";
$sql .= rtrim($keyVals, ", ");
$sql .= ");";
echo "<div style=\"padding:5px;background-color:#efefef\">".$sql."</div>"; // this output is working
I am trying to get the above code to work without error. IT currently works but I am getting " Array to string conversion in" error even though I am getting the result that I am expecting.
I am trying to build an sql query from array elements. Both loops throw an error but the echo SQL is giving me what I want. I just want to get rid of the error. I have tried (string) and (array) and implode() and join() but I have not been able to clear the error.
Can you point me in the right direction?
Your procedure seems quite useles because there is implode function for merging array's elements:
$keyNames = implode(',', array_keys($varArray));
$keyValues = '"' . implode('","', $varArray) . '"';
And SQL:
$sql = 'INSERT INTO Organizations (' . $keyNames . ') VALUES (' . $keyValues . ')';
The error is because you're initializing the variables as arrays, and then concatenating strings to them. What you want is:
$keyNames = implode(', ', array_keys($varArray));
$keyVals = implode(', ', array_map(function($val) {
return "'$val'";
}, array_values($varArray)));
The error comes from trying to concatenate a string onto an array. Because you are using $keyNames and $keyValues strictly as strings, there is no need to initialize them as arrays - simply use strings and the error will go away.
Change
$keyNames = array();
$keyVals = array();
to
$keyNames = $keyVals = '';

Build query to INSERT multiple rows

I want to INSERT more than one rows into MYSQL.
I am trying to build my query in this way, In the end I have to remove the COMMA in the end of query.
WHat is the better approach to achieve this(or in less lines of code)
$file_user_group_map_query = "INSERT INTO file_user_groups_map ";
foreach ($user_groups_selected as $file_user_group_map) {
$file_user_group_map_query .= "VALUES('',$file_id, " . $file_user_group_map . " ), ";
}
Try this:
$file_user_group_map_query = "INSERT INTO file_user_groups_map VALUES";
foreach ($user_groups_selected as $file_user_group_map) {
$insert[] = "('',$file_id, " . $file_user_group_map . " )";
}
$file_user_group_map_query .= implode(",",$insert);
$maps = array_map(function($m) use ($file_id) {
return $file_id.",".$m;
}, $file_user_group_map);
$file_user_group_map_query =
'INSERT INTO file_user_groups_map VALUES('.
implode ( "),('', $maps ).
')';
Alternatively:
$maps = array_map(function($m) use ($file_id) {
return "($file_id,$m)";
}, $file_user_group_map);
$file_user_group_map_query =
'INSERT INTO file_user_groups_map VALUES '.
implode ( ",'', $maps );
Documentation:
http://www.php.net/manual/en/function.implode.php
http://www.php.net/manual/en/function.array-map.php

PHP String from For Loop in MYSQL Insert Query not Working

I have a script as below.
There are some values from $_POST to be inserted to database.
But it is not working.
Need your help.
<?
$field = array(Priority_Rank, Attending_Period, Priority_Point_Low, Priority_Point_High, Other_Consideration);
$fields = implode(',', $field);
$fieldpost = array();
for ($i=0; $i<count($field); $i++) {
$fieldpost[] = $_POST[$i]; }
$fieldposts = implode (',', $fieldpost);
$query1 = "INSERT INTO $maindb ($mainID, $fields) VALUES ('$seq',$fieldposts)";
mysql_query($query1); ?>
I found out that the problem is in VALUES(...,$fieldposts), because if I change the query become the below, it is working perfectly.
$query1 = "INSERT INTO $maindb ($mainID, $fields) VALUES ('$seq','$_POST[0]','$_POST[1]','$_POST[2]','$_POST[3]','$_POST[4]')";
But since this query will also be used by other script that have different quantity of $_POST, I really need them to be looped in this file.
Note: $field is located in the other file.
You need to do:
for ($i=0; $i<count($field); $i++) {
$fieldpost[] = "'" . mysql_real_escape_string($_POST[$i]) . "'";
}
so that the values will be enclosed in quotes and also be escaped properly.
Let's assume you have an array containing the lines to insert :
<?php
$lines = array(
array("Value 1A", "Value 2A", "Value 3A", "..."),
array("Value 1B", "Value 2B", "Value 3B", "..."),
array("Value 1C", "Value 2C", "Value 3C", "...")
// ...
);
First of all, you need to escape your values before insterting them in a query, especially if they come from the user ($_POST, etc.). mysql_real_escape_string() does that for you.
<?php
foreach ($lines as &$line) {
foreach ($line as &$value) {
$value = '\'' . mysql_real_escape_string($value) . '\'';
}
}
Then your build your individual value sets :
<?php
$sets = array();
foreach ($lines as $line) {
$sets[] = '(' . implode(', ', $line) . ')';
}
And only then you build your query
<?php
$query = 'INSERT INTO yourtable (field1, field2, field3) VALUES '
$query .= implode(', ', $sets)
mysql_query($query)
You can of course combine the two first loops, I only separated for the sake of explanation :
<?php
$sets = array();
foreach ($lines as $line) {
foreach ($line as &$value) {
$value = '\'' . mysql_real_escape_string($value) . '\'';
}
$sets[] = '(' . implode(', ', $line) . ')';
}
$query = 'INSERT INTO yourtable (field1, field2, field3) VALUES '
$query .= implode(', ', $sets)
mysql_query($query)
Try something like the following to ensure the field name posted is valid and the values correctly escaped.
$fields = array('column_a', 'column_b', 'column_c');
foreach($_POST as $name => $value) {
if (isset($fields[$name])) {
$columns[] = $fields[$name];
$values[] = "'" . mysql_real_escape_string($value) ."'";
}
}
if (! empty($columns)) {
$sql = sprintf('INSERT INTO %s (%s) (%S)', $tableName, implode(',', $columns), implode(',', $values));
}
Really you should be using parameter placeholders (?) for the values and prepare the statement with PDO or equivalent.

insert multiple data

how i do wrong i want insert to db data from array:
$tabb = array(
'name' => 'test',
'login' => 'testt');
but i cant use SET, because end of query is char , .
public function insert($table, $values){
if($this->database){
print_r($values);
$we = 'INSERT INTO '. $table .' SET ';
foreach($values as $value => $key) {
$we .= ' ('. $value .' = "'. $key .'") ';
}
print $we;
mysql_query($we);
}
return true;
}
i do print $we:
INSERT INTO user SET (name = "test") (login = "testt")
not work, please help
php
I really recommend avoiding SET. It is far less common and given the choice between something which is uncommon and something which is common, always go with the common -- it means broader, faster, and better support by your community.
Here's how you'd approach that problem without it:
If you only have two columns in your USER table, you can simply use VALUES followed by a comma delineated list of data sets:
INSERT INTO user VALUES ("test","testt"),("test2","testt2")
Your function doesn't look like it is geared towards this, but it is a good thing to know either way.
But it looks like you are inserting by column name (a good idea in general):
INSERT INTO user (name, login) VALUES ("test","testt")
With PHP this becomes:
$items = array_map('mysql_real_escape_string', $values);
$items = '(\'' . implode( '\',\'', $items ) . '\')';
$q = 'INSERT INTO '.
$table .
// using implode with array_keys assumes that you know all of the keys
// ahead of time. If you don't, I MUST suggest your re-think your code
// omit the following line if you want to follow the first SQL example
' (' . implode( ',', array_keys( $values ) . ') '.
' VALUES ' .
$items;
public function insert($table, $values){
$fields = array();
$data = array();
foreach ($values as $key => $val) {
$fields[] = mysql_real_escape_string($key);
$data[] = mysql_real_escape_string($val);
}
$fields = implode(',', $fields);
$data = implode(',', $data)
$sql = "INSERT INTO $table ($fields) VALUES ($data);"
mysql_query($sql) or die(mysql_error());
}
public function insert($table, $values)
{
if($this->database)
{
print_r($values);
$we = 'INSERT INTO '. $table .' SET ';
$sep = '';
foreach($values as $value => $key)
{
$we .= $sep . ' ('. $value .' = "'. mysql_real_escape_string($key) .'") ';
$sep = ',';
}
print $we;
mysql_query($we);
}
return true;
}
Or, if you want to be tricky:
public function insert($table, $values)
{
if($this->database)
{
print_r($values);
$we = "insert into `".$table. "` (`". implode('`,`',array_keys($fields))."`) values ('".implode("','",array_map('mysql_real_escape_string', $fields))."');";
print $we;
mysql_query($we);
}
return true;
}
You need to seperate (name = "test") (login = "testt") with ", " between them (name = "test"), (login = "testt")
Another way is to do it is:
INSERT INTO user (name, login) VALUES ("test", "testt")

Categories