158 lines
5.2 KiB
Go
158 lines
5.2 KiB
Go
|
package imageaudit
|
|||
|
|
|||
|
import (
|
|||
|
"fmt"
|
|||
|
"service/api/consts"
|
|||
|
imageauditproto "service/api/proto/imageaudit/proto"
|
|||
|
imageaudittaskproto "service/api/proto/imageaudittask/proto"
|
|||
|
"service/bizcommon/util"
|
|||
|
"service/dbstruct"
|
|||
|
"service/library/logger"
|
|||
|
|
|||
|
"github.com/gin-gonic/gin"
|
|||
|
goproto "google.golang.org/protobuf/proto"
|
|||
|
)
|
|||
|
|
|||
|
// 图像审核任务控制块
|
|||
|
// ActionId设计初衷:由于图像审核是定时任务触发的批量作业,如果在一次作业间隔有针对同一个图像媒体的多次更新,则会提交关于它的多次审核,需要配合乐观锁保证数据一致性
|
|||
|
type ImageAuditTaskControlBlock struct {
|
|||
|
// 静态元素
|
|||
|
ActionId string // 审核动作id号,由图像审核实体数据库四要素拼接而成,用于指示对数据库-表-单条数据-图像字段的审核动作
|
|||
|
ImageAuditTask *dbstruct.ImageAuditTask // 审核任务
|
|||
|
RollbackFunc func() error // 审核失败时的回退方法
|
|||
|
|
|||
|
// 操作对象
|
|||
|
Images []*dbstruct.MediaComponent // 被审核的图像序列
|
|||
|
|
|||
|
// 动态元素
|
|||
|
IsTaskPassed bool // 任务状态,仅当任务已确定完成,即已完成审核任务的分片数 = 审核任务分片数时,才有意义
|
|||
|
AuditedFragmentsNum int // 已完成审核任务的分片数
|
|||
|
IsGivingNoticeToBatch bool // 是否进行批处理
|
|||
|
}
|
|||
|
|
|||
|
// 新建图像审核任务块
|
|||
|
func NewImageAuditTaskControlBlock(task *dbstruct.ImageAuditTask, rollbackFunc func() error) (tcb *ImageAuditTaskControlBlock) {
|
|||
|
if task == nil || task.AuditedMedia == nil {
|
|||
|
return
|
|||
|
}
|
|||
|
fragmentNum := len(util.DerefInt64Slice(task.AuditedMedia.ImageIds))
|
|||
|
if fragmentNum == 0 {
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
task.BatchId = goproto.String(defaultImageAuditTaskScheduler.batchId)
|
|||
|
task.Status = goproto.Int64(consts.ImageAudit_Created)
|
|||
|
if fragmentNum == 1 {
|
|||
|
task.IsFragmented = goproto.Int64(0)
|
|||
|
task.FragmentsNum = goproto.Int64(1)
|
|||
|
} else {
|
|||
|
task.IsFragmented = goproto.Int64(1)
|
|||
|
task.FragmentsNum = goproto.Int64(int64(fragmentNum))
|
|||
|
}
|
|||
|
|
|||
|
tcb = &ImageAuditTaskControlBlock{
|
|||
|
ActionId: fmt.Sprintf("%v%v%v%v", util.DerefString(task.AssociativeDatabase), util.DerefString(task.AssociativeTableName),
|
|||
|
util.DerefInt64(task.AssociativeTableId), util.DerefString(task.AssociativeTableColumn)),
|
|||
|
ImageAuditTask: task,
|
|||
|
RollbackFunc: rollbackFunc,
|
|||
|
IsTaskPassed: true,
|
|||
|
AuditedFragmentsNum: 0,
|
|||
|
IsGivingNoticeToBatch: false,
|
|||
|
}
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
func AddTask(task *ImageAuditTaskControlBlock) {
|
|||
|
if err := task.Prepare(); err != nil {
|
|||
|
logger.Error("ImageAuditTaskPrepareException: %v", err)
|
|||
|
return
|
|||
|
}
|
|||
|
defaultImageAuditTaskScheduler.AddTask(task)
|
|||
|
}
|
|||
|
|
|||
|
// 将图像审核任务信息写入数据库,准备送审
|
|||
|
func (task *ImageAuditTaskControlBlock) Prepare() (err error) {
|
|||
|
|
|||
|
if task == nil {
|
|||
|
return fmt.Errorf("task is nil, check your input")
|
|||
|
}
|
|||
|
|
|||
|
// 1.写入图像审核表
|
|||
|
if util.DerefInt64(task.ImageAuditTask.IsFragmented) == 1 {
|
|||
|
if task.Images, err = prepareFragmentedImageAuditTask(task.ImageAuditTask); err != nil {
|
|||
|
return err
|
|||
|
}
|
|||
|
} else {
|
|||
|
if err := prepareNotFragmentedImageAuditTask(task.ImageAuditTask); err != nil {
|
|||
|
return err
|
|||
|
}
|
|||
|
task.Images = make([]*dbstruct.MediaComponent, 1)
|
|||
|
task.Images[0] = task.ImageAuditTask.AuditedMedia
|
|||
|
}
|
|||
|
|
|||
|
// 2.写入图像审核任务表
|
|||
|
if err := _DefaultImageAuditTask.OpCreate(&gin.Context{}, &imageaudittaskproto.OpCreateReq{
|
|||
|
ImageAuditTask: task.ImageAuditTask,
|
|||
|
}); err != nil {
|
|||
|
logger.Error("Imageaudittask OpCreate failed: %v", err)
|
|||
|
return err
|
|||
|
}
|
|||
|
|
|||
|
return nil
|
|||
|
}
|
|||
|
|
|||
|
// 根据任务信息,创建单个图片的图片审核,并存入数据库,返回images
|
|||
|
func prepareFragmentedImageAuditTask(task *dbstruct.ImageAuditTask) (images []*dbstruct.MediaComponent, err error) {
|
|||
|
ctx := &gin.Context{}
|
|||
|
|
|||
|
fragmentsNum := util.DerefInt64(task.FragmentsNum)
|
|||
|
images = make([]*dbstruct.MediaComponent, fragmentsNum)
|
|||
|
imageAudits := make([]*dbstruct.ImageAudit, fragmentsNum)
|
|||
|
|
|||
|
// 将媒体拆分为单个图像并存入图片审核表
|
|||
|
imageIds := util.DerefInt64Slice(task.AuditedMedia.ImageIds)
|
|||
|
for i, imageId := range imageIds {
|
|||
|
images[i] = &dbstruct.MediaComponent{
|
|||
|
ImageIds: util.Int64Slice([]int64{imageId}),
|
|||
|
}
|
|||
|
imageAudits[i] = &dbstruct.ImageAudit{
|
|||
|
AuditedMedia: images[i],
|
|||
|
BatchId: task.BatchId,
|
|||
|
Status: goproto.Int64(consts.ImageAudit_Created),
|
|||
|
}
|
|||
|
}
|
|||
|
if err = _DefaultImageAudit.OpCreateFragmentGroup(ctx, &imageauditproto.OpCreateBatchReq{
|
|||
|
ImageAudits: imageAudits,
|
|||
|
FragmentsNum: fragmentsNum,
|
|||
|
}); err != nil {
|
|||
|
logger.Error("Imageaudit OpCreateFragmentGroup failed: %v", err)
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
auditFragmentIds := make([]string, fragmentsNum)
|
|||
|
for i, imageaudit := range imageAudits {
|
|||
|
auditFragmentIds[i] = util.DerefString(imageaudit.Id)
|
|||
|
}
|
|||
|
task.ImageAuditFragmentIds = &auditFragmentIds
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
func prepareNotFragmentedImageAuditTask(task *dbstruct.ImageAuditTask) (err error) {
|
|||
|
ctx := &gin.Context{}
|
|||
|
|
|||
|
imageAudit := &dbstruct.ImageAudit{
|
|||
|
AuditedMedia: task.AuditedMedia,
|
|||
|
BatchId: task.BatchId,
|
|||
|
Status: goproto.Int64(consts.ImageAudit_Created),
|
|||
|
}
|
|||
|
if err = _DefaultImageAudit.OpCreate(ctx, &imageauditproto.OpCreateReq{
|
|||
|
ImageAudit: imageAudit,
|
|||
|
}); err != nil {
|
|||
|
logger.Error("Imageaudit OpCreate failed: %v", err)
|
|||
|
return
|
|||
|
}
|
|||
|
|
|||
|
task.ImageAuditId = imageAudit.Id
|
|||
|
return
|
|||
|
}
|