Files
2026-10-27 16:44:55 +08:00

605 lines
22 KiB
Go

package web_playlet
import (
"videoweb/pub/common"
"videoweb/pub/common/srvdef"
"videoweb/web/api/proto"
"videoweb/web/service/srv_mediaresource"
"videoweb/web/service/srv_playlet"
"github.com/gin-gonic/gin"
)
// List web端短剧列表
// @Tags web短剧相关接口
// @Summary web端短剧列表
// @Description 分页查询短剧列表
// @Accept json
// @Produce json
// @Param params query proto.PlayletListReq true "短剧列表请求"
// @Success 200 {object} proto.PlayletListPageResp "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/list [get]
func List(ctx *gin.Context) {
var req proto.PlayletListReq
if err := ctx.ShouldBindQuery(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
resp, err := srv_playlet.ListPlaylet(ctx, &req)
if err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, resp)
}
// Add web端新增短剧
// @Tags web短剧相关接口
// @Summary web端新增短剧
// @Accept json
// @Produce json
// @Param params body proto.PlayletAddReq true "新增短剧请求"
// @Success 200 {object} proto.PlayletAddResp "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/add [post]
func Add(ctx *gin.Context) {
var req proto.PlayletAddReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
resp, err := srv_playlet.AddPlaylet(ctx, &req)
if err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, resp)
}
// Update web端更新短剧
// @Tags web短剧相关接口
// @Summary web端更新短剧
// @Accept json
// @Produce json
// @Param params body proto.PlayletUpdateReq true "更新短剧请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/update [post]
func Update(ctx *gin.Context) {
var req proto.PlayletUpdateReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.UpdatePlaylet(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// Del web端单/批量物理删除短剧
// @Tags web短剧相关接口
// @Summary web端单/批量物理删除短剧
// @Description 根据短剧ID集合物理删除 playlet 与 playlet_chapter 记录;不删除点赞、收藏、评论、观看记录、解锁记录和支付流水
// @Accept json
// @Produce json
// @Param params body proto.PlayletDelReq true "单/批量删除短剧请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/del [post]
func Del(ctx *gin.Context) {
var req proto.PlayletDelReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.DelPlaylet(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// SetStatus web端单/批量设置短剧上下架
// @Tags web短剧相关接口
// @Summary web端单/批量设置短剧上下架 --by 王鸣
// @Description 根据短剧ID集合批量更新 playlet 集合 status 字段,传1个ID表示单条设置,传多个ID表示批量设置
// @Accept json
// @Produce json
// @Param params body proto.PlayletStatusSetReq true "单/批量设置短剧上下架请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/status/set [post]
func SetStatus(ctx *gin.Context) {
var req proto.PlayletStatusSetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.SetPlayletStatus(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// FillOnlineAt web端临时回填已上架但上架时间为空的短剧
// @Tags web短剧相关接口
// @Summary 临时回填空上架时间
// @Description 将已上架且上架时间为空的短剧,上架时间设置为该条修改时间
// @Accept json
// @Produce json
// @Success 200 {object} proto.PlayletOnlineAtFillResp "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/online-at/fill [post]
func FillOnlineAt(ctx *gin.Context) {
resp, err := srv_playlet.FillEmptyPlayletOnlineAt(ctx)
if err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, resp)
}
// SetRecommend web端单/批量设置短剧是否推荐
// @Tags web短剧相关接口
// @Summary web端单/批量设置短剧是否推荐 --by 王鸣
// @Description 根据短剧ID集合批量更新 playlet 集合 isRecommend 字段,传1个ID表示单条设置,传多个ID表示批量设置
// @Accept json
// @Produce json
// @Param params body proto.PlayletRecommendSetReq true "单/批量设置短剧是否推荐请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/recommend/set [post]
func SetRecommend(ctx *gin.Context) {
var req proto.PlayletRecommendSetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.SetPlayletRecommend(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// SetFeatured web端单/批量设置短剧是否爆剧
// @Tags web短剧相关接口
// @Summary web端单/批量设置短剧是否爆剧 --by 王鸣
// @Description 根据短剧ID集合批量更新 playlet 集合 isFeatured 字段,传1个ID表示单条设置,传多个ID表示批量设置
// @Accept json
// @Produce json
// @Param params body proto.PlayletFeaturedSetReq true "单/批量设置短剧是否爆剧请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/featured/set [post]
func SetFeatured(ctx *gin.Context) {
var req proto.PlayletFeaturedSetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.SetPlayletFeatured(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// SetOperateType web端单/批量设置短剧运营类型
// @Tags web短剧相关接口
// @Summary web端单/批量设置短剧运营类型
// @Description 根据短剧ID集合批量更新 playlet 集合 operateType 字段,1-短剧 2-漫剧
// @Accept json
// @Produce json
// @Param params body proto.PlayletOperateTypeSetReq true "单/批量设置短剧运营类型请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/operate-type/set [post]
func SetOperateType(ctx *gin.Context) {
var req proto.PlayletOperateTypeSetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.SetPlayletOperateType(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// SetBanner web端单/批量设置短剧是否显示在首页banner
// @Tags web短剧相关接口
// @Summary web端单/批量设置短剧是否显示在首页banner --by 王鸣
// @Description 根据短剧ID集合批量更新 playlet 集合 showOnBanner 字段,传1个ID表示单条设置,传多个ID表示批量设置
// @Accept json
// @Produce json
// @Param params body proto.PlayletBannerSetReq true "单/批量设置短剧是否显示在首页banner请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/banner/set [post]
func SetBanner(ctx *gin.Context) {
var req proto.PlayletBannerSetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.SetPlayletBanner(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// SetTheme web端单/批量设置短剧题材
// @Tags web短剧相关接口
// @Summary web端单/批量设置短剧题材 --by 王鸣
// @Description 根据短剧ID集合批量更新 playlet 集合 themeIds 字段,传1个ID表示单条设置,传多个ID表示批量设置;themeIds 可设置多个题材
// @Accept json
// @Produce json
// @Param params body proto.PlayletThemeSetReq true "单/批量设置短剧题材请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/theme/set [post]
func SetTheme(ctx *gin.Context) {
var req proto.PlayletThemeSetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.SetPlayletTheme(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// SetTag web端单/批量设置短剧标签
// @Tags web短剧相关接口
// @Summary web端单/批量设置短剧标签 --by 王鸣
// @Description 根据短剧ID集合批量更新 playlet 集合 tagIds 字段,传1个ID表示单条设置,传多个ID表示批量设置;tagIds 可设置多个标签,传空数组表示清空标签
// @Accept json
// @Produce json
// @Param params body proto.PlayletTagSetReq true "单/批量设置短剧标签请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/tag/set [post]
func SetTag(ctx *gin.Context) {
var req proto.PlayletTagSetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.SetPlayletTag(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// SetCategory web端单/批量设置短剧分类
// @Tags web短剧相关接口
// @Summary web端单/批量设置短剧分类
// @Description 根据短剧ID集合批量更新 playlet 集合 categoryIds 字段,传1个ID表示单条设置,传多个ID表示批量设置;categoryIds 可为空,可设置多个分类,不传或空数组表示清空分类
// @Accept json
// @Produce json
// @Param params body proto.PlayletCategorySetReq true "单/批量设置短剧分类请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/category/set [post]
func SetCategory(ctx *gin.Context) {
var req proto.PlayletCategorySetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.SetPlayletCategory(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// SetVirtualLike web端单/批量设置短剧虚拟点赞数
// @Tags web短剧相关接口
// @Summary web端单/批量设置短剧虚拟点赞数 --by 王鸣
// @Description 根据短剧ID集合批量更新 playlet 集合 virtualCountLike 字段,每条短剧从最小值和最大值之间随机取不重复数值入库
// @Accept json
// @Produce json
// @Param params body proto.PlayletVirtualLikeSetReq true "单/批量随机设置短剧虚拟点赞数请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/like/virtual/set [post]
func SetVirtualLike(ctx *gin.Context) {
var req proto.PlayletVirtualLikeSetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.SetPlayletVirtualLike(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// ChapterList web端章节列表
// @Tags web短剧相关接口
// @Summary web端章节列表
// @Accept json
// @Produce json
// @Param params query proto.PlayletChapterListReq true "章节列表请求"
// @Success 200 {object} proto.PlayletChapterListPageResp "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/chapter/list [get]
func ChapterList(ctx *gin.Context) {
var req proto.PlayletChapterListReq
if err := ctx.ShouldBindQuery(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
resp, err := srv_playlet.ListPlayletChapter(ctx, &req)
if err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, resp)
}
// ChapterAdd web端新增章节
// @Tags web短剧相关接口
// @Summary web端新增章节
// @Accept json
// @Produce json
// @Param params body proto.PlayletChapterAddReq true "新增章节请求"
// @Success 200 {object} proto.PlayletChapterAddResp "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/chapter/add [post]
func ChapterAdd(ctx *gin.Context) {
var req proto.PlayletChapterAddReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
resp, err := srv_playlet.AddPlayletChapter(ctx, &req)
if err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, resp)
}
// ChapterUpdate web端更新章节
// @Tags web短剧相关接口
// @Summary web端更新章节
// @Accept json
// @Produce json
// @Param params body proto.PlayletChapterUpdateReq true "更新章节请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/chapter/update [post]
func ChapterUpdate(ctx *gin.Context) {
var req proto.PlayletChapterUpdateReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.UpdatePlayletChapter(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// ChapterDel web端单/批量删除章节
// @Tags web短剧相关接口
// @Summary web端单/批量删除章节
// @Description 根据章节ID集合删除 playlet_chapter 记录,传1个ID表示单条删除,传多个ID表示批量删除;同时清理该剧集的点赞、收藏、解锁记录
// @Accept json
// @Produce json
// @Param params body proto.PlayletChapterDelReq true "单/批量删除章节请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/chapter/del [post]
func ChapterDel(ctx *gin.Context) {
var req proto.PlayletChapterDelReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.DelPlayletChapter(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// ChapterFillStatus web端回填历史剧集上架状态
// @Tags web短剧相关接口
// @Summary 回填历史剧集为上架
// @Description 将未写 status 字段的历史剧集设为上架,发版后调用一次
// @Accept json
// @Produce json
// @Success 200 {object} proto.PlayletChapterStatusFillResp "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/chapter/status/fill [post]
func ChapterFillStatus(ctx *gin.Context) {
resp, err := srv_playlet.FillPlayletChapterStatusUp(ctx)
if err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, resp)
}
// ChapterSetStatus web端单/批量设置章节上架状态
// @Tags web短剧相关接口
// @Summary web端单/批量设置章节上架状态 --by 王鸣
// @Description 根据章节ID集合批量更新 playlet_chapter 集合 status 字段,传1个ID表示单条设置,传多个ID表示批量设置
// @Accept json
// @Produce json
// @Param params body proto.PlayletChapterStatusSetReq true "单/批量设置章节上架状态请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/chapter/status/set [post]
func ChapterSetStatus(ctx *gin.Context) {
var req proto.PlayletChapterStatusSetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.SetPlayletChapterStatus(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// ChapterSetPayType web端单/批量设置章节支付方式
// @Tags web短剧相关接口
// @Summary web端单/批量设置章节支付方式 --by 王鸣
// @Description 根据章节ID集合批量更新 playlet_chapter 集合 payType 字段,传1个ID表示单条设置,传多个ID表示批量设置
// @Accept json
// @Produce json
// @Param params body proto.PlayletChapterPayTypeSetReq true "单/批量设置章节支付方式请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/chapter/pay-type/set [post]
func ChapterSetPayType(ctx *gin.Context) {
var req proto.PlayletChapterPayTypeSetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.SetPlayletChapterPayType(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// ChapterSync web端手动同步短剧剧集
// @Tags web短剧相关接口
// @Summary web端手动单/批量同步短剧剧集 --by 王鸣
// @Description 根据短剧ID集合从媒资中心同步新增剧集,playletIds传1个表示单条同步,传多个表示批量同步,允许已完结短剧补集或修正状态
// @Accept json
// @Produce json
// @Param params body proto.PlayletChapterSyncReq true "手动单/批量同步短剧剧集请求"
// @Success 200 {object} proto.PlayletChapterSyncResp "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/chapter/sync [post]
func ChapterSync(ctx *gin.Context) {
var req proto.PlayletChapterSyncReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
resp, err := srv_mediaresource.SyncPlayletChapters(ctx, &req)
if err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, resp)
}
// SetPayType web端单/批量设置短剧默认支付方式
// @Tags web短剧相关接口
// @Summary web端单/批量设置短剧默认支付方式
// @Description 根据短剧ID集合批量更新 playlet 集合 payType/singleCoins;上架且连载中时,新增剧集默认沿用该设置
// @Accept json
// @Produce json
// @Param params body proto.PlayletPayTypeSetReq true "单/批量设置短剧默认支付方式请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/pay-type/set [post]
func SetPayType(ctx *gin.Context) {
var req proto.PlayletPayTypeSetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.SetPlayletPayType(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// ResetWatermark web端按短剧ID批量重置剧集水印
// @Tags web短剧相关接口
// @Summary web端按短剧ID批量重置剧集水印
// @Description 根据短剧ID集合,将其下全部剧集水印状态重置为未处理,并清空水印地址与 media 任务关联;原片地址不变,等待定时任务重新加水印
// @Accept json
// @Produce json
// @Param params body proto.PlayletWatermarkResetReq true "批量重置短剧水印请求"
// @Success 200 {string} string "成功"
// @Failure 400 {string} string "失败"
// @Security ApiKeyAuth
// @Router /api/web/playlet/watermark/reset [post]
func ResetWatermark(ctx *gin.Context) {
var req proto.PlayletWatermarkResetReq
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
if err := srv_playlet.ResetPlayletWatermark(ctx, &req); err != nil {
common.ServerJSON(ctx, err.Code, err.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, "")
}
// SyncSlug web端同步历史空 slug
// @Tags web短剧相关接口
// @Summary 同步历史空 slug
// @Description 为题材、标签、分类、短剧、首页配置中空的 slug 按 SEO 关键词或名称自动生成。可重复调用,hasMore 为 true 时继续请求。
// @Accept json
// @Produce json
// @Param param body proto.PlayletSlugSyncReq false "同步参数"
// @Success 200 {object} proto.PlayletSlugSyncResp "成功"
// @Failure 400 {string} string "参数错误"
// @Security ApiKeyAuth
// @Router /api/web/playlet/slug/sync [POST]
func SyncSlug(ctx *gin.Context) {
var req proto.PlayletSlugSyncReq
if ctx.Request.ContentLength > 0 {
if err := ctx.ShouldBindJSON(&req); err != nil {
common.ServerJSON(ctx, srvdef.ErrParamError, nil)
return
}
}
resp, serr := srv_playlet.SyncEmptySlugs(ctx, &req)
if serr != nil {
common.ServerJSON(ctx, serr.Code, serr.Tips)
return
}
common.ServerJSON(ctx, srvdef.Success, resp)
}