package controllers import ( "encoding/json" "fmt" "io" "net/http" "path/filepath" "shudao-chat-go/models" "shudao-chat-go/utils" "strings" "time" "github.com/beego/beego/v2/server/web" ) type TotalController struct { web.Controller } // 随机返回5条推荐问题 func (c *TotalController) GetRecommendQuestion() { //获取limit数量 limit, _ := c.GetInt("limit") if limit == 0 { limit = 5 } var result []map[string]interface{} // 直接查询需要的字段,避免循环 models.DB.Model(&models.RecommendQuestion{}). Select("question"). Order("rand()"). Limit(limit).Where("is_deleted = ?", 0). Find(&result) c.Data["json"] = map[string]interface{}{ "statusCode": 200, "msg": "success", "data": result, } c.ServeJSON() } // 提交意见反馈 func (c *TotalController) SubmitFeedback() { var feedback models.FeedbackQuestion // 尝试解析JSON数据 if err := json.Unmarshal(c.Ctx.Input.RequestBody, &feedback); err != nil { c.Data["json"] = map[string]interface{}{ "statusCode": 400, "msg": "JSON解析失败: " + err.Error(), } c.ServeJSON() return } // 打印解析后的数据 fmt.Println("解析后的数据:", feedback) tx := models.DB.Begin() if err := tx.Create(&feedback).Error; err != nil { tx.Rollback() c.Data["json"] = map[string]interface{}{ "statusCode": 500, "msg": "fail", } c.ServeJSON() return } tx.Commit() c.Data["json"] = map[string]interface{}{ "statusCode": 200, "msg": "success", } c.ServeJSON() } // 返回政策文件 func (c *TotalController) GetPolicyFile() { policy_type, _ := c.GetInt("policy_type") search := c.GetString("search") page, _ := c.GetInt("page") pageSize, _ := c.GetInt("pageSize") var policyFile []models.PolicyFile offset := (page - 1) * pageSize if policy_type == 0 { models.DB.Model(&models.PolicyFile{}).Where("is_deleted = ? AND policy_name LIKE ?", 0, "%"+search+"%").Offset(offset).Limit(pageSize).Order("-updated_at").Find(&policyFile) } else { models.DB.Model(&models.PolicyFile{}).Where("is_deleted = ? AND policy_type = ? AND policy_name LIKE ?", 0, policy_type, "%"+search+"%").Offset(offset).Limit(pageSize).Order("-updated_at").Find(&policyFile) } // 将原始OSS URL转换为代理URL for i := range policyFile { if policyFile[i].PolicyFileUrl != "" { // 检查是否已经是代理URL格式 if !strings.Contains(policyFile[i].PolicyFileUrl, "/apiv1/oss/parse/?url=") { policyFile[i].PolicyFileUrl = utils.GetProxyURL(policyFile[i].PolicyFileUrl) } } } c.Data["json"] = map[string]interface{}{ "statusCode": 200, "msg": "success", "data": policyFile, } c.ServeJSON() } // 随机返回四条功能卡片 func (c *TotalController) GetFunctionCard() { //问题类型,0为AI问答,1为安全培训 functionType, _ := c.GetInt("function_type") var functionCard []models.FunctionCard models.DB.Model(&models.FunctionCard{}).Order("rand()").Limit(4).Where("function_type = ? AND is_deleted = ?", functionType, 0).Find(&functionCard) c.Data["json"] = map[string]interface{}{ "statusCode": 200, "msg": "success", "data": functionCard, } c.ServeJSON() } // 随机返回三条热点问题 func (c *TotalController) GetHotQuestion() { //问题类型,0为AI问答,1为安全培训 questionType, _ := c.GetInt("question_type") var hotQuestion []models.HotQuestion models.DB.Model(&models.HotQuestion{}).Order("rand()").Limit(4).Where("question_type = ? AND is_deleted = ?", questionType, 0).Find(&hotQuestion) c.Data["json"] = map[string]interface{}{ "statusCode": 200, "msg": "success", "data": hotQuestion, } c.ServeJSON() } type LikeAndDislikeRequest struct { ID uint `json:"id"` UserFeedback int `json:"user_feedback"` } // 点赞和踩 func (c *TotalController) LikeAndDislike() { var likeAndDislike LikeAndDislikeRequest if err := json.Unmarshal(c.Ctx.Input.RequestBody, &likeAndDislike); err != nil { c.Data["json"] = map[string]interface{}{ "statusCode": 400, "msg": "JSON解析失败: " + err.Error(), } c.ServeJSON() return } id := likeAndDislike.ID userFeedback := likeAndDislike.UserFeedback models.DB.Model(&models.AIMessage{}).Where("id = ?", id).Update("user_feedback", userFeedback) c.Data["json"] = map[string]interface{}{ "statusCode": 200, "msg": "success", } c.ServeJSON() } // 下载文件接口,支持从OSS链接下载文件并返回给前端 func (c *TotalController) GetPdfOssDownloadLink() { pdfOssDownloadLink := c.GetString("pdf_oss_download_link") customFileName := c.GetString("file_name") // 支持自定义文件名 // 验证URL是否为空 if pdfOssDownloadLink == "" { c.Data["json"] = map[string]interface{}{ "statusCode": 400, "msg": "下载链接不能为空", } c.ServeJSON() return } // 创建HTTP客户端,设置超时时间 client := &http.Client{ Timeout: 30 * time.Second, } // 发送GET请求下载文件 resp, err := client.Get(pdfOssDownloadLink) if err != nil { c.Data["json"] = map[string]interface{}{ "statusCode": 500, "msg": "下载文件失败: " + err.Error(), } c.ServeJSON() return } defer resp.Body.Close() // 检查HTTP状态码 if resp.StatusCode != http.StatusOK { c.Data["json"] = map[string]interface{}{ "statusCode": 500, "msg": "文件下载失败,状态码: " + fmt.Sprintf("%d", resp.StatusCode), } c.ServeJSON() return } // 从URL中提取文件名 fileName := filepath.Base(pdfOssDownloadLink) if fileName == "." || fileName == "/" { fileName = "download_file_" + fmt.Sprintf("%d", time.Now().Unix()) } // 如果提供了自定义文件名,使用自定义文件名 if customFileName != "" { fileName = customFileName } // 从Content-Disposition头中获取文件名(如果存在) if contentDisposition := resp.Header.Get("Content-Disposition"); contentDisposition != "" { if strings.Contains(contentDisposition, "filename=") { parts := strings.Split(contentDisposition, "filename=") if len(parts) > 1 { fileName = strings.Trim(parts[1], "\"") } } } // 获取文件大小 contentLength := resp.Header.Get("Content-Length") // 设置文件下载响应头 c.Ctx.Output.Header("Content-Type", "application/octet-stream") c.Ctx.Output.Header("Content-Disposition", fmt.Sprintf("attachment; filename=\"%s\"", fileName)) if contentLength != "" { c.Ctx.Output.Header("Content-Length", contentLength) } c.Ctx.Output.Header("Cache-Control", "no-cache") // 将文件内容写入响应(流式传输) _, err = io.Copy(c.Ctx.ResponseWriter, resp.Body) if err != nil { c.Data["json"] = map[string]interface{}{ "statusCode": 500, "msg": "文件传输失败: " + err.Error(), } c.ServeJSON() return } // 注意:文件下载成功后,响应已经通过io.Copy发送给客户端 // 此时不能再调用c.ServeJSON(),因为响应已经完成 } // 政策文件查看和下载查看次数+1 func (c *TotalController) GetPolicyFileViewAndDownloadCount() { // 定义请求结构体 type PolicyFileCountRequest struct { PolicyFileID int `json:"policy_file_id"` ActionType int `json:"action_type"` } var request PolicyFileCountRequest // 解析JSON请求体 if err := json.Unmarshal(c.Ctx.Input.RequestBody, &request); err != nil { c.Data["json"] = map[string]interface{}{ "statusCode": 400, "msg": "JSON解析失败: " + err.Error(), } c.ServeJSON() return } policyFileID := request.PolicyFileID actionType := request.ActionType fmt.Println("policyFileID", policyFileID) if policyFileID <= 0 { c.Data["json"] = map[string]interface{}{ "statusCode": 400, "msg": "政策文件ID不能为空或无效", } c.ServeJSON() return } fmt.Println("actionType", actionType) if actionType != 1 && actionType != 2 { c.Data["json"] = map[string]interface{}{ "statusCode": 400, "msg": "操作类型无效,1-查看,2-下载", } c.ServeJSON() return } // 检查政策文件是否存在 var policyFile models.PolicyFile if err := models.DB.Where("id = ? AND is_deleted = ?", policyFileID, 0).First(&policyFile).Error; err != nil { c.Data["json"] = map[string]interface{}{ "statusCode": 404, "msg": "政策文件不存在", } c.ServeJSON() return } // 更新查看次数 if err := models.DB.Model(&models.PolicyFile{}).Where("id = ?", policyFileID).Update("view_count", policyFile.ViewCount+1).Error; err != nil { c.Data["json"] = map[string]interface{}{ "statusCode": 500, "msg": "更新查看次数失败: " + err.Error(), } c.ServeJSON() return } // 返回成功响应 var actionText string if actionType == 1 { actionText = "查看" } else { actionText = "下载" } c.Data["json"] = map[string]interface{}{ "statusCode": 200, "msg": fmt.Sprintf("政策文件%s次数更新成功", actionText), "data": map[string]interface{}{ "policy_file_id": policyFileID, "action_type": actionType, "action_text": actionText, "view_count": policyFile.ViewCount + 1, }, } c.ServeJSON() } // GetUserDataID 从token中获取用户信息并返回用户数据 func (c *TotalController) GetUserDataID() { // 从token中获取用户信息 userInfo, err := utils.GetUserInfoFromContext(c.Ctx.Input.GetData("userInfo")) if err != nil { c.Data["json"] = map[string]interface{}{ "statusCode": 401, "msg": "获取用户信息失败: " + err.Error(), } c.ServeJSON() return } accountID := userInfo.AccountID if accountID == "" { c.Data["json"] = map[string]interface{}{ "statusCode": 400, "msg": "account_id不能为空", } c.ServeJSON() return } // 查询用户数据 var userData models.UserData if err := models.DB.Where("accountID = ?", accountID).First(&userData).Error; err != nil { c.Data["json"] = map[string]interface{}{ "statusCode": 404, "msg": "未找到对应的用户数据", } c.ServeJSON() return } // 返回主键id c.Data["json"] = map[string]interface{}{ "statusCode": 200, "msg": "success", "data": map[string]interface{}{ "id": userData.ID, }, } c.ServeJSON() }