I get Nearest 50 km location names from current location using google api, so it' works fine.
So I need to insert all these locations into my database. If some location already there in database, I need to update these location.
For example I get 10 locations in google api so 5 locations are already there in my database. I need to 5 location are update and remaining 5 locations are insert.
Here is my code:
<?php
require 'dbconnect.php';
$LocaName=$_REQUEST['locname'];
$address=$_REQUEST['address'];
$latt=$_REQUEST['Latt'];
$long=$_REQUEST['Long'];
if($latt && $long)
{
$LocaNamearray = explode("|||", $LocaName);
$addressarray = explode("|||", $address);
$lattarray=explode("|||",$latt);
$longarray=explode("|||",$long);
for($i=0;$i<count($lattarray);$i++)
{
$query1="select * from tbl_MapDetails where Latitude='".$lattarray[$i]."'and Longitude='".$longarray[$i]."'";
$result1=mysql_query($query1);
$now=mysql_num_rows($result1);
}
if($now >=1)
{
for($k=0;$k<count($lattarray);$k++)
{
$query="update tbl_MapDetails set LocationName='".$LocaNamearray[$k]."', Address='".$addressarray[$k]."',Latitude='".$lattarray[$k]."', Longitude='".$longarray[$k]."' where Latitude='".$lattarray[$k]."'and Longitude='".$longarray[$k]."'";
}
$nav="update";
}
else
{
$query ="INSERT INTO tbl_MapDetails(LocationName,Address,Latitude,Longitude) VALUES";
$strDelimiter = "";
for($j=0;$j<count($LocaNamearray);$j++)
{
$name =$LocaNamearray[$j];
$address =$addressarray[$j];
$lat = $lattarray[$j];
$long = $longarray[$j];
$query .= $strDelimiter."('$name', '$address','$lat','$long')";
$strDelimiter = ',';
}
$nav="Add";
}
$result= mysql_query($query);
if($result)
{
echo mysql_error();
$message=array("message"=>"sucessfully".$nav);
}
else
{
echo mysql_error();
$message=array("message"=>"fail".$nav);
}
}
else
{
$message=array("message"=>"require latt and long");
}
echo json_encode($message);
?>
Here insert and update working but I need to check every location in database. There is no location in database. It need to insert other location are update. how to check both these conditions matched locations are update and unmatched locations are inserted Please guide me.
Your logic is wrong in the code. What you are doing is looping through the provided data and for each set of data checking if a location with that lat/long exists and storing it in the $now variable. Once you've finished that loop, you're then checking $now and looping through the provided data again and either INSERTing or UPDATEing each set of data. So if the last set of data exists, your script will try and UPDATE each set of data. If it doesn't, your script will try to INSERT each set of data. Your code should be something like this (mixture of your code and pseudo-code):
for($i=0;$i<count($lattarray);$i++)
{
$query1="select * from tbl_MapDetails where Latitude='".$lattarray[$i]."'and Longitude='".$longarray[$i]."'";
$result1=mysql_query($query1);
$now=mysql_num_rows($result1);
if($now >=1)
{
// update table with location details
}
else
{
// insert location details into table
}
}
If this becomes a performance issue you could look at retrieving all the SELECT data first but if you're only dealing with 10 rows at a time you should be OK.
Note: depending on where your $_REQUEST data is coming from you might want to do some validation, i.e. to check you have matching sets of lat/long/name/address details.
Take a look at MySQL`s ON DUPLICATE KEY UPDATE. But you must be careful, because it is quite slow operation.
But, I think, it would be better if you just union all your SELECT requests in one using OR conditions.
Related
I'm having some trouble when it comes to updating checkboxes.
I have two different tables with arrays and i am trying to compare data from both tables as they contain similar info.
The ref no is used as the the unique identifier since the information is CSV uploaded therefore i cant use the primary key.
As for the query i ran it on php admin and it showed the results were fine and i am aware the code is vulnerable to SQL injection but if i can find a solution to get i could work on it.
Structure of both tables:
I run the following code
<?php
include 'DBConfig.php';
if(isset($_POST['Submit']))
{
reconcile();
}
function reconcile(){
include 'DBConfig.php';
if(isset($_POST['reconciled']) && (isset($_POST['reconciled2']))){
foreach ($_POST['reconciled']as $recon1){
foreach($_POST['reconciled2'] as $recon2){
$query="select bankstatement.date,bankstatement.referenceno,bankstatement.debit,bankstatement.credit,bankstatement.status,cashbook.date,cashbook.referenceno,
cashbook.debit,cashbook.credit,cashbook.status
from bankstatement cross join cashbook
where '$recon1' = '$recon2' and cashbook.credit = bankstatement.debit and cashbook.debit = bankstatement.credit and cashbook.date = bankstatement.date and bankstatement.status = '0' and cashbook.status = '0'";
$result= mysqli_query($db,$query);
if($result)
{
$recon1 = implode(',' ,$_POST['reconciled']);
$recon2 = implode(',' ,$_POST['reconciled2']);
echo $change = "update bankstatement set status='1' where statementid=$recon1";
echo $change1 = "update cashbook set status='1' where cashbookid=$recon2";
$db->query($change);
$db->query($change1);
echo "<script>
alert('Success in Reconciling Process!!!');
window.location.href='viewreconcile.php';
</script>
";
}else{
echo "<script>
alert('Error in Reconciling Process!!!');
window.location.href='managereconcile.php';
</script>
";
}
}
}
}
}
?>
Results after code is run:
My issue now comes when trying to compare the data from both tables. The image of results show the first ref no's that were stored in the database after import instead of searching the similar ref no's. I dont get an error message instead i'm shown a success message though no update actually happens and no hanging occurs.
A sample of the CSV test data
Since you are trying to update the data of multiple rows with the same value you can't send it as where cashbookid=$recon2 but instead your code should look like this:
echo $change = "update bankstatement set status='1' where statementid IN($recon1)";
echo $change1 = "update cashbook set status='1' where cashbookid IN ($recon2)";
Since your values are being sent as a comma separated values, this will look for all those rows and update them.
This question already has answers here:
Can I mix MySQL APIs in PHP?
(4 answers)
Closed 6 years ago.
I am attempting to implement a click count system. I am using the following code in this link Click here to see code, but changing it to modern standards. Initially I received errors for the msqli_real_escape_ string, but I believed I resolved it(no errors). Now, I am not receiving any errors at all, but the query is not sending into my database. I am using ini_set('display_errors', 1);
error_reporting(E_ALL); for error checking. Also I have my $con and session in and ini file that I call, so the session and connection are not issues.
Does anyone see what I am doing wrong or is there a good way I can check to see what isn't working?
//create current page constant
$curPage = mysqli_real_escape_string($con,htmlspecialchars($_SERVER['PHP_SELF']));
//set number of clicks variable to 0
$clicks = 0;
//do not recount if page currently loaded
if($_SESSION['page'] != $curPage) {
//set current page as session variable
$_SESSION['page'] = $curPage;
$click_sql = "
SELECT *
FROM click_count
WHERE page_url = ?
";
if (!$click_stmt = $con->prepare($click_sql)) {
$click_stmt->bind_param("s", $curPage);
$click_stmt->execute();
$num_rows = $click_stmt->fetchColumn();
if (!$click_stmt->errno) {
// Handle error here
}
$stmt->bind_result($click_id, $page_url, $page_count);
} elseif ($num_rows == 0) {
//try to create new record and set count for new page to 1
//output error message if problem encountered
$click_insert_stmt = "
INSERT INTO click_count
(page_url, page_count)
VALUES(?, ?)";
if(!$click_stmt = $con->prepare($click_insert_stmt)) {
$click_insert_stmt->execute(array('$curPage',1));
echo "Could not create new click counter.";
}
else {
$clicks= 1;
}
} else {
//get number of clicks for page and add 1 fetch(PDO::FETCH_BOTH)
while($click_row = $click_insert_stmt->fetch(PDO::FETCH_BOTH)) {
$clicks = $row['page_count'] + 1;
//update click count in database;
//report error if not updated
$click_update_stmt = "
UPDATE click_count
SET page_count = ?
WHERE page_url = ?
";
if(!$click_stmt = $con->prepare("$click_update_stmt")) {
$click_update_stmt->execute(array('$clicks', '$curPage'));
echo "Could not save new click count for this page.";
}
}
}
}
Edit: New Updated Code
// ********Page count************
//create current page constant
$curPage = mysqli_real_escape_string($con,($_SERVER['PHP_SELF']));
//set number of clicks variable to 0
$clicks = 0;
//do not recount if page currently loaded
if($_SESSION['page'] != $curPage) {
//set current page as session variable
$_SESSION['page'] = $curPage;
$click_sql = "
SELECT *
FROM click_count
WHERE page_url = ?
";
if (!$click_stmt = $con->prepare($click_sql)) {
$click_stmt->bind_param("s", $_SERVER['PHP_SELF']);
$click_stmt->execute();
$num_rows = $click_stmt->fetchColumn();
if (!$click_stmt->errno) {
// Handle error here
}
$stmt->bind_result($click_id, $page_url, $page_count);
} elseif ($num_rows == 0) {
//try to create new record and set count for new page to 1
//output error message if problem encountered
$click_insert_stmt = "
INSERT INTO click_count
(page_url, page_count)
VALUES(?, ?)";
if(!$click_stmt = $con->prepare($click_insert_stmt)) {
$click_insert_stmt->execute(array($curPage,1));
echo "Could not create new click counter.";
}
else {
$clicks= 1;
}
} else {
//get number of clicks for page and add 1 fetch(PDO::FETCH_BOTH)
while($click_row = $click_insert_stmt->fetch(PDO::FETCH_BOTH)) {
$clicks = $row['page_count'] + 1;
//update click count in database;
//report error if not updated
$click_update_stmt = "
UPDATE click_count
SET page_count=page_count+1
WHERE page_url = ?
";
if(!$click_stmt = $con->prepare("$click_update_stmt")) {
$click_update_stmt->execute(array($curPage));
echo "Could not save new click count for this page.";
}
}
}
}
It looks like you're doing a lot of stuff like this:
$click_update_stmt->execute(array('$clicks', '$curPage'));
I'm not sure where you picked up this habit of quoting variables as strings, but you need to drop it. '$x' and $x are two hugely different things. In the first case it's literally '$x' and in the second case it's whatever the $x variable happens to represent.
Fix it like this:
$click_update_stmt->execute(array($clicks, $curPage));
Also since you're using prepared statements, which by the way is great, you do not need to and should not manually escape your values. Applying them to placeholders with bind_param is the safe way of doing it. Doing any other escaping mangles the data.
Just bind directly to the source:
$click_stmt->bind_param("s", $_SERVER['PHP_SELF']);
Don't arbitrarily run things like htmlspecialchars on input out of paranoia or because you're doing cargo-cult programming and you saw it done in a YouTube tutorial somewhere. That function is intended to be used to display values only, not store them. Data in your database should be as raw as possible.
There's a lot of problems with this code, and one of them that has me confused is why there's so much code. Remember SELECT * and then binding results to arbitrary variables is trouble, your schema might change and then your code is out of sync. Whenever possible fetch rows as an associative array if doing this, then all you have to worry about is renamed ore removed columns.
The biggest problem is this is subject to race conditions because it doesn't use an atomic increment. When writing counters, always do your updates as operations that are a single statement:
UPDATE click_count SET page_count=page_count+1 WHERE page_url=?
Your approach of reading the count, incrementing it, and then writing it back into the database means that you're inviting problems if another operation runs concurrently, something very likely on click-counter code.
This is my block of code for doing that. It works fine until it reaches the last if statement. I cannot get it to find the Graphics column using the Department_ID. I am trying to check if the user input is equal to a id within the table. Then check if that id requires graphic work done. To do that, I need to find out that for that specific project graphic is a 1 in the database.
if($graphics_id != Null)
{
$query = mysqli_query($connect,"SELECT * FROM Project_Overview WHERE Project_ID='".$graphics_id."'");
$row = mysqli_fetch_assoc($query);
//echo $row['Project_ID'];
if($graphics_id == $row['Project_ID']) //if the graphics_id matches a project_id in the table
{
$result = mysqli_query($connect, "SELECT Graphics FROM Department WHERE Department_ID ='".$graphics_id."'")
$row = mysqli_fetch_assoc($result);
if($result)
{
echo $row['Department_ID'];
} else {
echo "This Project does not require graphics!"
}
} else {
echo "Project_ID ".$graphics_id." does not exist!";
}
}
A few thoughts:
The second SELECT Statement selects the Graphics column, but later you are echoing $row['Department_ID']; which should be empty as the only key in $row would be Graphics
The last if-Statement is if($result). Don't you mean if($row)? If $result is false (and hence "This Project does not require graphics!" is printed out), this would indicate, that mysqli_query has failed, possibly because of an error in your second SQL statement.
And, as ThomasEllis said, a JOIN would be nicer and SELECT * is not wrong but returns (probably) more than you need.
Depending on where $graphics_id comes from (a user input?) you should consider escaping it for security reasons ($graphics_id_escaped = mysqli_real_escape_string($connect, $graphics_id); - just in case ;)
I want to make a code where if the data already exists in the database and the user insert the same input again and send to the database, the sql command will detect it and will not allow the duplicate data enter the database. Addtional information, I don`t have primary key for my table. Here is my code.
$sql="INSERT IGNORE INTO tempahan(Nama,Aktiviti,No_HP,Unit,Tempat,Tarikh_Penggunaan,Masa_Mula,Masa_Akhir,Email) VALUES('$_POST[name]','$_POST[Aktiviti]','$_POST[number]','$_POST[unit]','$_POST[tempat]','$_POST[tarikh]','$_POST[masa1]','$_POST[masa2]','$_POST[email]')";
$_POST['tempat'] = $data['Tempat'] ;
$_POST['masa1'] = $data['Masa_Mula'];
$_POST['masa2'] = $data['Masa_Akhir']; if($_POST['tempat'] != $data['Tempat'] && $_POST['masa1'] != $data['Masa_Mula'] && $_POST['masa2'] != $data['Masa_Akhir']) {
echo 'the booking was successful.';
}
else
{ echo 'the place already occupied.';}
I'm new to sql and also php. Therefore, I really need help from all of you guys. I already see the other same question. But, every solution provided I've failed.
The correct way to do this is to enforce a unique constraint on your table, across the fields that you consider to be unique. You can do that as such.
alter table tempahan
add unique (Tempat, Masa_Mula, Masa_Akhir)
Your database will then reject out of hand any attempts to insert duplicate data. No need to do a prior check before inserting.
Here is a very basic demo of what happens when you set your table up with this unique constraint, and then try and insert duplicate data. In short: it errors.
$query = $db->query( // query your table );
$array = array('name'=>$_POST['name'],
'address'=>$_POST['address']);
while ($row = mysqli_fetch_all($query)) {
$diff = in_array($array, $row);
{
if(empty($diff))
{
// insert data into table
}
else{
//data already exist
}
}
}
// first check existing recors on the database
$select = "SELECT `Tempat`, `Masa_Mula`, `Masa_Akhir`
FROM `tempahan`
WHERE `Tempat` = {$_POST['tempat']}
AND `Masa_Mula` = {$_POST['masa1']}
AND `Masa_Akhir` = {$_POST['masa2']}";
$result = mysql_query($select, $dbconnection);
// check if the have existing records
// the query fetching depends on your work
// but this is a simple way only
// but have more examples on the internet
// to make query more better and ellegant
if (mysql_num_rows($select) > 0) {
echo 'the place already occupied.';
} else {
// insert new record
$sql="INSERT IGNORE INTO tempahan(Nama,Aktiviti,No_HP,Unit,Tempat,Tarikh_Penggunaan,Masa_Mula,Masa_Akhir,Email)
VALUES(
'$_POST[name]',
'$_POST[Aktiviti]',
'$_POST[number]',
'$_POST[unit]',
'$_POST[tempat]',
'$_POST[tarikh]',
'$_POST[masa1]',
'$_POST[masa2]',
'$_POST[email]')";
echo 'the booking was successful.';
}
Reason: I was assigned to run some script that advances a website,it's a fantasy football site and there are several instants of the site located into different domains. Some has more than 80k users and each users supposed to have a team that consists of 15 players. Hence some tables have No.users x No.players rows.
However Sometimes the script fails and the result gets corrupted, therefore I must backup 10 tables in question before i execute the script. Nevertheless, I still need to backup the tables to keep historical record of users action. Because football matches may last for 50+ game weeks.
Task: To duplicate db tables using php script. When i started i used to backup the tables using sqlyog. it's works but it's time consuming since I have to wait for each table to be duplicated. Besides, for large tables the sqlyog application crashes during the duplicating of large tables which may be very annoying.
Current solution: I have created a simple application with interface that does the job and it works great. It consist of three files, one for db connection, 2nd for db manipulation, 3rd for user interface and to use the 2nd file's code.
The thing is, sometimes it get stuck at the middle of duplicating tables process.
Objective: To create an application to be used by admin to facilitate database backing up using mysql+php.
My Question: How to ensure that the duplicating script will definitely backup the table completely without hanging the server or interrupting the script.
Down here I will include my code for duplicating function, but basically these are the two crucial lines that i think the problem is located in them:
//duplicate tables structure
$query = "CREATE TABLE $this->dbName.`$newTableName` LIKE $this->dbName.`$oldTable`";
//duplicate tables data
$query = "INSERT INTO $this->dbName.`$newTableName` SELECT * FROM $this->dbName.`$oldTable`";
The rest of the code is solely for validation in case error occur. If you wish to take a look at the whole code, be my guest. Here's the function:
private function duplicateTable($oldTable, $newTableName) {
if ($this->isExistingTable($oldTable))
{
$this->printLogger("Original Table is valid -table exists- : $oldTable ");
}
else
{
$this->printrR("Original Table is invalid -table does not exist- : $oldTable ");
return false;
}
if (!$this->isExistingTable($newTableName))// make sure new table does not exist alrady
{
$this->printLogger("Distination Table name is valid -no table with this name- : $newTableName");
$query = "CREATE TABLE $this->dbName.`$newTableName` LIKE $this->dbName.`$oldTable`";
$result = mysql_query($query) or $this->printrR("Error in query. Query:\n $query\n Error: " . mysql_error());
}
else
{
$this->printrR("Distination Table is invalid. -table already exists- $newTableName");
$this->printr("Now checking if tables actually match,: $oldTable => $newTableName \n");
$varifyStatus = $this->varifyDuplicatedTables($oldTable, $newTableName);
if ($varifyStatus >= 0)
{
$this->printrG("Tables match, it seems they were duplicated before $oldTable => $newTableName");
}
else
{
$this->printrR("The duplicate table exists, yet, doesn't match the original! $oldTable => $newTableName");
}
return false;
}
if ($result)
{
$this->printLogger("Query executed 1/2");
}
else
{
$this->printrR("Something went wrong duplicateTable\nQuery: $query\n\n\nMySql_Error: " . mysql_error());
return false;
}
if (!$this->isExistingTable($newTableName))//validate table has been created
{
$this->printrR("Attemp to duplicate table structure failed $newTableName table was not found after creating!");
return false;
}
else
{
$this->printLogger("Table created successfully: $newTableName");
//Now checking table structure
$this->printLogger("Now comparing indexes ... ");
$autoInc = $this->checkAutoInc($oldTable, $newTableName);
if ($autoInc == 1)
{
$this->printLogger("Auto inc seems ok");
}
elseif ($autoInc == 0)
{
$this->printLogger("No inc key for both tables. Continue anyways");
}
elseif ($autoInc == -1)
{
$this->printLogger("No match inc key!");
}
$time = $oldTable == 'team_details' ? 5 : 2;
$msg = $oldTable == 'team_details' ? "This may take a while for team_details. Please wait." : "Please wait.";
$this->printLogger("Sleep for $time ...\n");
sleep($time);
$this->printLogger("Preparing for copying data ...\n");
$query = "INSERT INTO $this->dbName.`$newTableName` SELECT * FROM $this->dbName.`$oldTable`";
$this->printLogger("Processing copyign data query.$msg...\n\n\n");
$result = mysql_query($query) or $this->printrR("Error in query. Query:\n $query\n Error: " . mysql_error());
// ERROR usually happens here if large tables
sleep($time); //to make db process current requeste.
$this->printLogger("Query executed 2/2");
sleep($time); //to make db process current requeste.
if ($result)
{
$this->printLogger("Table created ($newTableName) and data has been copied!");
$this->printLogger("Confirming number of rows ... ");
/////////////////////////////////
// start checking count
$numRows = $this->checkCountRows($oldTable, $newTableName);
if ($numRows)
{
$this->printLogger("Table duplicated successfully ");
return true;
}
else
{
$this->printLogger("Table duplicated, but, please check num rows $newTableName");
return -3;
}
// end of checking count
/////////////////////////////////
}//end of if(!$result) query 2/2
else
{
$this->printrR("Something went wrong duplicate Table\nINSERT INTO $oldTable -> $newTableName\n\n$query\n mysql_error() \n " . mysql_error());
return false;
}
}
}
AS you noticed the function is only to duplicate one table, that's why there is another function that that takes an array of tables from the user and pass the tables names array one by one to duplicateTable().
Any other function should be included for this question, please let me know.
One solution pops into my mind, would duplicating tables by part by part add any improvement, I'm not sure how Insert into works, but maybe if I could insert let's say 25% at a time it may help?
However Sometimes the script fails and the result gets corrupted,
therefore I must backup 10 tables in question before i execute the
script.
Probably you need to use another solution here: transactions. You need to wrap up all queries you are using in failing script into transaction. If transaction fails all data will be the same as in the beginning of the operation. If queries got executed correctly - you are OK.
why are you every time duplicating the table..
CLUSTERS are good option which can make duplicate copies of your table in distributed manner and is much more reliable and secure.