I'm using a simple form to do a database query. The database is accessed via password which I've included in the code. I'm not sure why I keep hitting the error on the string escape and the undefined variable $query = htmlspecialchars($query);
<?php
$servername = "localhost";
$username = "xxx";
$password = "xxx";
$dbname = "xxx";
// Create connection
$conn = new mysqli($servername, $username, $password, $dbname);
// Check connection
if ($conn->connect_error) {
die("Connection failed: " . $conn->connect_error);
}
?>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<title>Search</title>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<link rel="stylesheet" type="text/css" href="style.css"/>
</head>
<body>
<form action="Search2.php" method="POST">
<input type="text" name="query" />
<input type="submit" value="Search" />
</form>
<?php
if (isset($_POST['query']))
$query = $_POST['query'];
if (!empty($query))
$query = $_POST['query'];
// gets value sent over search form
$query = htmlspecialchars($query);
// changes characters used in html to their equivalents, for example: < to >
$query = mysql_real_escape_string($query);
// makes sure nobody uses SQL injection
$raw_results = mysql_query("SELECT LastName, FirstName FROM Staff
WHERE (`LastName` LIKE '%".$query."%') OR (`FirstName` LIKE '%".$query."%')") or die(mysql_error());
if(mysql_num_rows($raw_results) > 0){ // if one or more rows are returned do following
while($results = mysql_fetch_array($raw_results)){
// $results = mysql_fetch_array($raw_results) puts data from database into array, while it's valid it does the loop
echo "<p><h3>".$results['LastName']."</h3>".$results['FirstName']."</p>";
// posts results gotten from database(title and text) you can also show id ($results['id'])
}
}
else{ // if there is no matching rows do following
echo "No results";
}
?>
</body>
</html>
The issue here is that you've invoked a mysqli object with your credentials, however, later you try to execute with the mysql_ procedural method. You don't have a connection there. You need to stick with the mysqli object. Furthermore, you should use prepared statements to handle your user input on SQL queries.
Remove these, we don't need to do sanitization for prepared statements:
//BYE!
$query = htmlspecialchars($query);
// changes characters used in html to their equivalents, for example: < to >
$query = mysql_real_escape_string($query);
// makes sure nobody uses SQL injection
Now let's use the mysqli object and OOP prepared methods. However, first we need to construct our like statements as our query's variables aren't executed, you can't concatenate %?% directly into the prepared() statement.
$query = '%'.$query.'%';
$stmt = $mysqli->prepare("SELECT LastName, FirstName FROM Staff
WHERE LastName LIKE ? OR FirstName LIKE ?");
Now we can bind the parameters to our $stmt object.
$stmt->bind_param('ss', $query, $query);
Let's execute it now and get our data back.
$result = $stmt->execute();
Then we can loop:
while ($row = $result->fetch_assoc()) {
echo "<p><h3>".$result['LastName']."</h3>".$result['FirstName']."</p>";
}
Edit
You also don't need to escape your column names with a backtick because:
They don't have - in the name
They aren't reserved special words in MySQL.
make sure your PHP version is below 7.0 as stated here:
http://php.net/manual/en/function.mysql-real-escape-string.php
Warning
This extension was deprecated in PHP 5.5.0, and it was removed in PHP 7.0.0. Instead, the MySQLi or PDO_MySQL extension should be used. See also MySQL: choosing an API guide and related FAQ for more information. Alternatives to this function include:
mysqli_real_escape_string()
PDO::quote()
Related
I have read many articles on this password_hash and has applied as much as I can if not all the things I read about it
Still the password_verify still refuses to authenticate values no matter how much I tried. PHP Version 5.61.6 and SQL version 5.7.9
any form of help is appreciated, am already exhausted from trying many string combinations
<!DOCTYPE html>
<html>
<head>
<title>Administrator</title>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
</head>
<body>
<?PHP
//.......all variables are collected from html form....
$conn = mysqli_connect("localhost", "uname", "pword", "dbname");
mysqli_set_charset($conn, 'utf8');
//.......`SN` column has the unique attribute
$sql = "SELECT * FROM Sign_Up WHERE `SN`=$sn";
$result = mysqli_query($conn, $sql);
if (mysqli_num_rows($result) > 0) {
while ($row = mysqli_fetch_assoc($result)) {
$date = date('Y-m-j g:i:s');
//.......idgen is a function previously defined
$id = idgen();
//.......prints $id before hashing....
echo $id."<BR>";
$id = password_hash('$id', PASSWORD_DEFAULT);
//......string length before storing
echo strlen($id)."<BR>";
//......table columns
$f = $row["FirstName"];
$l = $row["LastName"];
$bn = $row["BusinessName"];
$ba = $row["BusinessAddress"];
$sq = "INSERT INTO Distributors (`FirstName`, `LastName`, `BusinessName`, `BusinessAddress`) VALUES ('$f', '$l', '$bn', '$ba')";
$res = mysqli_query($conn, $sq);
}
}
?>
</body>
</html>
And the code for verifying the hash is
<html>
<head>
<meta charset="UTF-8">
</head>
<body>
<?PHP
$conn = mysqli_connect($servername, $username, $password, $dbname);
mysqli_set_charset($conn, 'utf8');
//.....phone number has a unique attribute
$sql = "SELECT `ID` FROM Distributors WHERE `PhoneNumber`='number'";
$result = mysqli_query($conn, $sql) or die(mysqli_error($conn));
$result1= mysqli_num_rows($result);
$look = mysqli_fetch_array($result)['ID'];
print $look."<BR>";
$look = trim($look);
print $look."<BR>";
print strlen($look)."<BR>";
//......all print statements yields expected results and hashed password is stored
//......in VARCHAR (255)...I also tried CHAR
$ver = password_verify('user input data', '$look');
if ($ver) {
print "ok";
}
else {
print "no";
}
?>
</body>
</html>
Use php variables without any quote or inside double quotes, "":
$id = password_hash($id, PASSWORD_DEFAULT); // no quotes around $id
$ver = password_verify('user input data', "$look"); // double quotes around $look
Single quote strings are not parsed i.e. treated as literal strings while double quoted strings are parsed and therefore variables names are expanded with their values.
When hashing use:
$id = "school";
Password_hash($id);
When verifying use:
Password_verify($id, $data_from_database);
We have the following code in the HTML of one of our webpages. We are trying to display all of the Wifi speeds and GPS locations in our database using the MySQL call and while loop shown in the below PHP code. However, it doesn't return anything to the page. We put echo statements in various parts of the PHP (ex. before the while loop, before the database stuff) and it doesn't even print those statements to the webpage.
<body>
<h2>WiFi Speeds in the System</h2>
<p>Speeds Recorded in the System</p>
<?php
$username = "root";
$password = "";
$hostname = "localhost";
$dbc = mysql_connect($hostname, $username, $password)
or die('Connection Error: ' . mysql_error());
mysql_select_db('createinsertdb', $dbc) or die('DB Selection Error' .mysql_error());
$data = "(SELECT Wifi_speed AND GPS_location FROM Instance)";
$results = mysql_query($data, $dbc);
while ($row = mysql_fetch_array($results)) {
echo $row['Wifi_speed'];
echo $row['GPS_location'];
}
?>
</body>
This line is incorrect, being the AND:
$data = "(SELECT Wifi_speed AND GPS_location FROM Instance)";
^^^
Change that to and using a comma as column selectors:
$data = "(SELECT Wifi_speed, GPS_location FROM Instance)";
However, you should remove the brackets from the query:
$data = "SELECT Wifi_speed, GPS_location FROM Instance";
Read up on SELECT: https://dev.mysql.com/doc/refman/5.0/en/select.html
Using:
$results = mysql_query($data, $dbc) or die(mysql_error());
would have signaled the syntax error. Yet you should use it during testing to see if there are in fact errors in your query.
Sidenote:
AND is used for a WHERE clause in a SELECT.
I.e.:
SELECT col FROM table WHERE col_x = 'something' AND col_y = 'something_else'
Or for UPDATE, i.e.:
UPDATE table SET col_x='$var1'
WHERE col_y='$var2'
AND col_z='$var3'
Footnotes:
Consider moving to mysqli with prepared statements, or PDO with prepared statements, as mysql_ functions are deprecated and will be removed from future PHP releases.
Add error reporting to the top of your file(s) which will help find errors.
<?php
error_reporting(E_ALL);
ini_set('display_errors', 1);
// rest of your code
Sidenote: Error reporting should only be done in staging, and never production.
"Thank you for the suggest but we tried that and it didn't change anything. – sichen"
You may find that you may not be able to use those functions after all. If that is the case, then you will need to switch over to either mysqli_ or PDO.
References:
MySQLi: http://php.net/manual/en/book.mysqli.php
PDO: http://php.net/manual/en/ref.pdo-mysql.php
hi mate i see some problem with your DB connection & query
here is example check this out
in SELECT is incorrect, being the AND .using a comma as column selectors:
and make condition for after set query & check data validation that is proper method
<?php
$servername = "localhost";
$username = "root";
$password = "";
$dbname = "createinsertdb";
// Create connection
$conn = new mysqli($servername, $username, $password, $dbname);
// Check connection
if ($conn->connect_error) {
die("Connection failed: " . $conn->connect_error); }
$sql = "SELECT `Wifi_speed `, `GPS_location `, FROM `Instance`";
$result = $conn->query($sql);
if ($result->num_rows > 0) {
// output data of each row
while($row = $result->fetch_assoc()) {
echo $row['Wifi_speed'];
echo $row['GPS_location'];
}
} else {
echo "0 results";
}
$conn->close();
?>
I need help with the follow code to change it from Procedural to Prepared Statement. I will do my best to code it:
Default procedural script MYSQLI default
<?php
$conn = mysqli_connect ('localhost', 'gggggg', 'gggggg') ;
mysqli_select_db ($conn, 'ggggg');
$anti_injection = mysqli_real_escape_string($_GET['user']);
$sql = "SELECT * FROM profiles WHERE username =".$anti_injection);
$result = mysqli_query($conn, $query);
while($row = mysqli_fetch_array($sql)) {
$username = stripslashes($row['username']);
$age = stripslashes($row['age']);
$gender = stripslashes($row['gender']);
?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>title</title>
</head>
<body>
CUSTOM HTML FOR A NICE DESIGN I WANT TO KEEP THE SAME DESIGN LAYOUT ETC...
CATEGORY <?php echo $username; ?>
TITEL <?php echo $age; ?>
CONTENT <?php echo $sex; ?>
</body>
</html>
<?php
}
?>
#
NOW MY CHANGES TO STATEMENTS HOPE IT WORKS
#
$query = $sql->prepare("SELECT * FROM profiles WHERE `username`=?")
$prep->bind_param("s",$anti_injection);
$prep->execute();
Thats all I know for the SELECT in a safe mode but then with the MYSQLI_FETCH_ARRAY I really dont know it it will work and hopefully if there is a chance to keep the script the way I like with the echos between the HTML BODY page
Some Example On How it must be done?
First off, I highly recommend you not mix procedural with objects. It will get confusing much faster that way. Consider using the mysqli object instead.
$mysqli = new mysqli('localhost'...);
Second, you're close but, as I said, you're mixing objects and procedural so the way you've changed it won't work. Plus you're bouncing variables all over the place (if you ran your changes raw it would fail). Assuming you switch to the mysqli object as outlined above, you can do this
$prep = $mysqli->prepare("SELECT * FROM profiles WHERE `username`=?");
$prep->bind_param("s",$anti_injection);
$prep->execute();
Now, the next part is tricky. You have to have mysqlnd installed to do this but it's the best way to get your results back. If you run this and get an error about get_result being missing, you're not running mysqlnd
$result = $prep->get_result();
while($row = $result->fetch_array()) {
//Your HTML loop here
}
I provide a script, based on yours, that i have commented, tested, and uses procedural 'mysqli'. Hopefully, it will clarify things.
<?php
/* (PHP 5.3.18 on XAMPP, windows XP)
*
* I will use the procedural 'mysqli' functions in this example as that is
* what you seem familiar with.
*
* However, the 'object oriented' style is preferred currently.
*
* It all works fine though :-)
*
* I recommend PDO (PHP Data Objects) as the way to go for Database access
* as it provides a 'common' interface to many database engines.
*/
// this is an example 'select' parameter -- how this value gets set is up to you...
// use a form, get parameter or other, it is not important.
$bindparamUsername = 'user_2'; // example!!!!
// connect to the database...
$dbConnection = mysqli_connect('localhost', 'test', 'test'); // connect
mysqli_select_db($dbConnection, 'testmysql'); // my test database
// the SQL Query...
// the '?' is a placeholder for a value that will be substituted when the query runs.
// Note: the ORDER of the selected Columns is important not the column names.
//
// Note: The number of selected columns is important and must match the number of
// 'result' bind variables used later.
$sql = "SELECT username, age, gender FROM profiles WHERE username = ?";
// DB engine: parse the query into an internal form that it understands
$preparedQuery = mysqli_prepare($dbConnection, $sql);
// bind an actual input PHP variable to the prepared query so the db will have all required values
// when the query is executed.
//
mysqli_stmt_bind_param($preparedQuery, 's', $bindparamUsername);
// run the query...
$success = mysqli_execute($preparedQuery);
// You can only bind which variables to store the result columns in AFTER the query has run!
//
// Now bind where any results from the query will be returned...
// There must be as many 'bind' variables as there are selected columns!
// This is because each column value from the query will be returned into the
// 'bound' PHP variable.
//
// Note: You cannot bind to an array. You must bind to an individual PHP variable.
//
// I have kept the same names but they are only of use to you.
$fetchedRow = array( 'username' => null,
'age' => null,
'gender' => null);
/*
* Note: order of columns in the query and order of destination variables in the 'bind' statement is important.
*
* i.e. $fetchedRow[username] could be replaced with variable $firstColumn,
* $fetchedRow[age] could be replaces with variable $secondColumn
* and so on...
*
* There must be as many bind variables as there are columns.
*/
mysqli_stmt_bind_result($preparedQuery, $fetchedRow['username'],
$fetchedRow['age'],
$fetchedRow['gender']);
/*
* Note: if you use the 'Object Oriented' version of 'mysqli': All of this is 'hidden'
* but still happens 'behind the scenes'!
*
*/
?>
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title></title>
</head>
<body>
CUSTOM HTML FOR A NICE DESIGN I WANT TO KEEP THE SAME DESIGN LAYOUT ETC...
<?php // each 'fetch' updates the $fetchedRow PHP variable... ?>
<?php while (mysqli_stmt_fetch($preparedQuery)): ?>
<br />
CATEGORY <?php echo $fetchedRow['username']; ?>
<br />
TITEL <?php echo $fetchedRow['age']; ?> <br />
CONTENT <?php echo $fetchedRow['gender']; ?> <br />
<?php endwhile ?>
</body>
</html>
If you'r learning I encourage you to use Object Oriented Style
The Manual is the first resource where you can find the most accurate information. Following your example:
$mysqli = new mysqli("example.com", "user", "password", "database");
if ($mysqli->connect_errno) {
echo "Failed to connect to MySQL: (" . $mysqli->connect_errno . ") " . $mysqli->connect_error;
}
//Here you avoid the warning undefine variable if $_GET['user'] ins't set
$user = isset($_GET['user']) ? $_GET['user'] : NULL;
$row = array();
//Checking if $user is NULL
if(!empty($user)){
// Prepared statement, stage 1: prepare
if (!($stmt = $mysqli->prepare("SELECT * FROM profiles WHERE `username`=?"))) {
echo "Prepare failed: (" . $mysqli->errno . ") " . $mysqli->error;
}
/* Prepared statement, stage 2: bind and execute */
if (!$stmt->bind_param("s", $user)) {
echo "Binding parameters failed: (" . $stmt->errno . ") " . $stmt->error;
}
if (!$stmt->execute()) {
echo "Execute failed: (" . $stmt->errno . ") " . $stmt->error;
}
//Fetching the result
$res = $stmt->get_result();
$row = $res->fetch_assoc();
/* explicit close recommended */
$stmt->close();
}else{
//do this code if $user is null
}
//Printing out the result
echo '<pre>';
print_r($row);
echo '</pre>';
you can do it like that
$link = mysqli_connect("localhost", "my_user", "my_password", "db"); //Establishing connection to the database , this is alias of new mysqli('')
$query="SELECT * FROM profiles WHERE `username`=?";
$stmt = $link->prepare($query);
$stmt->bind_param("s",$anti_injection); // binding the parameter to it
$stmt->execute(); //Executing
$result = $stmt->get_result();
while($row = $result->fetch_array(MYSQLI_ASSOC)) // we used MYSQLI_ASSOC flag here you also can use MYSQLI_NUM or MYSQLI_BOTH
{
//Do stuff
}
I have made a search box so that you can enter the product id that you wish to gain the information of. When i input data in the product id box, there are no results returned, anyone know what im doing wrong? I think that 'while ($row = mysql_fetch_array($result)) {' is wrong but not too sure as everything ive tried didn't work.
<div class="searchbox">
<form action="Search.php" method="get">
<fieldset>
<input name="search" id="search" placeholder="Search for a Product" type="text" />
<input id="submit" type="button" />
</fieldset>
</form>
</div>
<div id="content">
<ul>
<?php
// connect to the database
include('base.php');
$search = mysql_real_escape_string($_GET['search']);
$query = "SELECT * FROM Product WHERE ProductID LIKE '%{$search}%'";
$result = mysql_query($query);
while ($row = mysql_fetch_array($result)) {
echo "<li><span class='name'><b>{$row['ProductID']}</b></span></li>";
}
Don't use mysql specific syntax, It's outdated and can get you into real trouble later on, especially if you decide to use sqlite or postgresql.
Use a PDO connection, you can init one like this:
// Usage: $db = connectToDatabase($dbHost, $dbName, $dbUsername, $dbPassword);
// Pre: $dbHost is the database hostname,
// $dbName is the name of the database itself,
// $dbUsername is the username to access the database,
// $dbPassword is the password for the user of the database.
// Post: $db is an PDO connection to the database, based on the input parameters.
function connectToDatabase($dbHost, $dbName, $dbUsername, $dbPassword)
{
try
{
return new PDO("mysql:host=$dbHost;dbname=$dbName;charset=UTF-8", $dbUsername, $dbPassword);
}
catch(PDOException $PDOexception)
{
exit("<p>An error ocurred: Can't connect to database. </p><p>More preciesly: ". $PDOexception->getMessage(). "</p>");
}
}
And then init the variables:
$host = 'localhost';
$user = 'root';
$dataBaseName = 'databaseName';
$pass = '';
Now you can access your database via
$db = connectToDatabase($host , $databaseName, $user, $pass); // You can make it be a global variable if you want to access it from somewhere else.
Then you should make sure that you actually have the variable:
$search = isset($_GET['search']) ? $_GET['search'] : false;
So you can actually skip the database thing if something, somehow, fails.
if(!$search)
{
//.. return some warning error.
}
else
{
// Do what follows.
}
Now you should construct a query that can be used as a prepared query, that is, it accepts prepared statements so that you prepare the query and then you execute an array of variables that are to be put executed into the query, and will avoid sql injection in the meantime:
$query = "SELECT * FROM Product WHERE ProductID LIKE :search;"; // Construct the query, making it accept a prepared variable search.
$statement = $db->prepare($query); // Prepare the query.
$statement->execute(array(':search' => $search)); // Here you insert the variable, by executing it 'into' the prepared query.
$statement->setFetchMode(PDO::FETCH_ASSOC); // Set the fetch mode.
while ($row = $statement->fetch())
{
$productId = $row['ProductID'];
echo "<li class='name><strong>$productId</strong></li>";
}
Oh yes, don't use the b tag, it's outdated. Use strong instead (It's even smarter to apply font-weight: bold; to .name in a separate css file.
Feel free to ask questions if anything is unclear.
remove the {} before and after $search.
should be:
$query = "SELECT * FROM Product WHERE ProductID LIKE '%$search%'";
You can use:
$result = mysql_query($query) or die($query."<br/><br/>".mysql_error());
To confirm that the data is returning.
I am having my first attempts to a search engine:
I have a database called "global" and a table called "mpl" which contains 11 columns (Named: Customer, Part No, Descripton, Country Of Origin, and several other) with multiple rows for parts.
What i aim to do with the code below - is to get the Description and Country Of Origin displayed for the Part No the user has entered to the search field.
Form:
<form action="search.php" method="post">
<input type="text" name="find" /><br />
<input type="submit" value="Search" /> </form>
And the PHP:
$host = "localhost";
$dbuser = "root";
$dbpass = " ";
$db = "global";
$con = mysql_connect($host, $dbuser, $dbpass);
if(!$con){ die(mysql_error());
}
$select = mysql_select_db($db, $con);
if(!$select){ die(mysql_error());
}
$item = $_REQUEST['find'];
$data = mysql_query("SELECT * FROM mpl WHERE 'Part No' ='".$item."'");
while($row = mysql_fetch_array($data)){
echo $row['Description']. "<br>";
echo $row['Country Of Origin']. "<br><p>";
}
?>
Can someone tell me what am i doing wrong? Once i enter anything to my form 'find' - i get no results. If i run the search using LIKE instead of "=" with no value - it displays a bunch of Descriptions and Country of origin - this means i have connected to my DB correctly. This is driving me nuts..I feel i have messed up the mysql_query() part somehow - but i can't figure out which part.
You are using the wrong characters to escape the Part No column name in your query. Escape them with the backticks (`) and it should be fine.
$data = mysql_query("SELECT * FROM mpl WHERE `Part No` ='".$item."'");
Also, you should validate the user's query to prevent SQL injection.
A lot of people here have already pointed out possible and actual errors in your code, but here's the combined solution. Firstly I converted your code to mysqli which is the correct way of connecting to a mySQL database. The way you were connecting is out of date, and not recommended. Secondly I added some code to stop sql injection. Thirdly, I changed 'Part No' to `Part No``(ignore the second back tick) in your query.
<?php
$mysqli = new mysqli('localhost', 'root', DB_PASSWORD, 'global');
/* check connection */
if ($mysqli->connect_error)
die('Connect Error (' . $mysqli->connect_errno . ') ' . $mysqli->connect_error);
/* escape string from sql injection */
$item = $mysqli->real_escape_string($_POST['find']);
/* query database */
$result = $mysqli->query("SELECT * FROM `mpl` WHERE `Part No` = '".$item."'");
while ($col = $result->fetch_array(MYSQLI_ASSOC))
echo '<p>' . $col['Description'] . '<br />' . $col['Country Of Origin'] . '</p>';
$result->close();
/* don't forget to close the connection */
$mysqli->close();
?>
What if you change:
$item = $_REQUEST['find'];
to
$item = $_POST['find'];
Also some function like mysql_select_db() are deprecated and going to be removed. See:
http://php.net/manual/en/function.mysql-select-db.php
Try changing this potion.
$item = $_REQUEST['find']; $data = mysql_query("SELECT * FROM mpl WHERE 'Part No' ='".$item."'");
to this
$item = $_POST['find'];
$data = mysql_query("SELECT * FROM mpl WHERE Part No ='$item'");
do something like this in your request to remove any possible whitespaces and normalize to upper case for select string.
$item = strtoupper(trim($_REQUEST['find']));
And do this in your SQL: to normalize as well.
$data = mysql_query("SELECT * FROM mpl WHERE UPPER(TRIM('Part No')) ='".$item."'");
You are basically not getting an exact match on your where clause
First off, I agree with Quentin; you should be using a database API like PDO or Mysqli. Secondly, it looks like people can search for parts by their part numbers or descriptions. Assuming the part numbers are numeric and the descriptions are strings... check the type of input and run the query accordingly.
$host = "localhost";
$dbuser = "root";
$dbpass = "";
$db = "global";
// Establish a database connection and select one.
// Try using one of the database API's.
// Then compose your sql by checking for the type of input from the form.
// Since your request method is a POST, then just look in the `_POST` superglobal.
$item = $_POST['find'];
if( is_numeric($item) ){
$sql = "SELECT * FROM mpl WHERE 'Part No' = {$item}";
}else{
$sql = "SELECT * FROM mpl WHERE 'Description' LIKE '%{$item}%'";
}
// Then perform the query.