This question already has answers here:
How can I prevent SQL injection in PHP?
(27 answers)
What is SQL injection? [duplicate]
(9 answers)
Closed 6 years ago.
Hello guys the below given php code is mine i need to know it is vulnerable or not
$sql = "select Email,Password from user where Email='$emailid'";
$ctr=0;
try
{
$result = $con->query($sql);
foreach($result as $row)
{
$ctr++;
$pword = $row['Password'];
}
}
catch(PDOException $e)
{
$errTyp = "danger";
$errMSG = "Something went wrong, try again later...";
}
if($ctr == 0)
{
$errTyp = "danger";
$errMSG = "Invalid Username | Password";
}
else
{
if( $pword==$password ) {
$_SESSION['Id']=$emailid;
Here is my php login page code Just to confirm, how vulnerable is the above code to sql injection?
Simple,
$sql = "select Email,Password from user where Email='$emailid'";
If $emailid could be,
$emailid = 'or 1=1';
Injection,
$sql = "select Email,Password from user where Email=''or 1=1";
It will return the first record of your database.
So attack will happen !
I see that the main problem could be the origin of the $emailid
Email='$emailid'"
You can't trust in the data sent from client($_POST,$_GET). That's a main principle in security.
So if you have Sanitize/Filtered the POST variables you should be ok.
If not you should at least use Prepared statements
http://php.net/manual/en/pdo.prepare.php
Related
This question already has answers here:
Can I mix MySQL APIs in PHP?
(4 answers)
PDO Return All Rows [duplicate]
(1 answer)
Closed 3 years ago.
I am trying to convert some MySQLi code to PDO for a Unity project. I am making a login system and I have already changed some of the MYSQLi into PDO, however I am getting an error on line 33:
Fatal Error: Call to undefined method PDOStatement::fetch_assoc()
I tried to find PDO's version of fetch_assoc and found this:
fetch(PDO::FETCH_ASSOC);
So I changed the line to
while($row = $result->fetch(PDO::FETCH_ASSOC)) {
And now my Unity DBcontroller which has a "Debug.Log(www.downloadHandler.text" isn't returning anything and the login message isn't appearing... Could you wizards please advise me on where to go next? I guess I should say the script worked fine when I was using MySQLi, but I needed to convert it to PDO for this project. Here is the code below:
<?php
$servername = "***";
$username = "***";
$password = "***";
$dbname = "***";
//variables submitted by user
$loginUser = $_POST["loginUser"];
$loginPass = $_POST["loginPass"];
// Create Connection
$conn = new PDO("mysql:host=***;dbname=***",
"***",
"***",
[PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION]);
//Check Connection
if(!$conn){
die("Connection failed.");
}
$sql = "SELECT password FROM users WHERE username = '" . $loginUser . "'";
$result = $conn->query($sql);
if ($result->fetchAll() > 0) {
// output data of each row
while($row = $result->fetch_assoc()) {
if($row["password"] == $loginPass){
echo "Login Success. Welcome ", $loginUser, "!";
}
else{
echo "Wrong Credentials.";
}
}
} else {
echo "Username does not exist.";
}
$conn = null;
?>
When you call fetchAll you fetch all the result rows from the query, so there is no data left when you call fetch. Since you only expect one row to be returned, you can just call fetch once instead:
if ($row = $result->fetch(PDO::FETCH_ASSOC)) {
if($row["password"] == $loginPass){
echo "Login Success. Welcome ", $loginUser, "!";
}
else{
echo "Wrong Credentials.";
}
}
else {
echo "Username does not exist.";
}
Notes:
You are wide open to SQL injection and should use a prepared statement
You should not store passwords in plain text, instead use PHP's password_hash and password_verify to store and verify them
It is generally considered bad practice to distinguish between incorrect password and an invalid username. Use the same error message for both.
You should use something like this code to avoid these issues:
$sql = "SELECT password FROM users WHERE username = :username";
$stmt = $conn->prepare($sql);
$stmt->bindParam(':username', $loginUser);
$stmt->execute();
if ($row = $stmt->fetch(PDO::FETCH_ASSOC)) {
if(password_verify($loginPass, $row["password"])) {
echo "Login Success. Welcome ", $loginUser, "!";
}
else{
echo "Wrong Credentials.";
}
}
else {
echo "Wrong Credentials.";
}
This question already has answers here:
When to use single quotes, double quotes, and backticks in MySQL
(13 answers)
Reference - What does this error mean in PHP?
(38 answers)
What to do with mysqli problems? Errors like mysqli_fetch_array(): Argument #1 must be of type mysqli_result and such
(1 answer)
Closed 5 years ago.
my if statement is stopping at empty it's not running the sql part, please help
//check if signin is clicked
if (isset($_POST['Signin'])){
//including database
include_once 'inc/dbs.php';
//variables
$email = mysqli_real_escape_string($conn, $_POST['email']);
$pwd = mysqli_real_escape_string($conn, $_POST['pwd']);
//check if fields are empty
//this is where the if statement stoped
if (empty($email) || empty($pwd)){
header('Location: project.php?empty field');
exit();
}
//if user has an account
//this line isn't working
else{
$sql = "SELECT * FROM users WHERE email = $email";
$row = mysqli_query($conn, $sql);
$result = mysqli_num_rows($row);
if ($result < 1)
{
header('Location: project.php?error');
exit();
}
else
{
header('Location: admin.php');
exit();
}
}
}
else{
header('Location: project.php?please fill and submit');
exit();
}
Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 8 years ago.
Improve this question
This is my attempt at a basic mysqli php login script (im only learning, so please dont be too harsh).
Can anyone see why it would be bringing up 0 rows every time and failing to login?
<?php
$con = mysqli_connect("localhost","user","pass","database");
if (mysqli_connect_errno())
{
echo "Failed to connect to MySQL, Please contact an Administrator";
}
$username = mysqli_real_escape_string($_POST['username']);
$password = mysqli_real_escape_string($_POST['password']);
$query = "SELECT * FROM users WHERE user_name='$username' AND pass_phrase='$password'";
$result = mysqli_query($con, $query);
$row_cnt = mysqli_num_rows($result);
if (!$row_cnt == 0) {
echo "Usename/Password Combination Failed";
} else {
echo "Welcome " . $_POST['username'];
}
mysqli_close($con);
?>
You need to pass DB connection to mysqli_real_escape_string() as an added parameter.
What you're presently using:
$username = mysqli_real_escape_string($_POST['username']);
$password = mysqli_real_escape_string($_POST['password']);
What you should be using:
$username = mysqli_real_escape_string($con, $_POST['username']);
$password = mysqli_real_escape_string($con, $_POST['password']);
Plus, if if (!$row_cnt == 0) doesn't work after making those changes, try a reverse approach:
I.e.:
$row_cnt = mysqli_num_rows($result);
if ($row_cnt > 0) {
echo "Welcome " . $_POST['username'];
} else {
echo "Usename/Password Combination Failed";
}
Consider adding or die(mysqli_error($con)) to mysqli_query() to signal errors in code.
Sidenote:
I noticed you may be storing passwords in plain text. If this is the case, it is highly discouraged.
I recommed you use CRYPT_BLOWFISH or PHP 5.5's password_hash() function.
For PHP < 5.5 use the password_hash() compatibility pack.
Footnotes:
Consider looking into using:
Prepared statements, or PDO with prepared statements, they're much safer.
Try removing ! or == 0 from your if condition at the bottom. Or even better:
if ($row_cnt) {
// Welcome
} else {
// Notify about authentication failure
}
Also, it's a good practice to hash your password/pass phrase.
This is very basic approach for login, assuming you have user table with id, username, and password :
<?php
if($_SERVER['REQUEST_METHOD'] == 'POST')
{
$errors = array();
if(!$_POST['username']) //check if username has been filled
{
$errors[] = 'bla bla text for empty username notice';
}
else
{
$username = mysqli_real_escape_string($conn, trim($_POST['username']));
}
if(!$_POST['password'])//check if password has been filled
{
$errors[] = 'bla bla text for empty password notice';
}
else
{
$password = mysqli_real_escape_string($conn, trim($_POST['username']));
}
if(empty($errors)) //no errors appears
{
$query = "SELECT * FROM tablename WHERE user_name = '$username' AND password = SHA1('$password')";
$result = #mysqli_query($conn, $query);
if(mysqli_num_rows($result) == 1)
{
//if one database row (record) matches the input:
// Start the session, fetch the record and insert the three values in an array
session_start();
$_SESSION = mysqli_fetch_array($result, MYSQLI_ASSOC);
header("direct to after login page");
}
else
{
// No match was made
$errors[] = 'Sorry no record match with the data you have submitted';
}
}
else
{
// If there was a problem.
echo mysqli_connect_error($conn);
}
}
You need to fix the quoting in your query. Right now you are trying to login as a user with user name $username and password $password and most likely no such combination exists. Also unless you are allowing two users to have the same username you should just query based on the username and then compare the hashed password provided with the stored hashed password.
This question already has answers here:
How can I prevent SQL injection in PHP?
(27 answers)
Closed 9 years ago.
I have the following code in my php file:
session_start();
include "connect.php";
if (isset($_POST['email']) && isset($_POST['password'])) {
$email = htmlspecialchars(mysqli_real_escape_string($conn, $_POST['email']));
$password = htmlspecialchars(mysqli_real_escape_string($conn, $_POST['password']));
function process() {
include "connect.php";
if (isset($_POST['email']) && isset($_POST['password'])) {
$email = $_POST["email"];
$password = $_POST["password"];
}
mysqli_select_db($conn, "users");
$sql = "SELECT * FROM users WHERE email='$email' AND password='$password'";
$result = mysqli_query($conn, $sql);
$count = mysqli_num_rows($result);
if ($count >= 1) {
$_SESSION['id'] = $id;
$_SESSION['email'] = $email;
$_SESSION['password'] = $password;
header('location:index.php');
} else {
echo "Email/Password is incorrect";
}
}
if ($email != "" or $password != "") {
if (isset($_POST['submit'])) {
process();
} else {
echo "Error: " . mysql_error();
}
}
}
How would I go about preventing sql injection in my login page?
I searched on the internet and most sites said I must use the mysqli_real_escape_string() function, but this did not seem to change things at all when I used the sql injection in my site again.
please help :)
Yes, use PDO and prepare statements with try/catch blocks. When using prepare, each passes as a secure parameter, eliminating risk of injection.
Use sql prepare :)
http://www.php.net/manual/en/mysqli.prepare.php
From what I know this filters any sql injection
foreach($_POST as $key => $value) $_POST[$key] = mysqli_real_escape_string($value);
Most simple way, anyway i suggest of use prepare statements
First of all, - to avoid sql injection you need to filter any kind of user input. And simplest way to do it, is to use PDO
You need to use prepared statements. I think following code snippet will give you some idea how to use it. please change according to your requirements
/* Create a prepared statement */
if($stmt = $mysqli -> prepare("SELECT * FROM users WHERE email=? AND password=?")) {
/* Bind parameters
s - string, b - blob, i - int, etc */
$stmt -> bind_param("ss", $email, $password);
/* Execute it */
$stmt -> execute();
$res = $stmt->get_result();
$row = $res->fetch_assoc();
$_SESSION['id'] = $row['id'];
$_SESSION['email'] = $row['email'];
$_SESSION['password'] = $row['password'];
header('location:index.php');
/* Close statement */
$stmt -> close();
}
/* Close connection */
$mysqli -> close();
Docs Link: http://www.php.net/manual/en/mysqli.prepare.php
http://www.php.net/manual/en/mysqli.quickstart.prepared-statements.php
http://forum.codecall.net/topic/44392-php-5-mysqli-prepared-statements/
This question already has answers here:
How can I prevent SQL injection in PHP?
(27 answers)
Closed 9 years ago.
How would i prevent SQL injections in a SQL query like this?
<?php
$mysqli = new mysqli("ip", "username", "pass", "database");
/* check connection */
if (mysqli_connect_errno()) {
printf("Sorry, the login server is 'Under Maintainance'");
exit();
}
$username = $_POST["username1"];
$username = strtolower($username);
$password = $_POST['password1'];
$hash = sha1(strtolower($username) . $password);
$query = "SELECT * FROM accounts WHERE name='$username'";
if ($result = $mysqli->query($query)) {
/* determine number of rows result set */
$rownum = $result->num_rows;
if($rownum != 0)
{
while ($row = $result->fetch_assoc()) {
{
$acct = $row['acct'];
$pass = $row['pass'];
}
if($hash == $pass){
session_start();
$_SESSION['name']=$username;
$_SESSION['acct']=$acct;
header('Location:index.php');
} else {
echo 'There was an error when logging in. Make sure your password and username are correct.';
}
}
$result->close();
}
else
{
echo 'Account does not exist. Please Register an account before logging in.';
}
$mysqli->close();
}
?>
I have already added encryption but i cannot seem to find a prevention method that i know how to use yet. Also, is it possible for a user to use a MySQL injection without using an input box? (page dissection???)
Encryption and query sanitation are not related.
You're already using mysqli, which is nice, but you don't sanitize the input to the query (namely $username, which probably doesn't need to be strtolowered either).
You should use properly parameterized queries for sanitation.
$query = "SELECT * FROM accounts WHERE name = ?";
$stmt = $mysqli->prepare($query);
$stmt->bind_param("s", $username);
$stmt->execute();
$stmt->bind_result($acct, $pass);
$stmt->fetch();
//$act and $pass are now properly set
The limits on SQL injection have nothing to do with the user. It's even possible for you to accidentally inject yourself in your own code, and injection does not even have to be malicious. For that reason, you should always properly parameterize your queries even if you don't think there's any risk of malicious injection.