feat: 新增客片案例与团队共创模块,重构玩法与配置
- 新增客片案例全流程功能,包含前台页面、管理端配置、后端API、数据库迁移与文档 - 新增团队共创详情页面与对应接口 - 重构玩法模块:将静态playData替换为动态API获取,拆分类型定义到playTypes.ts - 优化vite构建配置与环境变量处理,调整详情页操作栏文案 - 更新全量相关文档与配图,新增客片案例、团队共创API文档 - 新增测试用例,完善数据归一化逻辑 - 调整路由配置与环境变量示例文件
This commit is contained in:
1 parent
cda8069630
commit
7ba92f3c5d
76 files changed
+7970
-137
No files matched your search
@@ -1,11 +1,21 @@
|
||||
from fastapi import APIRouter, Depends, HTTPException, status
|
||||
from sqlalchemy import select
|
||||
from sqlalchemy.orm import Session
|
||||
from sqlalchemy.orm import Session, selectinload
|
||||
from .shared import site_config
|
||||
from ..auth import create_customer_token, require_customer
|
||||
from ..database import get_db
|
||||
from ..models import Customer, Lead
|
||||
from ..models import ConciergeAdvisor, Customer, HomeExperience, HomeTeamBuilding, HomeWanfaRecommendation, HomeWildArchive, Lead, WanfaCategory
|
||||
from ..schemas import LeadCreateIn, PhoneLoginIn
|
||||
from ..serializers import (
|
||||
public_concierge_advisor_dict,
|
||||
public_home_experience_dict,
|
||||
public_home_team_building_dict,
|
||||
public_home_team_building_detail_dict,
|
||||
public_home_wanfa_recommendation_dict,
|
||||
public_home_wild_archive_detail_dict,
|
||||
public_home_wild_archive_dict,
|
||||
public_wanfa_category_dict,
|
||||
)
|
||||
from ..wechat import WechatApiError, WechatConfigError, exchange_phone_code
|
||||
|
||||
|
||||
@@ -33,6 +43,93 @@ def get_site_config(db: Session = Depends(get_db)):
|
||||
return site_config(db, active_only=True)
|
||||
|
||||
|
||||
@router.get("/api/public/wanfa/categories")
|
||||
def get_public_wanfa_categories(db: Session = Depends(get_db)):
|
||||
categories = db.scalars(
|
||||
select(WanfaCategory)
|
||||
.options(selectinload(WanfaCategory.routes))
|
||||
.order_by(WanfaCategory.sortOrder.asc())
|
||||
).all()
|
||||
return {"categories": [public_wanfa_category_dict(category) for category in categories]}
|
||||
|
||||
|
||||
@router.get("/api/public/concierge/advisors")
|
||||
def get_public_concierge_advisors(db: Session = Depends(get_db)):
|
||||
advisors = db.scalars(
|
||||
select(ConciergeAdvisor)
|
||||
.where(ConciergeAdvisor.isActive.is_(True))
|
||||
.order_by(ConciergeAdvisor.sortOrder.asc())
|
||||
).all()
|
||||
return {"advisors": [public_concierge_advisor_dict(advisor) for advisor in advisors]}
|
||||
|
||||
|
||||
@router.get("/api/public/home")
|
||||
def get_public_home(db: Session = Depends(get_db)):
|
||||
experiences = db.scalars(
|
||||
select(HomeExperience)
|
||||
.where(HomeExperience.isActive.is_(True))
|
||||
.order_by(HomeExperience.sortOrder.asc())
|
||||
).all()
|
||||
team_buildings = db.scalars(
|
||||
select(HomeTeamBuilding)
|
||||
.where(HomeTeamBuilding.isActive.is_(True))
|
||||
.order_by(HomeTeamBuilding.sortOrder.asc())
|
||||
).all()
|
||||
wild_archives = db.scalars(
|
||||
select(HomeWildArchive)
|
||||
.where(HomeWildArchive.isActive.is_(True))
|
||||
.order_by(HomeWildArchive.sortOrder.asc())
|
||||
).all()
|
||||
play_recommendations = db.scalars(
|
||||
select(HomeWanfaRecommendation)
|
||||
.options(selectinload(HomeWanfaRecommendation.category).selectinload(WanfaCategory.routes))
|
||||
.where(HomeWanfaRecommendation.isActive.is_(True))
|
||||
.order_by(HomeWanfaRecommendation.sortOrder.asc())
|
||||
).all()
|
||||
return {
|
||||
"experiences": [public_home_experience_dict(item) for item in experiences],
|
||||
"teamBuildings": [public_home_team_building_dict(item) for item in team_buildings],
|
||||
"wildArchives": [public_home_wild_archive_dict(item) for item in wild_archives],
|
||||
"playRecommendations": [public_home_wanfa_recommendation_dict(item) for item in play_recommendations],
|
||||
}
|
||||
|
||||
|
||||
@router.get("/api/public/home/team-buildings/{team_building_id}")
|
||||
def get_public_team_building(team_building_id: str, db: Session = Depends(get_db)):
|
||||
team_building = db.scalar(
|
||||
select(HomeTeamBuilding).where(
|
||||
HomeTeamBuilding.id == team_building_id,
|
||||
HomeTeamBuilding.isActive.is_(True),
|
||||
)
|
||||
)
|
||||
if not team_building:
|
||||
raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="团队共创不存在")
|
||||
return public_home_team_building_detail_dict(team_building)
|
||||
|
||||
|
||||
@router.get("/api/public/home/wild-archives")
|
||||
def list_public_wild_archives(db: Session = Depends(get_db)):
|
||||
archives = db.scalars(
|
||||
select(HomeWildArchive)
|
||||
.where(HomeWildArchive.isActive.is_(True))
|
||||
.order_by(HomeWildArchive.sortOrder.asc())
|
||||
).all()
|
||||
return {"items": [public_home_wild_archive_dict(item) for item in archives]}
|
||||
|
||||
|
||||
@router.get("/api/public/home/wild-archives/{archive_id}")
|
||||
def get_public_wild_archive(archive_id: str, db: Session = Depends(get_db)):
|
||||
archive = db.scalar(
|
||||
select(HomeWildArchive).where(
|
||||
HomeWildArchive.id == archive_id,
|
||||
HomeWildArchive.isActive.is_(True),
|
||||
)
|
||||
)
|
||||
if not archive:
|
||||
raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="客片案例不存在")
|
||||
return public_home_wild_archive_detail_dict(archive)
|
||||
|
||||
|
||||
@router.post("/api/public/auth/phone-login")
|
||||
def phone_login(body: PhoneLoginIn, db: Session = Depends(get_db)):
|
||||
try:
|
||||
|
||||
Reference in new issue
Block a user