package controllers import ( "archive/zip" "eta/eta_api/models" "eta/eta_api/services" "eta/eta_api/utils" "fmt" "github.com/kgiannakakis/mp3duration/src/mp3duration" "github.com/rdlucklib/rdluck_tools/http" "os" "path" "strconv" "strings" "time" ) // VoiceController 音频 type VoiceController struct { BaseAuthController } // Upload // @Title 音频上传 // @Description 音频上传接口 // @Param file query file true "文件" // @Param ReportId query int true "报告ID" // @Success Ret=200 上传成功 // @router /upload [post] func (this *VoiceController) Upload() { br := new(models.BaseResponse).Init() defer func() { this.Data["json"] = br this.ServeJSON() }() f, h, err := this.GetFile("file") if err != nil { br.Msg = "获取资源信息失败" br.ErrMsg = "获取资源信息失败,Err:" + err.Error() return } reportId, err := this.GetInt("ReportId") if err != nil { br.Msg = "报告id异常" br.ErrMsg = "报告id异常,Err:" + err.Error() return } reportInfo, err := models.GetReportByReportId(reportId) if err != nil { br.Msg = "获取报告信息失败" br.ErrMsg = "获取报告信息失败,Err:" + err.Error() return } ext := path.Ext(h.Filename) dateDir := time.Now().Format("20060102") uploadDir := utils.STATIC_DIR + "hongze/" + dateDir err = os.MkdirAll(uploadDir, utils.DIR_MOD) if err != nil { br.Msg = "存储目录创建失败" br.ErrMsg = "存储目录创建失败,Err:" + err.Error() return } randStr := utils.GetRandStringNoSpecialChar(28) fileName := randStr + ext fpath := uploadDir + "/" + fileName defer f.Close() //关闭上传文件 err = this.SaveToFile("file", fpath) if err != nil { br.Msg = "文件上传失败" br.ErrMsg = "文件上传失败,Err:" + err.Error() return } resourceUrl := `` //上传到阿里云 和 minio //if utils.ObjectStorageClient == "minio" { // resourceUrl, err = services.UploadAudioToMinIo(fileName, fpath) // if err != nil { // br.Msg = "文件上传失败" // br.ErrMsg = "文件上传失败,Err:" + err.Error() // return // } //} else { // resourceUrl, err = services.UploadAudioAliyun(fileName, fpath) // if err != nil { // br.Msg = "文件上传失败" // br.ErrMsg = "文件上传失败,Err:" + err.Error() // return // } //} ossClient := services.NewOssClient() if ossClient == nil { br.Msg = "上传失败" br.ErrMsg = "初始化OSS服务失败" return } resourceUrl, err = ossClient.UploadFile(fileName, fpath, "") if err != nil { br.Msg = "文件上传失败" br.ErrMsg = "文件上传失败,Err:" + err.Error() return } defer func() { os.Remove(fpath) }() item := new(models.Resource) item.ResourceUrl = resourceUrl item.ResourceType = 2 item.CreateTime = time.Now() newId, err := models.AddResource(item) if err != nil { br.Msg = "资源上传失败" br.ErrMsg = "资源上传失败,Err:" + err.Error() return } var playSeconds float64 playSeconds, err = mp3duration.Calculate(fpath) if playSeconds <= 0 { playSeconds, err = utils.GetVideoPlaySeconds(fpath) if err != nil { br.Msg = "获取音频时间失败" br.ErrMsg = "获取音频时间失败,Err:" + err.Error() return } } fileBody, err := os.ReadFile(fpath) videoSize := len(fileBody) sizeFloat := (float64(videoSize) / float64(1024)) / float64(1024) sizeStr := utils.SubFloatToFloatStr(sizeFloat, 2) // 修改报告的音频信息 { reportCreateTime, err := time.Parse(utils.FormatDateTime, reportInfo.CreateTime) if err != nil { br.Msg = "上传失败" br.ErrMsg = "上传失败,Err:" + err.Error() return } createTimeStr := reportCreateTime.Format("0102") videoName := reportInfo.Title + "(" + createTimeStr + ")" reportInfo.VideoUrl = resourceUrl reportInfo.VideoName = videoName reportInfo.VideoPlaySeconds = fmt.Sprint(playSeconds) reportInfo.VideoSize = sizeStr reportInfo.LastModifyAdminId = this.SysUser.AdminId reportInfo.LastModifyAdminName = this.SysUser.RealName reportInfo.VoiceGenerateType = 1 reportInfo.ModifyTime = time.Now() err = reportInfo.UpdateReport([]string{"VideoUrl", "VideoName", "VideoPlaySeconds", "VideoSize", "LastModifyAdminId", "LastModifyAdminName", "VoiceGenerateType", "ModifyTime"}) if err != nil { br.Msg = "上传失败" br.ErrMsg = "修改报告的音频信息失败,Err:" + err.Error() return } } resp := new(models.ResourceResp) resp.Id = newId resp.ResourceUrl = resourceUrl br.Msg = "上传成功" br.Ret = 200 br.Success = true br.Data = resp return } // VoiceCommonController 音频 type VoiceCommonController struct { BaseCommonController } // Download // @Title 音频下载 // @Description 音频下载接口 // @Param ReportId query int true "报告ID" // @Success Ret=200 下载成功 // @router /download [get] func (this *VoiceCommonController) Download() { br := new(models.BaseResponse).Init() defer func() { this.Data["json"] = br this.ServeJSON() }() reportId, err := this.GetInt("ReportId") if err != nil { br.Msg = "参数错误" br.ErrMsg = "获取,ReportId,Err:" + err.Error() return } reportInfo, err := models.GetReportById(reportId) if err != nil { br.Msg = "获取信息失败" br.ErrMsg = "获取信息失败,Err:" + err.Error() return } savePath, fileName, err, errMsg := services.DownloadVoice(reportInfo) // 如果生成了文件,那么就在退出的时候,删除该文件 if savePath != `` { defer func() { os.Remove(savePath) }() } if err != nil { br.Msg = errMsg br.ErrMsg = "下载失败,Err:" + err.Error() return } if savePath != `` { this.Ctx.Output.Download(savePath, fileName) } br.Ret = 200 br.Msg = "下载成功" br.Success = true return } //func (this *VoiceCommonController) Download() { // br := new(models.BaseResponse).Init() // defer func() { // this.Data["json"] = br // this.ServeJSON() // }() // reportId, err := this.GetInt("ReportId") // if err != nil { // br.Msg = "参数错误" // br.ErrMsg = "获取,ReportId,Err:" + err.Error() // return // } // report, err := models.GetReportById(reportId) // if err != nil { // br.Msg = "获取信息失败" // br.ErrMsg = "获取信息失败,Err:" + err.Error() // return // } // savePath := time.Now().Format(utils.FormatDateTimeUnSpace) + utils.GetRandString(5) + ".mp3" // fileBody, err := http.Get(report.VideoUrl) // if err != nil { // br.Msg = "获取信息失败" // br.ErrMsg = "获取信息失败,Err:" + err.Error() // return // } // err = file.SaveFile(fileBody, savePath) // if err != nil { // br.Msg = "保存信息失败" // br.ErrMsg = "保存信息失败,Err:" + err.Error() // return // } // fileName := report.VideoName + ".mp3" // this.Ctx.Output.Download(savePath, fileName) // defer func() { // os.Remove(savePath) // }() // br.Ret = 200 // br.Msg = "下载成功" // br.Success = true // return //} // ReportChapterDownload // @Title 报告章节列表音频下载 // @Description 音频下载接口 // @Param ChapterIds query string true "章节IDs" // @Success Ret=200 下载成功 // @router /report/download [get] func (this *VoiceCommonController) ReportChapterDownload() { br := new(models.BaseResponse).Init() defer func() { this.Data["json"] = br this.ServeJSON() }() strChapterIds := this.GetString("ChapterIds") if strChapterIds == "" { br.Msg = "参数错误" return } chapterIds := make([]int, 0) chapterIdArr := strings.Split(strChapterIds, ",") for _, v := range chapterIdArr { id, e := strconv.Atoi(v) if e != nil { br.Msg = "参数有误" br.ErrMsg = "章节ID有误, Err: " + e.Error() return } chapterIds = append(chapterIds, id) } if len(chapterIds) == 0 { br.Msg = "参数有误" return } videoList, err := models.GetReportChapterVideoListByChapterIds(chapterIds) if err != nil { br.Msg = "获取音频列表失败" br.ErrMsg = "获取音频列表失败, Err: " + err.Error() return } if len(videoList) > 0 { reportId := videoList[0].ReportId reportInfo, err := models.GetReportById(reportId) if err != nil { br.Msg = "报告信息有误" br.ErrMsg = "获取报告信息失败, Err: " + err.Error() return } // 创建zip zipName := time.Now().Format(utils.FormatDateTimeUnSpace) + utils.GetRandString(5) + ".zip" savePath := zipName zipFile, err := os.Create(zipName) if err != nil { return } zipWriter := zip.NewWriter(zipFile) // 生成zip过程中报错关闭 defer func() { if err != nil { zipWriter.Close() zipFile.Close() } os.Remove(savePath) }() // 获取音频,写入zip for i := 0; i < len(videoList); i++ { item := videoList[i] if item.VideoName == "" || item.VideoUrl == "" { continue } // 音频文件后缀 ext := path.Ext(item.VideoUrl) ioWriter, err := zipWriter.Create(fmt.Sprintf("%s%s", item.VideoName, ext)) if err != nil { if os.IsPermission(err) { fmt.Println("权限不足: ", err) return } return } var content []byte content, err = http.Get(item.VideoUrl) if err != nil { content = []byte("") } ioWriter.Write(content) } // 生成zip后关闭,否则下载文件会损坏 zipWriter.Close() zipFile.Close() this.Ctx.Output.Download(savePath, fmt.Sprintf("%s.zip", reportInfo.Title)) } br.Ret = 200 br.Msg = "下载成功" br.Success = true return }