feat: 添加用户注册和个人信息管理接口

- 添加用户注册接口 POST /api/auth/register
- 添加获取用户信息接口 GET /api/user/profile
- 添加更新用户信息接口 PUT /api/user/profile
This commit is contained in:
zhanggangyong
2026-01-11 16:22:40 +00:00
parent 22bd9d812f
commit 726b4dd4c6
2 changed files with 192 additions and 5 deletions
+80
View File
@@ -26,6 +26,7 @@ from app.schemas import (
PasswordChangeRequest,
APIKeyInfo,
RegenerateAPIKeyResponse,
UserCreate,
)
from config import settings
@@ -408,3 +409,82 @@ async def regenerate_api_key(
}
)
@router.post("/register", response_model=SuccessResponse)
async def register(req: UserCreate, db: AsyncSession = Depends(get_db)):
"""
用户注册接口
允许用户自由注册,创建普通用户账户
"""
# 检查邮箱是否已存在
result = await db.execute(select(User).where(User.email == req.email))
existing_user = result.scalar_one_or_none()
if existing_user:
raise HTTPException(
status_code=status.HTTP_400_BAD_REQUEST,
detail="该邮箱已被注册"
)
# 检查用户名是否已存在(如果提供了username)
if req.username:
result = await db.execute(select(User).where(User.username == req.username))
existing_username = result.scalar_one_or_none()
if existing_username:
raise HTTPException(
status_code=status.HTTP_400_BAD_REQUEST,
detail="该用户名已被使用"
)
# 创建新用户
password_hash = get_password_hash(req.password)
username = req.username or req.email.split("@")[0]
name = req.full_name or username
new_user = User(
name=name,
email=req.email,
password_hash=password_hash,
hashed_password=password_hash, # 兼容字段
username=username,
full_name=req.full_name or name,
role="user", # 默认角色为普通用户
status="active",
is_active=True,
is_admin=False,
balance=0,
credit_limit=0,
eu_balance=0,
total_eu_consumed=0,
)
db.add(new_user)
await db.commit()
await db.refresh(new_user)
# 创建JWT token,自动登录
token = create_access_token(
data={
"sub": str(new_user.id),
"email": new_user.email,
"role": new_user.role,
"user_id": str(new_user.id),
}
)
return SuccessResponse(
data={
"token": token,
"refreshToken": token,
"user": {
"id": str(new_user.id),
"name": new_user.name,
"email": new_user.email,
"username": new_user.username,
"role": new_user.role,
}
},
message="注册成功"
)
+112 -5
View File
@@ -1273,7 +1273,8 @@ async def deploy_agent(
client = get_agent_manager_client()
# 生成实例名称
instance_name = f"{quota.template_name}-{str(user_id)[:8]}-{uuid.uuid4().hex[:6]}"
safe_template_name = quota.template_name.replace("_", "-")
instance_name = f"{safe_template_name}-{str(user_id)[:8]}-{uuid.uuid4().hex[:6]}"
# 准备环境变量(注入用户模型配置)
env_vars = {}
@@ -1313,9 +1314,9 @@ async def deploy_agent(
agent_config = AgentConfig(
user_id=str(user_id),
cpu_request=quota.cpu_per_pod or "100m",
cpu_limit=quota.cpu_per_pod or "500m",
cpu_limit="500m", # 固定 limit,避免与 request 相等
memory_request=quota.memory_per_pod or "128Mi",
memory_limit=quota.memory_per_pod or "512Mi",
memory_limit="512Mi", # 固定 limit,避免与 request 相等
replicas=req.instances, # 副本数量
)
@@ -2215,7 +2216,8 @@ async def deploy_platform_agent(
client = get_agent_manager_client()
# 生成实例名称
instance_name = f"{req.agentType}-{str(user_id)[:8]}-{uuid.uuid4().hex[:6]}"
safe_agent_type = req.agentType.replace("_", "-")
instance_name = f"{safe_agent_type}-{str(user_id)[:8]}-{uuid.uuid4().hex[:6]}"
# 准备环境变量(从用户的模型配置中注入)
env_vars = req.envOverrides or {}
@@ -2382,7 +2384,8 @@ async def use_platform_agent(
client = get_agent_manager_client()
# 生成实例名称
instance_name = f"{req.agentType}-{user_id[:8]}-{uuid.uuid4().hex[:6]}"
safe_agent_type = req.agentType.replace("_", "-")
instance_name = f"{safe_agent_type}-{user_id[:8]}-{uuid.uuid4().hex[:6]}"
# 创建平台 Agent 实例
agent_config = AgentConfig(
@@ -3304,3 +3307,107 @@ async def get_my_agent_billing_history(
"records": data,
}
)
@router.get("/profile", response_model=SuccessResponse)
async def get_user_profile(
principal: dict = Depends(require_auth),
db: AsyncSession = Depends(get_db)
):
"""
获取当前用户信息
"""
user_id = principal.get("user_id")
# 查询用户
result = await db.execute(select(User).where(User.id == user_id))
user = result.scalar_one_or_none()
if not user:
raise HTTPException(
status_code=status.HTTP_404_NOT_FOUND,
detail="用户不存在"
)
# 返回用户信息
user_data = {
"id": str(user.id),
"username": user.username or (user.email.split("@")[0] if user.email else ""),
"name": user.name or user.full_name or "",
"full_name": user.full_name or user.name or "",
"email": user.email,
"role": user.role,
"company": getattr(user, "company", None), # 如果模型有company字段则返回,否则返回None
"created_at": user.created_at.isoformat() if user.created_at else None,
"updated_at": user.updated_at.isoformat() if user.updated_at else None,
}
return SuccessResponse(data=user_data)
@router.put("/profile", response_model=SuccessResponse)
async def update_user_profile(
req: dict,
principal: dict = Depends(require_auth),
db: AsyncSession = Depends(get_db)
):
"""
更新当前用户信息
请求体示例:
{
"username": "new_username",
"company": "公司名称" // 可选
}
"""
user_id = principal.get("user_id")
# 查询用户
result = await db.execute(select(User).where(User.id == user_id))
user = result.scalar_one_or_none()
if not user:
raise HTTPException(
status_code=status.HTTP_404_NOT_FOUND,
detail="用户不存在"
)
# 更新用户名
if "username" in req and req["username"]:
# 检查用户名是否已被其他用户使用
existing_user_result = await db.execute(
select(User).where(
and_(
User.username == req["username"],
User.id != user_id
)
)
)
existing_user = existing_user_result.scalar_one_or_none()
if existing_user:
raise HTTPException(
status_code=status.HTTP_400_BAD_REQUEST,
detail="用户名已被使用"
)
user.username = req["username"]
# 更新公司信息(如果模型支持)
if "company" in req:
if hasattr(user, "company"):
user.company = req["company"] if req["company"] else None
# 如果没有company字段,可以存储在permissions或其他JSON字段中
# 这里暂时忽略,如果后端需要支持,可以添加company字段到User模型
user.updated_at = datetime.utcnow()
await db.commit()
await db.refresh(user)
return SuccessResponse(
message="用户信息更新成功",
data={
"id": str(user.id),
"username": user.username,
"company": getattr(user, "company", None),
}
)