127 lines
4.8 KiB
Go
127 lines
4.8 KiB
Go
package service
|
|
|
|
import (
|
|
"context"
|
|
"encoding/json"
|
|
"errors"
|
|
"strings"
|
|
"time"
|
|
|
|
"kra/internal/biz"
|
|
"kra/internal/service/dto"
|
|
|
|
"github.com/google/uuid"
|
|
)
|
|
|
|
var (
|
|
ErrExportTokenInvalid = errors.New("export token invalid")
|
|
ErrExportTokenMalformed = errors.New("export token malformed")
|
|
ErrExportTokenType = errors.New("export token type mismatch")
|
|
)
|
|
|
|
type ExportService struct {
|
|
uc *biz.ExportUsecase
|
|
cache biz.Cache
|
|
}
|
|
|
|
type ExportToken struct {
|
|
TemplateID string
|
|
Params map[string]string
|
|
Blank bool
|
|
}
|
|
|
|
type exportTokenCache struct {
|
|
TemplateID string `json:"templateID"`
|
|
Params map[string]string `json:"params"`
|
|
Blank bool `json:"blank"`
|
|
}
|
|
|
|
func NewExportService(uc *biz.ExportUsecase, cache biz.Cache) *ExportService {
|
|
return &ExportService{uc: uc, cache: cache}
|
|
}
|
|
|
|
func (s *ExportService) IssueToken(ctx context.Context, templateID string, params map[string]string, blank bool) (string, error) {
|
|
token := strings.ReplaceAll(uuid.NewString(), "-", "")
|
|
raw, err := json.Marshal(exportTokenCache{TemplateID: templateID, Params: params, Blank: blank})
|
|
if err != nil {
|
|
return "", err
|
|
}
|
|
if err = s.cache.Set(ctx, "export:"+token, string(raw), 30*time.Minute); err != nil {
|
|
return "", err
|
|
}
|
|
return token, nil
|
|
}
|
|
|
|
func (s *ExportService) ConsumeToken(ctx context.Context, token string, expectBlank bool) (*ExportToken, error) {
|
|
raw, ok, err := s.cache.Get(ctx, "export:"+token)
|
|
if err != nil || !ok {
|
|
return nil, ErrExportTokenInvalid
|
|
}
|
|
var value exportTokenCache
|
|
if json.Unmarshal([]byte(raw), &value) != nil {
|
|
return nil, ErrExportTokenMalformed
|
|
}
|
|
if value.Blank != expectBlank {
|
|
return nil, ErrExportTokenType
|
|
}
|
|
_ = s.cache.Delete(ctx, "export:"+token)
|
|
return &ExportToken{TemplateID: value.TemplateID, Params: value.Params, Blank: value.Blank}, nil
|
|
}
|
|
func exportTemplateDomain(value *dto.ExportTemplateRequest) *biz.ExportTemplate {
|
|
out := &biz.ExportTemplate{ID: value.ID, DBName: value.DBName, Name: value.Name, TableName: value.TableName, TemplateID: value.TemplateID, TemplateInfo: value.TemplateInfo, SQL: value.SQL, ImportSQL: value.ImportSQL, Limit: value.Limit, Order: value.Order}
|
|
for _, item := range value.Conditions {
|
|
out.Conditions = append(out.Conditions, biz.ExportCondition{From: item.From, Column: item.Column, Operator: item.Operator})
|
|
}
|
|
for _, item := range value.Joins {
|
|
out.Joins = append(out.Joins, biz.ExportJoin{Join: item.Join, Table: item.Table, On: item.On})
|
|
}
|
|
return out
|
|
}
|
|
func (s *ExportService) CreateRequest(ctx context.Context, req *dto.ExportTemplateRequest) error {
|
|
return s.Create(ctx, exportTemplateDomain(req))
|
|
}
|
|
func (s *ExportService) UpdateRequest(ctx context.Context, req *dto.ExportTemplateRequest) error {
|
|
return s.Update(ctx, exportTemplateDomain(req))
|
|
}
|
|
func (s *ExportService) TemplatesFilter(ctx context.Context, page, size int, name, tableName, templateID string, start, end *time.Time) ([]map[string]any, int64, error) {
|
|
return s.Templates(ctx, page, size, &biz.ExportTemplate{Name: name, TableName: tableName, TemplateID: templateID, StartCreatedAt: start, EndCreatedAt: end})
|
|
}
|
|
func exportDTO(v *biz.ExportTemplate) map[string]any {
|
|
conditions := make([]map[string]any, 0, len(v.Conditions))
|
|
for _, x := range v.Conditions {
|
|
conditions = append(conditions, map[string]any{"from": x.From, "column": x.Column, "operator": x.Operator})
|
|
}
|
|
joins := make([]map[string]any, 0, len(v.Joins))
|
|
for _, x := range v.Joins {
|
|
joins = append(joins, map[string]any{"joins": x.Join, "table": x.Table, "on": x.On})
|
|
}
|
|
return map[string]any{"ID": v.ID, "CreatedAt": v.CreatedAt, "UpdatedAt": v.UpdatedAt, "DeletedAt": nil, "dbName": v.DBName, "name": v.Name, "tableName": v.TableName, "templateID": v.TemplateID, "templateInfo": v.TemplateInfo, "sql": v.SQL, "importSql": v.ImportSQL, "limit": v.Limit, "order": v.Order, "conditions": conditions, "joinTemplate": joins}
|
|
}
|
|
func (s *ExportService) Create(ctx context.Context, v *biz.ExportTemplate) error {
|
|
return s.uc.CreateExportTemplate(ctx, v)
|
|
}
|
|
func (s *ExportService) Update(ctx context.Context, v *biz.ExportTemplate) error {
|
|
return s.uc.UpdateExportTemplate(ctx, v)
|
|
}
|
|
func (s *ExportService) Delete(ctx context.Context, ids []uint) error {
|
|
return s.uc.DeleteExportTemplates(ctx, ids)
|
|
}
|
|
func (s *ExportService) Template(ctx context.Context, id uint, tid string) (map[string]any, error) {
|
|
v, err := s.uc.FindExportTemplate(ctx, id, tid)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
return exportDTO(v), nil
|
|
}
|
|
func (s *ExportService) Templates(ctx context.Context, page, size int, q *biz.ExportTemplate) ([]map[string]any, int64, error) {
|
|
items, total, err := s.uc.ListExportTemplates(ctx, page, size, q)
|
|
if err != nil {
|
|
return nil, 0, err
|
|
}
|
|
out := make([]map[string]any, 0, len(items))
|
|
for _, v := range items {
|
|
out = append(out, exportDTO(v))
|
|
}
|
|
return out, total, nil
|
|
}
|