PDO PHP如果用户名存在,请将用户名增加1

时间:2014-02-11 06:44:01

标签: php

我从网上有这个登录和注册脚本。一切都很好。

目的: 用户输入的用户名只是字母表。如果输入的用户名在数据库中不存在,它将自动在用户名上添加数字1,例如user1。

假设数据库已经有user1,user2,user3。每当用户输入用户时,它将检查最后一个递增的数字是什么,在这种情况下,它是3,因此它将以user4的形式添加到数据库中。

问题: 当我尽可能多地学习PDO时,我仍然很难理解。另外,我不知道从哪里开始。

以下是我目前的工作代码:

if (isset($_POST['submit'])) {

    if(empty($_POST['username']) || empty($_POST['password'])){

        $errors[] = 'All fields are required.';

    }else if(!ctype_alpha($_POST['username'])){
        $errors[] = 'Please enter only alphabet letters.';
    }else{
        if ($users->user_exists($_POST['username']) === true) {
            $errors[] = 'That username already exists';
        }
    }

    if(empty($errors) === true){

        $username   = htmlentities($_POST['username']);
        $password   = $_POST['password'];

        $users->register($username, $password);
        header('Location: register.php?success');
        exit();
    }
}

public function user_exists($username) {

        $stmt = $this->db->prepare("SELECT COUNT(`id`) FROM `userinfo` WHERE `username`= ?");
        $stmt->bindValue(1, $username, PDO::PARAM_STR);

        try{

            $stmt->execute();
            $rows = $stmt->fetchColumn();

            if($rows == 1){
                return true;
            }else{
                return false;
            }

        } catch (PDOException $e){
            die($e->getMessage());
        }

    }

    public function register($username, $password){

        $password   = sha1($password);

        $stmt   = $this->db->prepare("INSERT INTO `userinfo` (`username`, `password`) VALUES (?, ?) ");

        $stmt->bindValue(1, $username, PDO::PARAM_STR);
        $stmt->bindValue(2, $password, PDO::PARAM_STR);

        try{
            $stmt->execute();

            // mail($email, 'Please activate your account', "Hello " . $username. ",\r\nThank you for registering with us. Please visit the link below so we can activate your account:\r\n\r\nhttp://www.example.com/activate.php?email=" . $email . "&email_code=" . $email_code . "\r\n\r\n-- Example team");
        }catch(PDOException $e){
            die($e->getMessage());
        }   
    }

那里有什么善良的灵魂可以帮助我吗?让我知道我应该从哪里开始,我该怎么办?或整个程序流程实现我的目标。

任何帮助将不胜感激!提前谢谢。

4 个答案:

答案 0 :(得分:1)

以下是如何更改函数以检查用户是否存在以及最后一个索引的示例。 它不是很漂亮但会完成工作,可能会指出正确的想法。

public function register($username, $password){

        $password   = sha1($password);

    //check if the user exists and find first posible free index
    $_username = $username;
    if($this->db->query("SELECT * FROM `userinfo` WHERE `username` = 'user' ")){
        $n = 1;
        $max_index = 20;
        while ($n < $max_index ) { //just to be safe
            $_username = $username . $n;
            if (!$this->db->query("SELECT * FROM `userinfo` WHERE `username` = '" . $_username . "' ")) {
                break;
            }
            $n++;
        }
        if($n == $max_index){
            die("Sorry ,there already (".$max_index.") entries of this username.");
        }
    }
    //continue as normal just use $_username in the final query

    $stmt   = $this->db->prepare("INSERT INTO `userinfo` (`username`, `password`) VALUES (?, ?) ");

    $stmt->bindValue(1, $_username, PDO::PARAM_STR);
    $stmt->bindValue(2, $password, PDO::PARAM_STR);

    try{
        $stmt->execute();

        // mail($email, 'Please activate your account', "Hello " . $username. ",\r\nThank you for registering with us. Please visit the link below so we can activate your account:\r\n\r\nhttp://www.example.com/activate.php?email=" . $email . "&email_code=" . $email_code . "\r\n\r\n-- Example team");
    }catch(PDOException $e){
        die($e->getMessage());
    }   
}

答案 1 :(得分:0)

首先,您必须添加一个Sql-Wildcard,例如%_ * meaning see here,以查找以“user”开头的所有用户名,并在“user”-string后面添加一个或多个charakter。目前,您只会获得与插入用户名匹配的用户名。 但是你可能会因使用错误的通配符而遇到麻烦,那么

SELECT COUNT(id) FROM userinfo LIKE username = user%;

将始终选择user1,user2,user3等用户名,但也包括userhorst ..

对于pdo,pdo可以帮助您保护系统免受sql注入。 prepare函数只向参数发送带有通配符的查询,这意味着它们将没有参数的语句发送到数据库。在此之后,使用bindValue函数将单个值发送到数据库。最后,你将完成声明。在此过程中,数据库可以检查每个已发送的无效符号值。

最后你必须检查你的if语句。只有当一个具有相同名称的用户在所有其他情况下(0,2,3,4,5,6,7)在数据库中时,您才会得到错误。但是你想要

if countUsers equal 0 then: 
     return false; 
else 
     return true;
fi

另一部分是您应该考虑使用sha1 - 哈希,还有更好的哈希来保护您的密码。

答案 2 :(得分:0)

您可以使用以下选项user*选择所有用户名:

SELECT username FROM `userinfo` WHERE username LIKE 'user%'

接下来,您应该使用asort对结果进行排序:

asort($array_of_usernames);

然后使用substrpreg_match获取用户名末尾的数字:

$number = substr($each_username, -1, 2) //within a foreach

增加数量然后插入数据库。

$new_username = "user" . $number++;

答案 3 :(得分:0)

感谢帮助人员!

以下是我目前的工作代码,我根据给出的帮助设法在这里调整:

public function register($username, $password){

        $stmt = $this->db->prepare("SELECT username FROM `userinfo` WHERE `username` LIKE :username");
        $parse_username = "%".$username."%";
        $stmt->bindValue(':username', $parse_username, PDO::PARAM_STR);
        $stmt ->execute();
        $user = $stmt->fetch();

        $n = 1;

        if($user){
            $db_username = $user["username"];

            $username_counter = preg_match("/".$username."(\d+)/", $db_username, $matches) ? (int)$matches[1] : NULL;

                while ($n < $username_counter ) { //just to be safe
                    $new_username = $username . $n;
                    if (!$user) {
                        break;
                    }
                    $n++;
                }
                if($n == $username_counter){
                    $n++;
                    $new_username = $username.$n;
                }
        }else if(!$user){
            $new_username = $username.$n;
        }

        $password   = sha1($password);

        $query  = $this->db->prepare("INSERT INTO `userinfo` (`username`, `password`) VALUES (?, ?) ");

        $query->bindValue(1, $new_username);
        $query->bindValue(2, $password);

        try{
            $query->execute();
            $_SESSION['new_username'] = $new_username;

            // mail($email, 'Please activate your account', "Hello " . $username. ",\r\nThank you for registering with us. Please visit the link below so we can activate your account:\r\n\r\nhttp://www.example.com/activate.php?email=" . $email . "&email_code=" . $email_code . "\r\n\r\n-- Example team");
        }catch(PDOException $e){
            die($e->getMessage());
        }   
    }

我不确定我的编码方式是最好的还是专业的,它只是基于我对流程的一点逻辑知识。如果有任何我可以改进或重写的领域,如果你愿意,可以帮助我。 =)