首页 > 解决方案 > 如何防止使用现有用户名注册?

问题描述

我正在尝试使用 Python 创建一个论坛应用程序。我的登录功能:

uname = username_const.get()
pword = password_const.get()

# this will delete the entry after login button is pressed
username.delete(0, END)
password.delete(0, END)

conn = sqlite3.connect('users_info.db')
c = conn.cursor()
c.execute("SELECT username, password FROM users")
account_list = c.fetchall()
flag = True
for account in account_list:
    if uname == account[0] and pword == account[1]:
        raise_frame(exsisting_account_frame)  # allow the user to log into his account
        flag = False
    elif uname == account[0]:
        password_not_recognised() #presents an error message
        flag = False
if flag:
    user_not_found() #presents an error message

我的注册功能(不允许已经存在/使用的用户名):

new_uname = newUsername_const.get()

conn = sqlite3.connect('users_info.db')
c = conn.cursor()

c.execute("SELECT username FROM users")
usernames = c.fetchall()

for user_name in usernames:
    if user_name == new_uname:
        username_already_exists()
        flag = False
        break
    else:
        flag = True

if flag:
    new_fname = name_const.get()
    new_mail = mail_const.get()
    new_uname = newUsername_const.get()
    new_pword = newPassword_const.get()

    FullName.delete(0, END)
    mailAccount.delete(0, END)
    newUsername.delete(0, END)
    newPassword.delete(0, END)

    conn = sqlite3.connect('users_info.db')
    c = conn.cursor()
    c.execute("INSERT INTO users (fullname, mail, username, password) VALUES(?,?,?,?)",
              (new_fname, new_mail, new_uname, new_pword))
    raise_frame(new_account_frame)
    conn.commit()

登录功能有效,但注册功能仍然允许使用用户名。我该如何解决?

标签: pythondatabasesqliteauthentication

解决方案


“……我要怎么修??

在列上定义UNIQUE约束:username

CREATE TABLE users (
    id          INTEGER PRIMARY KEY,
    regdate     TEXT            NOT NULL    DEFAULT CURRENT_TIMESTAMP,
    fullname    TEXT,
    mail        TEXT    UNIQUE  NOT NULL,
    username    TEXT    UNIQUE  NOT NULL,
    password    TEXT            NOT NULL
);

SQLite 现在为包含已经存在的用户名(和/或电子邮件地址)的语句返回约束违反错误INSERT(数据完整性应该由数据库而不是应用程序强制执行)。更多信息(单击table-constraint)。语句上的跳过idregdateINSERT会为其分配默认值。

“......注册功能仍然允许使用保存在数据库中的帐户注册应用程序......

查询现有用户名,例如:

SELECT count(*) FROM users WHERE username = 'already_taken_username_here';

返回单个记录,单个字段,包含01(不需要for-loop,也不需要flag变量)。

考虑存储password为哈希(而不是纯文本)。在与数据库记录进行比较之前,哈希密码输入(登录时)。


推荐阅读