如何更改班级PDO以进行正确的工作

问题描述 投票:0回答:1

我已经将与数据库的连接从mysqli重写为PDO。我的连接适用于准备好的语句。我的班级PDO看起来像这样:

  <?php

define('DB_HOST', 'xxx');
define('DB_NAME', 'xxx');
define('DB_USER', 'xxx');
define('DB_PASS', 'xxx');
define('DB_CHAR', 'xxx');

class DBController
{
    protected static $instance;
    protected $pdo;

    public function __construct() {
        $opt  = array(
            PDO::ATTR_ERRMODE            => PDO::ERRMODE_EXCEPTION,
            PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_OBJ,
            PDO::ATTR_EMULATE_PREPARES   => FALSE,
        );
        $dsn = 'mysql:host='.DB_HOST.';dbname='.DB_NAME.';charset='.DB_CHAR;
        $this->pdo = new PDO($dsn, DB_USER, DB_PASS, $opt);

    }

    // a classical static method to make it universally available
    public static function instance()
    {
        if (self::$instance === null)
        {
            self::$instance = new self;
        }
        return self::$instance;
    }

    // a proxy to native PDO methods
    public function __call($method, $args)
    {
        return call_user_func_array(array($this->pdo, $method), $args);
    }

    // a helper function to run prepared statements smoothly
    public function run($sql, $args = [])
    {
        if (!$args)
        {
            return $this->query($sql);
        }
        $stmt = $this->pdo->prepare($sql);
        $stmt->execute($args);
        return $stmt;
    }
    function insert($query) {
        if (!$args)
        {
            return $this->query($sql);
        }
        $stmt = $this->pdo->prepare($sql);
        $stmt->execute($args);
        return $stmt;
    }

    function update($query) {
        if (!$args)
        {
            return $this->query($sql);
        }
        $stmt = $this->pdo->prepare($sql);
        $stmt->execute($args);
        return $stmt;
    }
}

使用新的PDO类与数据库的连接很明显。但是,当我想以用户身份登录时,我得到了“无效登录名”。但是,登录名和密码正确。

我的班级Auth看起来像这样:

       <?php
require "DBController.class.php";

class Auth {

    protected $db;

    protected $data;

    public function __construct()
    {
        $this->db = DBController::instance();
    }

        function getMemberByUsername($username)
    {
        $this->data = $this->db->run("Select * from `members` where `member_name` = ?", array($username))->fetchAll(0);
    }


    function getTokenByUsername($username,$expired)
    {
        $this->data = $this->db->run("Select * from `tbl_token_auth` where `username` = ? and `is_expired` = ?", [$username, $expired])->fetchAll();
    }

    function markAsExpired($tokenId)
    {
        $expired = 1;
        $this->data = $this->db->run("UPDATE `tbl_token_auth` SET `is_expired` = ? WHERE id = ?", [$expired, $tokenId])->fetchAll();
    }

    function insertToken($username, $random_password_hash, $random_selector_hash, $expiry_date)
    {
        $this->data = $this->db->run("INSERT INTO `tbl_token_auth` (username, password_hash, selector_hash, expiry_date) values (?, ?, ?,?)", [$username, $random_password_hash, $random_selector_hash, $expiry_date])->fetchAll();
    }

}

下面的代码,与功能getMemberByUsername一起使用

if (! empty($_POST["login"])) {
$isAuthenticated = false;

$username = $_POST["member_name"];
$password = $_POST["member_password"];

$user = $auth->getMemberByUsername($username);
if (password_verify($password, $user[0]->member_password)) {
    $isAuthenticated = true;
}
if ($isAuthenticated) {
    $_SESSION["member_id"] = $user[0]["member_id"];

    // Set Auth Cookies if 'Remember Me' checked
    if (! empty($_POST["remember"])) {
        setcookie("member_login", $username, $cookie_expiration_time);

        $random_password = $util->getToken(16);
        setcookie("random_password", $random_password, $cookie_expiration_time);

        $random_selector = $util->getToken(32);
        setcookie("random_selector", $random_selector, $cookie_expiration_time);

        $random_password_hash = password_hash($random_password, PASSWORD_DEFAULT);
        $random_selector_hash = password_hash($random_selector, PASSWORD_DEFAULT);

        $expiry_date = date("Y-m-d H:i:s", $cookie_expiration_time);

        // mark existing token as expired
        $userToken = $auth->getTokenByUsername($username, 0);
        if (! empty($userToken[0]["id"])) {
            $auth->markAsExpired($userToken[0]["id"]);
        }
        // Insert new token
        $auth->insertToken($username, $random_password_hash, $random_selector_hash, $expiry_date);
    } else {
        $util->clearAuthCookie();
    }
    $util->redirect("dashboard.php");
} else {
    $message = "Invalid Login";
}

}

我做错了什么?

php oop pdo
1个回答
0
投票

您正在使用O::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_OBJ,因此fetchAll()返回一个对象数组,而不是数组。因此,您需要使用$user[0]->member_password从结果中获取密码。

if (password_verify($password, $user[0]->member_password)) {
    $isAuthenticated = true;
}
© www.soinside.com 2019 - 2024. All rights reserved.