Jelajahi Sumber

批量上传素材

xyxie 5 bulan lalu
induk
melakukan
c47b1ebd36

+ 148 - 48
controllers/material/material.go

@@ -9,18 +9,15 @@ import (
 	materialService "eta/eta_api/services/material"
 	"eta/eta_api/utils"
 	"fmt"
+	"github.com/h2non/filetype"
 	"github.com/rdlucklib/rdluck_tools/paging"
-	"io"
-	"os"
+	"io/ioutil"
 	"path"
-	"path/filepath"
+	"strconv"
 	"strings"
 	"time"
 )
 
-// versionSize 版本列表第一页数据约定是:3条
-var versionSize = 3
-
 // MaterialController 逻辑导图
 type MaterialController struct {
 	controllers.BaseAuthController
@@ -714,12 +711,13 @@ func (this *MaterialController) ClassifyMove() {
 	br.Msg = "移动成功"
 }
 
-// @Title ETA图表列表接口
-// @Description ETA图表列表接口
+// List
+// @Title 素材列表接口
+// @Description 素材列表接口
 // @Param   PageSize   query   int  true       "每页数据条数"
 // @Param   CurrentIndex   query   int  true       "当前页页码,从1开始"
-// @Param   ChartClassifyId   query   int  true       "分类id"
-// @Param   KeyWord   query   string  true       "搜索关键词"
+// @Param   ClassifyId   query   int  true       "分类id"
+// @Param   Keyword   query   string  true       "搜索关键词"
 // @Param   IsShowMe   query   bool  true       "是否只看我的,true、false"
 // @Success 200 {object} data_manage.ChartListResp
 // @router /list [get]
@@ -737,11 +735,11 @@ func (this *MaterialController) List() {
 		return
 	}
 
-	MaterialClassifyId, _ := this.GetInt("MaterialClassifyId")
+	classifyId, _ := this.GetInt("ClassifyId")
 
 	pageSize, _ := this.GetInt("PageSize")
 	currentIndex, _ := this.GetInt("CurrentIndex")
-	keyWord := this.GetString("KeyWord")
+	keyword := this.GetString("Keyword")
 
 	var total int
 	page := paging.GetPaging(currentIndex, pageSize, total)
@@ -758,18 +756,51 @@ func (this *MaterialController) List() {
 	var condition string
 	var pars []interface{}
 
-	if MaterialClassifyId > 0 {
-		MaterialClassifyId, err := material.GetMaterialClassify(MaterialClassifyId)
-		if err != nil && err.Error() != utils.ErrNoRow() {
-			br.Msg = "获取图表信息失败"
-			br.ErrMsg = "获取信息失败,GetChartClassify,Err:" + err.Error()
-			return
+	if classifyId <= 0 {
+		br.Msg = "请选择分类"
+		return
+	}
+	// 查询当前的分类
+	classifyInfo, err := material.GetMaterialClassifyById(classifyId)
+	if err != nil {
+		br.Msg = "分类不存在"
+		br.ErrMsg = "获取分类信息失败,Err:" + err.Error()
+		return
+	}
+	// 获取所有子分类
+	childList, e := material.GetMaterialClassifyByLevelPath(classifyInfo.LevelPath)
+	if e != nil {
+		err = fmt.Errorf("保存分类失败,Err:" + e.Error())
+		return
+	}
+	// 把原先的父级levePath,替换成最新的父级序列
+	classifyIdMap := make(map[string]struct{})
+	classifyIds := make([]string, 0)
+	childClassifyMap := make(map[int]*material.MaterialClassify)
+	for _, tmp := range childList {
+		childClassifyMap[tmp.ClassifyId] = tmp
+		//获取字符串前缀的位置
+		after, _ := strings.CutPrefix(tmp.LevelPath, classifyInfo.LevelPath)
+		fmt.Println("after", after)
+		// 拼接字符串
+		if after != "" {
+			ids := strings.Split(after, ",")
+			for _, v := range ids {
+				if _, ok := classifyIdMap[v]; !ok {
+					classifyIds = append(classifyIds, v)
+					classifyIdMap[v] = struct{}{}
+				}
+			}
 		}
-		condition += " AND sandbox_classify_id IN(" + MaterialClassifyId + ") "
-		//pars = append(pars, chartClassifyId)
 	}
-	if keyWord != "" {
-		condition += ` AND  ( name LIKE '%` + keyWord + `%' )`
+	classifyIds = append(classifyIds, strconv.Itoa(classifyId))
+	if len(classifyIds) > 0 {
+		condition += " AND classify_id IN(" + utils.GetOrmInReplace(len(classifyIds)) + ") "
+		pars = append(pars, classifyIds)
+	}
+
+	if keyword != "" {
+		condition += ` AND  ( material_name LIKE '%` + keyword + `%' )`
 	}
 
 	//只看我的
@@ -780,7 +811,6 @@ func (this *MaterialController) List() {
 	}
 
 	//获取图表信息
-	condition += ` AND is_delete = 0 `
 	list, err := material.GetMaterialListByCondition(condition, pars, startSize, pageSize)
 	if err != nil && err.Error() != utils.ErrNoRow() {
 		br.Success = true
@@ -790,13 +820,9 @@ func (this *MaterialController) List() {
 	}
 
 	for i, v := range list {
-		ids, err := material.GetMaterialAllParentByClassifyId(v.ClassifyId)
-		if err != nil {
-			br.Msg = "获取父级信息错误!"
-			br.ErrMsg = "获取父级信息错误,Err:" + err.Error()
-			return
+		if classifyTmp, ok := childClassifyMap[v.ClassifyId]; ok {
+			list[i].ParentIds = classifyTmp.LevelPath
 		}
-		list[i].ParentIds = ids
 	}
 	resp := new(material.MaterialListResp)
 	if list == nil || len(list) <= 0 || (err != nil && err.Error() == utils.ErrNoRow()) {
@@ -1046,30 +1072,48 @@ func (this *MaterialController) BatchAdd() {
 		br.Ret = 408
 		return
 	}
-	classifyId, _ := this.GetInt("ClassifyId", 0)
+	var req material.BatchAddMaterialReq
+	err := json.Unmarshal(this.Ctx.Input.RequestBody, &req)
+	if err != nil {
+		br.Msg = "参数解析异常!"
+		br.ErrMsg = "参数解析失败,Err:" + err.Error()
+		return
+	}
+	classifyId := req.ClassifyId
 	if classifyId <= 0 {
 		br.Msg = "请选择分类"
 		return
 	}
-	materialNames := this.GetStrings("MaterialNames")
+	materialNames := make([]string, 0)
+	for _, v := range req.MaterialList {
+		if v.MaterialName == "" {
+			br.Msg = "请填写图片名称"
+			return
+		}
+		if v.ImgUrl == "" {
+			br.Msg = "请上传图片"
+			return
+		}
+		materialNames = append(materialNames, v.MaterialName)
+	}
 	if len(materialNames) == 0 {
 		br.Msg = "请填写图片名称"
 		return
 	}
 
 	// 判断文件名是否已存在
-	count, err := material.GetMaterialCountByNames(materialNames)
-	if err != nil {
+	exist, e := material.GetMaterialByNames(materialNames)
+	if e != nil && e.Error() != utils.ErrNoRow() {
 		br.Msg = "获取失败"
 		br.ErrMsg = "获取数据失败,Err:" + err.Error()
 		return
 	}
-	if count > 0 {
-		br.Msg = "图片名称已存在,请重新填写"
+	if e == nil && exist.MaterialId > 0 {
+		br.Msg = fmt.Sprintf("图片名称:%s 已存在", exist.MaterialName)
 		return
 	}
 	// 获取表单中的所有文件
-	files, err := this.GetFiles("Files")
+	/*files, err := this.GetFiles("Files")
 	if err != nil {
 		br.Msg = "文件上传失败"
 		br.ErrMsg = "文件上传失败,Err:" + err.Error()
@@ -1083,15 +1127,6 @@ func (this *MaterialController) BatchAdd() {
 		br.Msg = "图片数量与名称数量不一致"
 		return
 	}
-	// 限制上传文件的大小(可选)
-	maxSize := int64(10 << 20) // 10MB
-	for _, file := range files {
-		if file.Size > maxSize {
-			br.Msg = "文件大小超过限制"
-			return
-		}
-	}
-
 	// 创建目标目录(如果不存在)
 	uploadDir := utils.STATIC_DIR + "hongze/" + time.Now().Format("20060102")
 	if err = os.MkdirAll(uploadDir, utils.DIR_MOD); err != nil {
@@ -1165,16 +1200,81 @@ func (this *MaterialController) BatchAdd() {
 
 		// 将文件保存到map中(这里主要是为了演示,实际使用中可能不需要)
 		fileUrlMap[materialNames[k]] = resourceUrl
-	}
+	}*/
 
-	err = materialService.BatchAddMaterial(fileUrlMap, classifyId, sysUser.AdminId, sysUser.AdminName)
+	err = materialService.BatchAddMaterial(req.MaterialList, classifyId, sysUser.AdminId, sysUser.AdminName)
 	if err != nil {
 		br.Msg = "文件上传失败"
 		br.ErrMsg = "文件上传失败,Err:" + err.Error()
 		return
 	}
-	msg := "上传成功"
+	msg := "添加成功"
 	br.Ret = 200
 	br.Success = true
 	br.Msg = msg
 }
+
+// Upload
+// @Title 上传素材
+// @Description 上传素材接口
+// @Param	request	body material.AddAndEditSandbox true "type json string"
+// @Success 200 {object} material.Material
+// @router /upload [post]
+func (this *MaterialController) Upload() {
+	br := new(models.BaseResponse).Init()
+	defer func() {
+		this.Data["json"] = br
+		this.ServeJSON()
+	}()
+	sysUser := this.SysUser
+	if sysUser == nil {
+		br.Msg = "请登录"
+		br.ErrMsg = "请登录,SysUser Is Empty"
+		br.Ret = 408
+		return
+	}
+
+	f, h, err := this.GetFile("file")
+	if err != nil {
+		br.Msg = "获取资源信息失败"
+		br.ErrMsg = "获取资源信息失败,Err:" + err.Error()
+		return
+	}
+	defer f.Close() //关闭上传文件
+
+	// 不依赖于文件扩展名检查文件格式
+	fileData, e := ioutil.ReadAll(f)
+	if e != nil {
+		br.Msg = "上传失败"
+		br.ErrMsg = "读取文件失败, Err: " + e.Error()
+		return
+	}
+	pass := filetype.IsImage(fileData)
+	if !pass {
+		br.Msg = "文件格式有误"
+		br.ErrMsg = "文件格式有误"
+		return
+	}
+	ext := path.Ext(h.Filename)
+	randStr := utils.GetRandStringNoSpecialChar(28)
+	fileName := randStr + ext
+
+	// 上传到阿里云
+	ossDir := utils.RESOURCE_DIR + "material_dir/"
+	savePath := ossDir + time.Now().Format("200601/20060102/") + fileName
+	// 上传文件
+	resourceUrl, err := services.CommonUploadToOssAndFileName(f, fileName, savePath)
+	if err != nil {
+		br.Msg = "文件上传失败"
+		br.ErrMsg = "文件上传失败,Err:" + err.Error()
+		return
+	}
+
+	resp := new(models.UploadImgResp)
+	resp.ResourceUrl = resourceUrl
+
+	br.Msg = "上传成功"
+	br.Ret = 200
+	br.Success = true
+	br.Data = resp
+}

+ 35 - 22
models/material/material.go

@@ -10,15 +10,15 @@ import (
 )
 
 type Material struct {
-	MaterialId   int       `orm:"column(material_id);pk" description:"素材id"`
-	MaterialName string    `description:"素材名称"`
-	ImgUrl       string    `description:"素材图片地址"`
-	SysUserId    int       `description:"作者id"`
-	SysUserName  string    `description:"作者名称"`
-	ModifyTime   time.Time `description:"修改时间"`
-	CreateTime   time.Time `description:"创建时间"`
-	ClassifyId   int       `description:"分类id"`
-	Sort         int       `description:"排序"`
+	MaterialId      int       `orm:"column(material_id);pk" description:"素材id"`
+	MaterialName    string    `description:"素材名称"`
+	ImgUrl          string    `description:"素材图片地址"`
+	SysUserId       int       `description:"作者id"`
+	SysUserRealName string    `description:"作者名称"`
+	ModifyTime      time.Time `description:"修改时间"`
+	CreateTime      time.Time `description:"创建时间"`
+	ClassifyId      int       `description:"分类id"`
+	Sort            int       `description:"排序"`
 }
 
 // Update 素材字段变更
@@ -70,13 +70,13 @@ func UpdateMaterial(materialInfo *Material, updateMaterialColumn []string) (err
 
 // MaterialListItem 素材推演列表数据
 type MaterialListItem struct {
-	MaterialId   int    `description:"素材id"`
-	MaterialName string `description:"素材名称"`
-	ImgUrl       string `description:"素材图片地址"`
-	ModifyTime   string `description:"修改时间"`
-	CreateTime   string `description:"创建时间"`
-	SysUserId    int    `description:"作者id"`
-	SysUserName  string `description:"作者名称"`
+	MaterialId      int    `description:"素材id"`
+	MaterialName    string `description:"素材名称"`
+	ImgUrl          string `description:"素材图片地址"`
+	ModifyTime      string `description:"修改时间"`
+	CreateTime      string `description:"创建时间"`
+	SysUserId       int    `description:"作者id"`
+	SysUserRealName string `description:"作者名称"`
 }
 
 // GetList 获取素材列表页
@@ -129,7 +129,7 @@ func CheckOpMaterialPermission(sysUser *system.Admin, createUserId int) (ok bool
 func GetMaterialInfoByAdminId(adminId int) (items []*MaterialClassifyItems, err error) {
 	o := orm.NewOrmUsingDB("rddp")
 	sql := ` SELECT material_id,classify_id,material_name AS classify_name,code,
-             sys_user_id,sys_user_name
+             sys_user_id,sys_user_real_name
             FROM material where sys_user_id = ? ORDER BY sort asc,create_time ASC `
 	_, err = o.Raw(sql, adminId).QueryRows(&items)
 	return
@@ -156,7 +156,9 @@ WHERE
 
 type MaterialListItems struct {
 	Material
-	ParentIds string
+	ModifyTime string `description:"修改时间"`
+	CreateTime string `description:"创建时间"`
+	ParentIds  string
 }
 
 func GetMaterialListByCondition(condition string, pars []interface{}, startSize, pageSize int) (item []*MaterialListItems, err error) {
@@ -165,7 +167,7 @@ func GetMaterialListByCondition(condition string, pars []interface{}, startSize,
 	if condition != "" {
 		sql += condition
 	}
-	sql += " ORDER BY create_time DESC LIMIT ?,? "
+	sql += " ORDER BY create_time DESC, material_id DESC LIMIT ?,? "
 	_, err = o.Raw(sql, pars, startSize, pageSize).QueryRows(&item)
 	return
 }
@@ -309,6 +311,17 @@ type AddAndEditMaterial struct {
 	ClassifyId   int    `description:"分类id"`
 }
 
+// BatchAddMaterialReq 批量添加素材的请求数据
+type BatchAddMaterialReq struct {
+	MaterialList []BatchAddMaterialItem
+	ClassifyId   int `description:"分类id"`
+}
+
+type BatchAddMaterialItem struct {
+	MaterialName string `description:"素材名称"`
+	ImgUrl       string `description:"素材图片地址"`
+}
+
 // DeleteMaterial 删除素材的请求数据
 type DeleteMaterial struct {
 	MaterialId int `description:"素材id"`
@@ -327,10 +340,10 @@ func GetMaterialInfoCountByClassifyIds(classifyIds []string) (count int, err err
 	return
 }
 
-func GetMaterialCountByNames(materialNames []string) (count int, err error) {
+func GetMaterialByNames(materialNames []string) (item *Material, err error) {
 	o := orm.NewOrmUsingDB("rddp")
-	sql := `SELECT COUNT(1) AS count FROM material WHERE material_name in(` + utils.GetOrmInReplace(len(materialNames)) + `)`
-	err = o.Raw(sql, materialNames).QueryRow(&count)
+	sql := `SELECT * FROM material WHERE material_name in (` + utils.GetOrmInReplace(len(materialNames)) + `) limit 1`
+	err = o.Raw(sql, materialNames).QueryRow(&item)
 	return
 }
 

+ 4 - 0
models/resource.go

@@ -57,3 +57,7 @@ type ImageSvgToPngResp struct {
 	Ret         int64  `json:"Ret"`
 	Success     bool   `json:"Success"`
 }
+
+type UploadImgResp struct {
+	ResourceUrl string `description:"资源地址"`
+}

+ 9 - 0
routers/commentsRouter.go

@@ -7468,6 +7468,15 @@ func init() {
             Filters: nil,
             Params: nil})
 
+    beego.GlobalControllerRouter["eta/eta_api/controllers/material:MaterialController"] = append(beego.GlobalControllerRouter["eta/eta_api/controllers/material:MaterialController"],
+        beego.ControllerComments{
+            Method: "Upload",
+            Router: `/upload`,
+            AllowHTTPMethods: []string{"post"},
+            MethodParams: param.Make(),
+            Filters: nil,
+            Params: nil})
+
     beego.GlobalControllerRouter["eta/eta_api/controllers/report_approve:ReportApproveController"] = append(beego.GlobalControllerRouter["eta/eta_api/controllers/report_approve:ReportApproveController"],
         beego.ControllerComments{
             Method: "Approve",

+ 35 - 0
services/file.go

@@ -267,3 +267,38 @@ func AddWatermarks(rs io.ReadSeeker, w io.Writer, selectedPages []string, wmList
 
 	return api.Write(ctx, w, conf)
 }
+
+// CommonUploadToOssAndFileName 通用上传文件
+func CommonUploadToOssAndFileName(fileMulti multipart.File, newFileName, savePath string) (resourceUrl string, err error) {
+	dateDir := time.Now().Format("20060102")
+	uploadDir := utils.STATIC_DIR + "hongze/" + dateDir
+	err = os.MkdirAll(uploadDir, utils.DIR_MOD)
+	if err != nil {
+		err = errors.New("存储目录创建失败,Err:" + err.Error())
+		return
+	}
+
+	//本地地址
+	fpath := uploadDir + "/" + newFileName
+	err = saveToFile(fileMulti, fpath)
+	if err != nil {
+		err = errors.New("文件上传失败,Err:" + err.Error())
+		return
+	}
+
+	ossClient := NewOssClient()
+	if ossClient == nil {
+		err = fmt.Errorf("初始化OSS服务失败")
+		return
+	}
+	resourceUrl, err = ossClient.UploadFile(newFileName, fpath, savePath)
+	if err != nil {
+		err = fmt.Errorf("文件上传失败, Err: %s", err.Error())
+		return
+	}
+
+	defer func() {
+		os.Remove(fpath)
+	}()
+	return
+}

+ 22 - 22
services/material/material.go

@@ -62,27 +62,27 @@ func GetMaterialClassifyListForMe(adminInfo system.Admin, resp *material.Materia
 	return
 }
 
-func BatchAddMaterial(materialMap map[string]string, classifyId, opUserId int, opUserName string) (err error) {
-	materialList := make([]*material.Material, 0)
+func BatchAddMaterial(materialList []material.BatchAddMaterialItem, classifyId, opUserId int, opUserName string) (err error) {
+	addList := make([]*material.Material, 0)
 	sort, err := material.GetMaterialMaxSort()
 	if err != nil {
 		return
 	}
-	for k, v := range materialMap {
+	for _, v := range materialList {
 		sort = sort + 1
-		materialList = append(materialList, &material.Material{
-			MaterialName: k,
-			ImgUrl:       v,
-			SysUserId:    opUserId,
-			SysUserName:  opUserName,
-			ModifyTime:   time.Now(),
-			CreateTime:   time.Now(),
-			ClassifyId:   classifyId,
-			Sort:         sort,
+		addList = append(addList, &material.Material{
+			MaterialName:    v.MaterialName,
+			ImgUrl:          v.ImgUrl,
+			SysUserId:       opUserId,
+			SysUserRealName: opUserName,
+			ModifyTime:      time.Now(),
+			CreateTime:      time.Now(),
+			ClassifyId:      classifyId,
+			Sort:            sort,
 		})
 	}
-	if len(materialList) > 0 {
-		err = material.AddMultiMaterial(materialList)
+	if len(addList) > 0 {
+		err = material.AddMultiMaterial(addList)
 	}
 	return
 }
@@ -92,14 +92,14 @@ func AddMaterial(req material.AddAndEditMaterial, opUserId int, opUserName strin
 	resp = new(material.MaterialSaveResp)
 	//素材主表信息
 	materialInfo := &material.Material{
-		MaterialName: utils.TrimStr(req.MaterialName),
-		ImgUrl:       utils.TrimStr(req.ImgUrl),
-		SysUserId:    opUserId,
-		SysUserName:  opUserName,
-		ModifyTime:   time.Now(),
-		CreateTime:   time.Now(),
-		ClassifyId:   req.ClassifyId,
-		Sort:         0,
+		MaterialName:    utils.TrimStr(req.MaterialName),
+		ImgUrl:          utils.TrimStr(req.ImgUrl),
+		SysUserId:       opUserId,
+		SysUserRealName: opUserName,
+		ModifyTime:      time.Now(),
+		CreateTime:      time.Now(),
+		ClassifyId:      req.ClassifyId,
+		Sort:            0,
 	}
 
 	//新增素材