TV 채널 웹사이트: 사용자 인증

GitHub: https://github.com/Sokhavuth/TV-Channel
베르셀: https://khmerweb-tv-channel.vercel.app/login

사용자 인증은 해당 사용자가 데이터베이스에 등록되어 있는지 여부를 확인하고 검증하는 과정입니다. 그/그녀가 등록된 경우 웹사이트의 제한 구역에 들어갈 수 있도록 코드를 작성할 수 있습니다.

사용자가 인증되면 사용자 데이터를 Redis Enterprise 데이터베이스의 클라우드에 저장하기 위한 세션을 생성할 수 있습니다. 그리고 보안 문제를 위해 클라우드의 Redis 데이터베이스에 이 토큰을 저장하기 전에 JSON 웹 토큰(JWT)에서 사용자 데이터를 인코딩할 수 있습니다.

토큰에 대한 참조를 위해 Python 표준 라이브러리의 uuid 모듈을 사용하여 세션 ID를 생성하고 서명된 쿠키에 저장할 수 있습니다. 이렇게 하면 쿠키를 볼 수 있지만 수정할 수는 없습니다. 또한 JWT를 디코딩하고 사용자 데이터가 JWT로 인코딩되었는지 확인하기 위해 세션 ID를 사용하여 Redis 데이터베이스에서 JWT를 가져옴으로써 사용자가 인증되었는지 여부를 확인할 수 있습니다. 사용자가 인증된 경우 다시 로그인하지 않고 바로 제한 구역으로 이동할 수 있습니다.


# routes/frontend/login.py

from bottle import Bottle, get, post, redirect
from controllers.frontend.login import Login


app = Bottle()
login = Login()

@app.get("/")
def getLogin():
    if(login.checkLogged()):
        return redirect("/admin/post")
    else:
        return login.getPage()


@app.post("/")
def postLogin():
    return login.postItem()





# controllers/frontend/login.py

import config, copy, hashlib, jwt, uuid
from datetime import datetime, timezone, timedelta
from bottle import template, request, response, redirect
from models.user import User


class Login:
    def __init__(self):
        settings = copy.deepcopy(config.settings)
        self.setup = settings()
        self.redis = config.redis
        self.secret_key = config.secret_key
        self.user = User()


    def getPage(self):
        self.setup["pageTitle"] = "Log into Admin Page"
        self.setup["route"] = "/login"

        return template("base", data=self.setup)


    def checkLogged(self):
        sessionid = request.get_cookie('sessionid', secret=self.secret_key)
        encoded_jwt = self.redis.get(sessionid) 
        try:
            payload = jwt.decode(encoded_jwt, self.secret_key, algorithms=["HS256"])
            if(payload["user"]):
                return True
        except jwt.ExpiredSignatureError:
            return False


    def postItem(self):
        password = request.forms.getunicode('password')
        email = request.forms.getunicode('email')

        user = self.user.checkUser(email)

        if user:
            passw = hashlib.sha512(password.encode("utf-8") + user["salt"]).hexdigest()
            if(passw == user["password"]):
                self.setup["pageTitle"] = 'Post Page'

                payload = {"userid": user["id"], "role": user["role"]}
                exp = datetime.now(timezone.utc) + timedelta(seconds=60*60*24*15)

                myjwt = jwt.encode({"user": payload, "exp": exp }, self.secret_key, algorithm="HS256")
                sessionid = uuid.uuid4().hex
                self.redis.set(sessionid, myjwt)
                self.redis.expire(sessionid, 60*60*24*15)
                response.set_cookie('sessionid', sessionid, path='/', secret=self.secret_key)

                return redirect('/admin/post')
            else:
                self.setup["pageTitle"] = 'Log into Admin Page'
                self.setup['message'] = 'Your password is wrong!'
                self.setup['route'] = '/login'
                return template("base", data=self.setup)
        else:
            self.setup["pageTitle"] = 'Log into Admin Page'
            self.setup['message'] = 'Your Email is wrong!'
            self.setup['route'] = '/login'
            return template("base", data=self.setup)





# models/user.py

import config, hashlib, uuid
from bottle import request


class User:
    def __init__(self):
        self.db = config.conndb()


    def createRootUser(self):
        raw_salt = uuid.uuid4().hex
        password = "xxxxxxxxxxxxxxxxxxx".encode('utf-8')
        salt = raw_salt.encode('utf-8')
        hashed_password = hashlib.sha512(password + salt).hexdigest()

        user = { 
            "id": uuid.uuid4().hex, 
            "title": 'Guest',
            "content": '',
            "thumb": '',
            "date": '',
            "role": 'Guest',
            "email": '[email protected]',
            "salt": salt,
            "password": hashed_password,
        }

        self.db["users"].insert_one(user)


    def checkUser(self, email):
        return self.db["users"].find_one({ 'email': email })


좋은 웹페이지 즐겨찾기