首页 > 数据库 >FastApi-tortoise-jwt-mysql

FastApi-tortoise-jwt-mysql

时间:2024-05-11 09:41:22浏览次数:21  
标签:username return tortoise FastApi jwt token user password def

抽了半天时间学了一下fastapi,为了方便,代码没分结构。

import sys
import jwt
import uvicorn,asyncio,signal,os
from fastapi import FastAPI, HTTPException, Depends
from fastapi.security import OAuth2PasswordBearer, OAuth2PasswordRequestForm
from tortoise import fields
from tortoise.models import Model
from tortoise.contrib.pydantic import pydantic_model_creator
from tortoise.contrib.fastapi import register_tortoise
from fastapi import FastAPI, Request
from fastapi.security import HTTPBearer, HTTPAuthorizationCredentials
from fastapi.middleware.cors import CORSMiddleware

app = FastAPI()
async def startup_event():
    print("Application has started.")

async def shutdown_event():
     print("Application is shutting down.")

app.add_event_handler("startup", startup_event)
app.add_event_handler("shutdown", shutdown_event)

db_config = {
  'connections': {
    'default': {
      'engine': 'tortoise.backends.mysql',
      'credentials': {
        'host': 'localhost',
        'port': '3306',
        'user': 'root',
        'password': 'root',
        'database': 'fiber'
      }
    },
  },
  'apps': {
    'models': {
      'models': ['main'],
      'default_connection': 'default',  # 更新为数据库连接名称
    }
  }
}

register_tortoise(
  app,
  config=db_config,
  generate_schemas=False
)

# JWT验证中间件
async def jwt_middleware(request: Request, call_next):
    # 检查是否是登录接口
    if request.url.path == "/token":
        response = await call_next(request)
        return response
    http_bearer = HTTPBearer()
    credentials: HTTPAuthorizationCredentials = await http_bearer(request)
    token = credentials.credentials

    # 检查令牌是否存在
    if token is None:
        raise HTTPException(status_code=401, detail="Token missing")
    try:
        payload = jwt.decode(token, JWT_SECRET, algorithms=['HS256'])
        user = await User.get(id=payload.get('id'))
    except Exception:
        raise HTTPException(status_code=401, detail="Token invalid")
    # 将解析后的payload存储在请求的状态中
    request.state.payload = payload
    response = await call_next(request)
    return response

# 添加JWT验证中间件到应用程序
app.middleware("http")(jwt_middleware)
# 全局中间件,用于处理程序中的异常
@app.exception_handler(Exception)
async def handle_exceptions(request: Request, exc: Exception):
    # 在这里可以根据需要进行相应的异常处理逻辑
    # 例如记录日志、返回自定义的错误响应等
    return {
        "code": 500,
        "message": "Internal Server Error",
    }

# 添加CORS中间件
app.add_middleware(
    CORSMiddleware,
    allow_origins=["*"],
    allow_methods=["*"],
    allow_headers=["*"],
)

class User(Model):
    id = fields.IntField(pk=True,generated=True)
    username = fields.CharField(max_length=50, unique=True)
    password = fields.CharField(max_length=128)
    def __str__(self):
        return self.username
    class Meta:
        table = 'users'
    @classmethod
    def get_user(cls, username):
        return cls.get(username=username)

    # 这里没有真正校验pass
    def verify_password(self, password):
        return password == self.password

UserPydantic = pydantic_model_creator(User, name='User')
UserInPydantic = pydantic_model_creator(User, name='UserIn',exclude_readonly=True)

oauth2_sceheme = OAuth2PasswordBearer(tokenUrl="token")
JWT_SECRET = 'myeasypeasyjwtsecret'
# async def get_current_user(token: str = Depends(oauth2_sceheme)):
#     try:
#         payload = jwt.decode(token, JWT_SECRET, algorithms=['HS256'])
#         user = await User.get(id=payload.get('id'))
#     except:
#         raise HTTPException(
#             status_code=401,
#             detail='Invalid username or password'
#         )
#     return await UserPydantic.from_tortoise_orm(user)
async def authenticate_user(username: str, password: str):
    user = await User.get(username=username)
    if not user:
        return False
    if not user.verify_password(password):
        return False
    return user

# @app.post('/token')
# async def generate_token(form_data: OAuth2PasswordRequestForm = Depends()):
#     user = await authenticate_user(form_data.username, form_data.password)
#     if not user:
#         return {"Error": "Invalid username or password"}
#     user_obj = await UserPydantic.from_tortoise_orm(user)
#     token = jwt.encode(user_obj.dict(), JWT_SECRET)
#     return {
#         "access_token": token,
#         "token_type": "Bearer",
#     }

@app.post('/token')
async def generate_token(form_data: UserInPydantic):
    user = await authenticate_user(form_data.username, form_data.password)
    if not user:
        return {"Error": "Invalid username or password"}
    user_obj = await UserPydantic.from_tortoise_orm(user)
    token = jwt.encode(user_obj.dict(), JWT_SECRET)
    return {
        "access_token": token,
        "token_type": "Bearer",
    }

