🎨 更新项目版本

This commit is contained in:
2025-09-03 01:45:01 +08:00
parent f928348284
commit 5496bdaa94
130 changed files with 9397 additions and 1816 deletions

View File

@@ -3,6 +3,7 @@ package system
import (
"bytes"
"encoding/json"
"errors"
"fmt"
"mime/multipart"
"net/url"
@@ -127,6 +128,11 @@ func (sysExportTemplateService *SysExportTemplateService) GetSysExportTemplateIn
// ExportExcel 导出Excel
// Author [piexlmax](https://github.com/piexlmax)
func (sysExportTemplateService *SysExportTemplateService) ExportExcel(templateID string, values url.Values) (file *bytes.Buffer, name string, err error) {
var params = values.Get("params")
paramsValues, err := url.ParseQuery(params)
if err != nil {
return nil, "", fmt.Errorf("解析 params 参数失败: %v", err)
}
var template system.SysExportTemplate
err = global.GVA_DB.Preload("Conditions").Preload("JoinTemplate").First(&template, "template_id = ?", templateID).Error
if err != nil {
@@ -175,10 +181,38 @@ func (sysExportTemplateService *SysExportTemplateService) ExportExcel(templateID
db = db.Select(selects).Table(template.TableName)
filterDeleted := false
filterParam := paramsValues.Get("filterDeleted")
if filterParam == "true" {
filterDeleted = true
}
if filterDeleted {
// 自动过滤主表的软删除
db = db.Where(fmt.Sprintf("%s.deleted_at IS NULL", template.TableName))
// 过滤关联表的软删除(如果有)
if len(template.JoinTemplate) > 0 {
for _, join := range template.JoinTemplate {
// 检查关联表是否有deleted_at字段
hasDeletedAt := sysExportTemplateService.hasDeletedAtColumn(join.Table)
if hasDeletedAt {
db = db.Where(fmt.Sprintf("%s.deleted_at IS NULL", join.Table))
}
}
}
}
if len(template.Conditions) > 0 {
for _, condition := range template.Conditions {
sql := fmt.Sprintf("%s %s ?", condition.Column, condition.Operator)
value := values.Get(condition.From)
value := paramsValues.Get(condition.From)
if condition.Operator == "IN" || condition.Operator == "NOT IN" {
sql = fmt.Sprintf("%s %s (?)", condition.Column, condition.Operator)
}
if value != "" {
if condition.Operator == "LIKE" {
value = "%" + value + "%"
@@ -188,7 +222,7 @@ func (sysExportTemplateService *SysExportTemplateService) ExportExcel(templateID
}
}
// 通过参数传入limit
limit := values.Get("limit")
limit := paramsValues.Get("limit")
if limit != "" {
l, e := strconv.Atoi(limit)
if e == nil {
@@ -201,7 +235,7 @@ func (sysExportTemplateService *SysExportTemplateService) ExportExcel(templateID
}
// 通过参数传入offset
offset := values.Get("offset")
offset := paramsValues.Get("offset")
if offset != "" {
o, e := strconv.Atoi(offset)
if e == nil {
@@ -224,7 +258,7 @@ func (sysExportTemplateService *SysExportTemplateService) ExportExcel(templateID
}
// 通过参数传入order
order := values.Get("order")
order := paramsValues.Get("order")
if order == "" && template.Order != "" {
// 如果没有order入参这里会使用模板的默认排序
@@ -281,7 +315,17 @@ func (sysExportTemplateService *SysExportTemplateService) ExportExcel(templateID
}
for i, row := range rows {
for j, colCell := range row {
sErr := f.SetCellValue("Sheet1", fmt.Sprintf("%s%d", getColumnName(j+1), i+1), colCell)
cell := fmt.Sprintf("%s%d", getColumnName(j+1), i+1)
var sErr error
if v, err := strconv.ParseFloat(colCell, 64); err == nil {
sErr = f.SetCellValue("Sheet1", cell, v)
} else if v, err := strconv.ParseInt(colCell, 10, 64); err == nil {
sErr = f.SetCellValue("Sheet1", cell, v)
} else {
sErr = f.SetCellValue("Sheet1", cell, colCell)
}
if sErr != nil {
return nil, "", sErr
}
@@ -344,6 +388,13 @@ func (sysExportTemplateService *SysExportTemplateService) ExportTemplate(templat
return file, template.Name, nil
}
// 辅助函数检查表是否有deleted_at列
func (s *SysExportTemplateService) hasDeletedAtColumn(tableName string) bool {
var count int64
global.GVA_DB.Raw("SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE TABLE_NAME = ? AND COLUMN_NAME = 'deleted_at'", tableName).Count(&count)
return count > 0
}
// ImportExcel 导入Excel
// Author [piexlmax](https://github.com/piexlmax)
func (sysExportTemplateService *SysExportTemplateService) ImportExcel(templateID string, file *multipart.FileHeader) (err error) {
@@ -368,6 +419,9 @@ func (sysExportTemplateService *SysExportTemplateService) ImportExcel(templateID
if err != nil {
return err
}
if len(rows) < 2 {
return errors.New("Excel data is not enough.\nIt should contain title row and data")
}
var templateInfoMap = make(map[string]string)
err = json.Unmarshal([]byte(template.TemplateInfo), &templateInfoMap)
@@ -387,11 +441,17 @@ func (sysExportTemplateService *SysExportTemplateService) ImportExcel(templateID
return db.Transaction(func(tx *gorm.DB) error {
excelTitle := rows[0]
for i, str := range excelTitle {
excelTitle[i] = strings.TrimSpace(str)
}
values := rows[1:]
items := make([]map[string]interface{}, 0, len(values))
for _, row := range values {
var item = make(map[string]interface{})
for ii, value := range row {
if _, ok := titleKeyMap[excelTitle[ii]]; !ok {
continue // excel中多余的标题在模板信息中没有对应的字段因此key为空必须跳过
}
key := titleKeyMap[excelTitle[ii]]
item[key] = value
}