私はこのMysqli PHPクラスを使っています。 私はドキュメントを読んだ後、さまざまな試行の後、私はこの単純なログインスクリプトにロックされています。 dbに存在しないログイン詳細でログインしようとすると、ユーザーページにリダイレクトされます。私は$db->has()
関数を試してもこの問題が続くので、現在はこの問題を解決する方法はありません。クラスのドキュメントに示されているように、この関数は、要求された要素が存在するかどうかを確認するためにdbをチェックすることになっていますが、$db->has()
は、資格情報が正しくデータベースに存在する場合に間違ったユーザー名またはパスワードエラーを返します。
//process login form if submitted
if(isset($_POST['submit'])){
$user = $_POST['username'];
$password = $_POST['password'];
NB:これは、パスワードハッシュをチェックする間違った方法です。試してprint_r($hash);
を試してみると、ユーザーのパスワード入力から生成されたハッシュがdbに格納されたハッシュと決して一致しないことに気付くでしょう。
// check that the hashed password match and query the db.
$hash = password_hash($password, PASSWORD_BCRYPT);
$db->where("username", $user);
$db->where("password", password_verify($password, $hash));
$db->get('members');
if($db->has('members')){
$success[] = "You are now logged in";
$_SESSION['username'] = $user;
header('refresh:5; url=dashboard.php');
} else {
$error[] = "Wrong username or password";
}
EDIT:
私は、テストページを作りましたし、正常に動作するようです。コメントで示唆されているように、私は最初にデータベースに照会してユーザー名が存在するかどうかを確認した後、照会が実行された後、パスワードとユーザー名が正しいかどうかを確認する2つの変数を作成しました。
if(isset($_POST['test'])){
$cols = Array ("username","password");
$db->where('username', $_POST['username']);
//execute the query
$results = $db->get("members", null, $cols);
// fetch the results and verify credentials for the login
if(!empty($results)){
foreach($results as $results){
$username = $results['username'];
$hashPwd = $results['password'];
}
$verifyPwd = password_verify($_POST['password'], $hashPwd);
if($_POST['username'] == $username and $verifyPwd == TRUE){
echo 'success';
#this print is used inly to verify if the query work print_r($results);
}
}else {
#this print is only to verify if the query work print_r($results);
echo 'error';
}
}
NB:コメントで報告したように 、私は編集で投稿した作業コードの最初のバージョンは、SQLインジェクション攻撃に対して潜在的に脆弱でした。
私はスクリプトを少し安全にするためにいくつかのセキュリティ機能を追加しました。以下のコードを参照してください。セキュリティを向上させるためのあらゆる提案が評価されます。
<?php
session_start();
ob_start();
require('includes/MysqliDb.php');
$db = new MysqliDb ('localhost', 'root', 'root', 'my_recordz');
//process login form if submitted
if(isset($_POST['submit'])){
//sanitize user input
$query = filter_var($_POST['username'], FILTER_SANITIZE_SPECIAL_CHARS);
filter_var($query, FILTER_SANITIZE_EMAIL);
$fields = array('username', 'password');
foreach($fields as $fieldname){
if(!isset($_POST[$fieldname]) || empty($_POST[$fieldname])) {
$error[] = 'Empty '.$fieldname.'<br/>';
}
}
if(!$error) {
$cols = Array ("email","username","password");
$db->escape($query);
NB:$db->escape()
機能はmysqli_real_escape_string()
のクラスラッパーです。私は$db->where()
と$db->orWhere()
を使用してdbにユーザ名または電子メールをチェックしました。これにより、ユーザはログイン用に両方を使用することができます。 $db->where()
のみを使用すると動作しません。
$db->where('username', $query);
$db->orWhere('email', $query);
$results = $db->get("members", null, $cols);
if(!empty($results)){
foreach($results as $results){
$username = $results['username'];
$usermail = $results['email'];
$hashPwd = $results['password'];
}
NB:これは私が、パスワードの正しい方法を確認する方法です。結果の配列から$hashPwd
変数をデータベースに格納されたハッシュされたパスワードに割り当てた後、password_verify()
を使用してハッシュと照合し、挿入されたパスワードが正しいかどうかを確認しました。 password_hash()
はログインスコープには必要ありません。
$verifyPwd = password_verify($_POST['password'], $hashPwd);
if($query == $username and $verifyPwd == TRUE){
$success[] = 'Login Success';
print_r($results);
}
elseif($query == $usermail and $verifyPwd == TRUE){
$success[] = 'Login Success';
print_r($results);
}else {
$error[] = 'Wrong username or email address';
print_r($results);
}
}else {
$error[] = 'Wrong username and/or password';
print_r($results);
}
}
}
ob_end_flush();
//include header template
require('layout/header.php');
?>
を使用しています。 –
@NigelRen 'password_verify()'と 'password_hash()'関数を使わずにコードを実行しようとしましたが、問題は残っています。正しい資格情報が確認されず、ユーザー/パスワードのエラーメッセージが表示されます。 – BrP
純粋にユーザー名に基づいてユーザーを取得し、password_verifyを使用して、使用したレコードの値をチェックしてください。 –