@app.post('/users')
async def create_user(user: UserInPydantic):
    try:
        user_obj = User(username=user.username, password=user.password) # 使用哈希密码
        await user_obj.save()
        return await UserPydantic.from_tortoise_orm(user_obj)
    except Exception as e:
        print(f"An error occurred while saving the user: {e}")
        raise HTTPException(status_code=500, detail="Internal server error")

# @app.get('/users/me')
# async def get_user(current_user: UserPydantic = Depends(get_current_user)):
#     return current_user
@app.get('/users/me')
async def get_user(request: Request):
    return request.state.payload


if __name__ == "__main__":
    try:
        # 程序主逻辑
        uvicorn.run('main:app', host="127.0.0.1", port=8000, reload=True)
    except KeyboardInterrupt:
        sys.exit(0)
        # 执行必要的清理工作
    else:
        # 程序正常退出
        print("Program exited normally")


标签:username,return,tortoise,FastApi,jwt,token,user,password,def
From: https://www.cnblogs.com/qcy-blog/p/18185785

相关文章

  • apisix~jwt-auth插件
    在网关开启jwt-auth插件之后,你的网关就具有了jwt解析和校验的功能,主要是校验jwttoken的有效性,包含过期时间和签名等。https://apisix.apache.org/docs/apisix/plugins/jwt-auth/支持的签名算法"HS256""HS512""RS256""ES256"如果使用非对称算法rs256和es256时,需要配置公......
  • Gateway、Shiro 和 JWT 三者的区别?
    Gateway、Shiro和JWT都是用于认证和授权的技术,但它们在功能、应用场景和实现方式上存在一些区别。1.功能Gateway:API网关,用于管理API的访问权限,并提供一些通用功能,例如负载均衡、熔断限流等。Shiro:ApacheShiro,是一个强大的权限框架,用于控制用户对系统的访问权限。JWT:J......
  • ollama + ollama web + fastapi app (langchain) demo
    ollama+ollamaweb+fastapiapp(langchain)demohttps://github.com/fanqingsong/ollama-dockerWelcometotheOllamaDockerComposeSetup!ThisprojectsimplifiesthedeploymentofOllamausingDockerCompose,makingiteasytorunOllamawithallitsd......
  • simple-jwt的简单使用
    【一】安装pipinstalldjangorestframework-simplejwt【二】配置#settings.pyINSTALLED_APPS=[ ...'rest_framework',#add'rest_framework_simplejwt',#add]REST_FRAMEWORK={'DEFAULT_PERMISSION_CLASSES......
  • [web]cookie session和token(jwt)
    cookie:用户登录后,服务器生成一个cookie返回,并要求浏览器set-cookie,存储一下,下次访问时带上cookie,即可区分用户cookie可以被篡改session:信息存储在服务端,客户端cookie中存一个sessionid服务端有额外的存储成本负载均衡需要考虑session共享查询session是查库操作,耗时高......
  • DRF之JWT认证
    DRF之JWT认证【一】JWTWT(JSONWebToken)是一种开放标准(RFC7519),用于在网络上传输声明的一种紧凑且自包含的方式。JWT可以使用HMAC算法或是使用RSA或ECDSA等公钥/私钥对进行签名。通常,它用于在身份提供者和服务之间传递被认证的用户身份信息,以便于在用户和服务之间安全地......
  • jwt的思路
    我们通常在项目中使用登录接口的时候,会利用jwt的token实现一个对其他接口的一个请求头这层的一个验证,那么如何去应用呢,正常来讲我们需要写出两个功能1.jwt基本的加密和解密2.jwt的一个拦截器,检验token请求头使用依赖jdk1.8仅需<dependency><......
  • 凭证管理揭秘:Cookie-Session 与 JWT 方案的对决
    概述在上一篇文章我们聊完了授权的过程,在服务器对客户端完成授权之后,服务器会给客户端颁发对应的凭证,客户端持有该凭证访问服务端,服务器便能知道你是谁,你有什么权限等信息。这一章我们具体聊聊常见的凭证管理技术有哪些。在软件架构中,关于凭证如何存储和传递,一直有两种不同的解......
  • 凭证管理揭秘:Cookie-Session 与 JWT 方案的对决
    概述在上一篇文章我们聊完了授权的过程,在服务器对客户端完成授权之后,服务器会给客户端颁发对应的凭证,客户端持有该凭证访问服务端,服务器便能知道你是谁,你有什么权限等信息。这一章我们具体聊聊常见的凭证管理技术有哪些。在软件架构中,关于凭证如何存储和传递,一直有两种不同的解......
  • DRF之jwt介绍与使用
    一、jwt介绍1、什么是jwtJWT(JSONWebToken)是一种用于在网络应用中传递信息的开放标准(RFC7519)。它通过在用户和服务器之间传递的信息生成具有一定结构的令牌,这些令牌可以袐用于身份验证和信息传递。它是一种前后端登陆认证的方案,区别于之前的cookie,session。2、JWT结构一个J......