Files
observer/server/biz/dao/label_task.go
T
2026-08-27 11:04:56 +08:00

148 lines
4.3 KiB
Go

package dao
import (
"context"
"github.com/gogf/gf/v2/frame/g"
"github.com/gogf/gf/v2/os/gtime"
"observer-server/biz/consts"
"observer-server/biz/model/entity"
"observer-server/common"
)
// LabelTask 标注任务表 DAO:进度更新(done 计数)高频,单行 UPDATE 原子。
type labelTaskDao struct{}
var LabelTask = &labelTaskDao{}
func init() {
ctx := context.Background()
_, err := g.DB().Exec(ctx, `CREATE TABLE IF NOT EXISTS label_task (
id INTEGER PRIMARY KEY AUTOINCREMENT,
dataset_id INTEGER NOT NULL,
status TEXT NOT NULL DEFAULT 'running',
total INTEGER NOT NULL DEFAULT 0,
done INTEGER NOT NULL DEFAULT 0,
filenames TEXT,
error TEXT,
created_at TEXT NOT NULL,
finished_at TEXT
)`)
if err != nil {
panic(err)
}
}
// Insert 创建标注任务,返回自增 id
func (d *labelTaskDao) Insert(ctx context.Context, m *entity.LabelTask) (int64, error) {
res, err := g.DB().Model(consts.TableLabelTask).Ctx(ctx).Data(g.Map{
"dataset_id": m.DatasetId,
"status": m.Status,
"total": m.Total,
"done": m.Done,
"filenames": m.Filenames,
"error": m.Error,
"created_at": m.CreatedAt,
"finished_at": m.FinishedAt,
}).Insert()
if err != nil {
return 0, err
}
return res.LastInsertId()
}
// GetById 按主键查询,不存在返回 nil
func (d *labelTaskDao) GetById(ctx context.Context, id int64) (*entity.LabelTask, error) {
var e entity.LabelTask
err := g.DB().Model(consts.TableLabelTask).Ctx(ctx).Where("id", id).Scan(&e)
if err != nil {
if common.IsNoRows(err) {
return nil, nil
}
return nil, err
}
return &e, nil
}
// ListRunning 全部 running 任务(服务重启恢复用)
func (d *labelTaskDao) ListRunning(ctx context.Context) ([]*entity.LabelTask, error) {
var list []*entity.LabelTask
err := g.DB().Model(consts.TableLabelTask).Ctx(ctx).
Where("status", consts.LabelTaskRunning).OrderAsc("id").Scan(&list)
if err != nil {
if common.IsNoRows(err) {
return []*entity.LabelTask{}, nil
}
return nil, err
}
return list, nil
}
// GetRunningByDataset 某数据集 running 任务(并发检查用)
func (d *labelTaskDao) GetRunningByDataset(ctx context.Context, datasetId int64) (*entity.LabelTask, error) {
var e entity.LabelTask
err := g.DB().Model(consts.TableLabelTask).Ctx(ctx).
Where("dataset_id", datasetId).Where("status", consts.LabelTaskRunning).Scan(&e)
if err != nil {
if common.IsNoRows(err) {
return nil, nil
}
return nil, err
}
return &e, nil
}
// UpdateProgress 更新处理进度
func (d *labelTaskDao) UpdateProgress(ctx context.Context, id int64, done int) error {
_, err := g.DB().Model(consts.TableLabelTask).Ctx(ctx).Where("id", id).
Data(g.Map{"done": done}).Update()
return err
}
// Finish 完成任务(done 状态 + 完成时间 + 失败原因)
func (d *labelTaskDao) Finish(ctx context.Context, id int64, errMsg string) error {
_, err := g.DB().Model(consts.TableLabelTask).Ctx(ctx).Where("id", id).
Data(g.Map{"status": consts.LabelTaskDone, "finished_at": gtime.Now(), "error": errMsg}).Update()
return err
}
// LatestByDataset 某数据集最近一次任务(无则 nil)
func (d *labelTaskDao) LatestByDataset(ctx context.Context, datasetId int64) (*entity.LabelTask, error) {
var e entity.LabelTask
err := g.DB().Model(consts.TableLabelTask).Ctx(ctx).
Where("dataset_id", datasetId).OrderDesc("id").Limit(1).Scan(&e)
if err != nil {
if common.IsNoRows(err) {
return nil, nil
}
return nil, err
}
return &e, nil
}
// DeleteByDataset 删除数据集关联的全部标注任务(数据集删除时级联清理孤儿记录)
func (d *labelTaskDao) DeleteByDataset(ctx context.Context, datasetId int64) error {
_, err := g.DB().Model(consts.TableLabelTask).Ctx(ctx).
Where("dataset_id", datasetId).Delete()
return err
}
// Page 标注任务分页:创建时间倒序
func (d *labelTaskDao) Page(ctx context.Context, page, size int) ([]*entity.LabelTask, int64, error) {
base := g.DB().Model(consts.TableLabelTask).Ctx(ctx)
total, err := base.Count()
if err != nil {
return nil, 0, err
}
var list []*entity.LabelTask
err = base.OrderDesc("id").Limit((page-1)*size, size).Scan(&list)
if err != nil {
if common.IsNoRows(err) {
return []*entity.LabelTask{}, int64(total), nil
}
return nil, 0, err
}
return list, int64(total), nil
}