feat: 首页展示最近生成的素材画廊

- 后端新增 GET /api/v1/assets 接口,返回已完成任务的素材列表(按创建时间倒序)
- 前端新增 AssetGallery 组件,网格展示素材缩略图、类型标签和提示词
- HomePage 中工程列表上方展示最近生成素材
This commit is contained in:
2026-05-25 21:02:03 +08:00
parent 5be74e3ce1
commit b88f9aaf03
6 changed files with 172 additions and 0 deletions
+52
View File
@@ -306,6 +306,58 @@ func getTaskDBID(ctx context.Context, taskID string) uint {
return task.ID
}
// RecentAssetItem 首页素材展示项。
type RecentAssetItem struct {
Key string `json:"key"`
URL string `json:"url"`
Format string `json:"format"`
Prompt string `json:"prompt"`
AssetType string `json:"assetType"`
TaskID string `json:"taskId"`
CreatedAt string `json:"createdAt"`
}
// GetRecentAssets 获取最近生成的素材列表(已完成任务的全部素材)。
func GetRecentAssets(c *gin.Context) {
limit := 20
var dbRows []struct {
Key string
URL string
Format string
Prompt string
AssetType string
TaskID string
ProjectID uint
CreatedAt string
}
db.GetDB().WithContext(c.Request.Context()).
Raw(`SELECT a.key, a.url, a.format, t.prompt, t.asset_type as asset_type,
t.external_id as task_id, t.project_id, t.created_at as created_at
FROM assets a
INNER JOIN tasks t ON a.task_id = t.id
WHERE t.status = 'completed'
ORDER BY a.created_at DESC
LIMIT ?`, limit).
Scan(&dbRows)
result := make([]RecentAssetItem, len(dbRows))
for i, r := range dbRows {
result[i] = RecentAssetItem{
Key: r.Key,
URL: storageSvc.GetSignedURL(r.Key),
Format: r.Format,
Prompt: r.Prompt,
AssetType: r.AssetType,
TaskID: r.TaskID,
CreatedAt: r.CreatedAt,
}
}
c.JSON(http.StatusOK, model.OK(result))
}
// toTaskResponse 转换任务响应格式。
func toTaskResponse(task *model.Task) model.TaskResponse {
return model.TaskResponse{