import datetime import os import sys sys.path.append(os.path.dirname(os.path.dirname(__file__))) import jwt from fastapi import FastAPI,APIRouter, HTTPException, Depends, Request,Header from fastapi import Depends, FastAPI, HTTPException, status from fastapi.security import HTTPBearer, HTTPAuthorizationCredentials from pydantic import BaseModel from fastapi.responses import JSONResponse from config import * from douyin.access_token import get_access_token from douyin.user_info import get_user_info from db.user import UserOAuthRepository,UserInfoRepository,UserOAuthToken from api.jwt import verify_jwt_token,get_uer_oauth_and_verify login_router = APIRouter() # code=676a1101ea02bc5dTaUVtKg8c5enYaGqB4dT 只能被使用一次,用完失效 # scopes=user_info,trial.whitelist 用户授权的范围 class ScanCode(BaseModel): code: str scopes: str class User(BaseModel): nickname: str avatar: str # 登录端点 @login_router.post("/login") async def login(data: ScanCode): logger.info(data) data = await get_access_token(data.code) if data.get("error_code") != 0: raise HTTPException(status_code=400, detail=data) db_manager = UserOAuthRepository() db_manager.add_or_update(data) # 计算过期时间戳(基于北京时间) expires_in = data.get("expires_in", 1296000) # expires_in = 15 expiration_time_utc = datetime.datetime.utcnow() + datetime.timedelta(seconds=expires_in) beijing_timezone_delta = datetime.timedelta(hours=8) # 北京时间是UTC+8 expiration_time_beijing = expiration_time_utc + beijing_timezone_delta exp = int(expiration_time_beijing.timestamp()) # 生成并返回 token,包含过期时间 payload = { "sub": data["open_id"], "exp": exp # 添加过期时间戳(北京时间)到 payload } account_token = jwt.encode(payload, SECRET_KEY, algorithm="HS256") logger.info(f"login success, expires_time:{datetime.datetime.fromtimestamp(exp).strftime('%Y-%m-%d %H:%M:%S') }, token:{account_token}") return {"token": account_token} @login_router.get("/user_info") async def user_info(db_user_oauth: UserOAuthToken = Depends(get_uer_oauth_and_verify)): info = await get_user_info(db_user_oauth.open_id, db_user_oauth.access_token) if info.get("error_code") != 0: raise HTTPException(status_code=400, detail=info) return info # 受保护资源示例 @login_router.get("/account") async def read_account(open_id: str = Depends(verify_jwt_token)): UserOAuthRepository().display_all_records() return {"message": "Account information", "open_id": open_id} # 在这里返回当前用户的信息 return {"nickname": current_user.username, "avatar": "https://p26.douyinpic.com/aweme/100x100/aweme-avatar/tos-cn-i-0813_66c4e34ae8834399bbf967c3d3c919db.jpeg?from=4010531038"} @login_router.get("/token") async def read_account(open_id: str = Depends(verify_jwt_token)): pass # 启动应用 def main(): pass if __name__ == "__main__": main()