1.新增接口:其他出入库汇总、其他出入库明细;

This commit is contained in:
chenlin 2024-04-24 16:53:14 +08:00
parent 49970e13d2
commit 7c159858ef
4 changed files with 649 additions and 10 deletions

View File

@ -103,7 +103,14 @@ func InventoryReportByOther(c *gin.Context) {
return
}
app.OK(c, "", "OK")
resp, err := req.ReportByOtherList(c)
if err != nil {
//logger.Error("erp commodity list err:", err)
app.Error(c, http.StatusInternalServerError, err, "查询失败:"+err.Error())
return
}
app.OK(c, resp, "OK")
return
}
@ -122,6 +129,13 @@ func InventoryReportOtherDetail(c *gin.Context) {
return
}
app.OK(c, "", "OK")
resp, err := req.ReportByOtherDetailList(c)
if err != nil {
//logger.Error("erp commodity list err:", err)
app.Error(c, http.StatusInternalServerError, err, "查询失败:"+err.Error())
return
}
app.OK(c, resp, "OK")
return
}

View File

@ -32,7 +32,7 @@ const (
PurchaseReturn = 3 // 采购退货
InAllot = 4 // 调拨中(调入门店)
OnSale = 5 // 销售锁定中
ProductReturn = 6 // 产品出库
SystemOut = 6 // 系统出库
CheckOut = 7 // 盘点出库
)
@ -2171,9 +2171,9 @@ func SetStockCommodityState(id uint32) error { //更新库存状态为5并同
return err
}
// 更新商品库存详情表状态为5出库
// 更新商品库存详情表状态为6系统出库
if err := begin.Model(&ErpStockCommodity{}).Where("id=?", id).Updates(map[string]interface{}{
"state": 5}).Error; err != nil {
"state": SystemOut}).Error; err != nil {
return fmt.Errorf("[update err]%v", err)
}

View File

@ -163,7 +163,7 @@ type InventoryReportByOtherResp struct {
Total int `json:"total"` // 总条数/记录数
PageIndex int `json:"pageIndex"` // 页码
PageSize int `json:"pageSize"` // 页面条数
TotalCount int32 `json:"total_count"` // 总数量
TotalCount uint32 `json:"total_count"` // 总数量
TotalAmount float64 `json:"total_amount"` // 总金额
ExportUrl string `json:"export_url"` // 导出excel路径
List []ReportByOtherData `json:"list"` //
@ -177,8 +177,8 @@ type ReportByOtherData struct {
CommodityName string `json:"commodity_name"` // 商品名称
CategoryID uint32 `json:"category_id"` // 商品分类id
CategoryName string `json:"category_name"` // 商品分类名称
State uint32 `json:"state"` // 调拨状态1-产品入库 2-盘点入库 3-系统出库 4-盘点出库
Count int32 `json:"count"` // 数量
Type uint32 `json:"type"` // 调拨状态1-产品入库 2-盘点入库 3-系统出库 4-盘点出库
Count int64 `json:"count"` // 数量
Amount float64 `json:"amount"` // 金额
}
@ -188,7 +188,7 @@ type InventoryReportOtherDetailReq struct {
StoreId []uint32 `json:"store_id"` // 门店id
CommodityName []string `json:"commodity_name"` // 商品名称
CategoryID []uint32 `json:"category_id"` // 商品分类id
State uint32 `json:"state"` // 调拨状态1-产品入库 2-盘点入库 3-系统出库 4-盘点出库
Type uint32 `json:"type"` // 出入库方式1-产品入库 2-盘点入库 3-系统出库 4-盘点出库
StartTime string `json:"start_time"` // 开始时间/入库时间
EndTime string `json:"end_time"` // 结束时间/出库时间
IsExport uint32 `json:"is_export"` // 1-导出
@ -220,7 +220,7 @@ type ReportOtherDetailData struct {
SupplierId uint32 `json:"supplier_id"` // 供应商id
SupplierName string `json:"supplier_name"` // 供应商名称
StockTime *time.Time `json:"stock_time"` // 出入库时间
State uint32 `json:"state"` // 调拨状态1-产品入库 2-盘点入库 3-系统出库 4-盘点出库
Type uint32 `json:"type"` // 调拨状态1-产品入库 2-盘点入库 3-系统出库 4-盘点出库
SerialNumber string `json:"serial_number"` // 单据编号
PurchasePrice float64 `json:"purchase_price"` // 入库采购价
EmployeePrice float64 `json:"employee_price"` // 入库员工成本价
@ -1150,3 +1150,608 @@ func reportAllotDetailExport(req *InventoryReportAllotDetailResp) (string, error
}
return url + fileName, nil
}
// ReportByOtherList 其他出入库汇总
func (m *InventoryReportByOtherReq) ReportByOtherList(c *gin.Context) (*InventoryReportByOtherResp, error) {
// 非管理员才判断所属门店
if !(tools.GetRoleName(c) == "admin" || tools.GetRoleName(c) == "系统管理员") {
sysUser, err := GetSysUserByCtx(c)
if err != nil {
return nil, errors.New("操作失败:" + err.Error())
}
// 返回sysUser未过期的门店id列表
storeList := GetValidStoreIDs(sysUser.StoreData)
if len(storeList) > 0 {
m.StoreId = CompareLists(storeList, m.StoreId)
if len(m.StoreId) == 0 { // 没有匹配的数据,表示入参门店不是用户有权限的门店
return &InventoryReportByOtherResp{}, nil
}
} else {
return nil, errors.New("用户未绑定门店")
}
}
resp := &InventoryReportByOtherResp{
PageIndex: m.PageIndex,
PageSize: m.PageSize,
}
page := m.PageIndex - 1
if page < 0 {
page = 0
}
if m.PageSize == 0 {
m.PageSize = 10
}
// 查询产品入库数据
var err error
var productList []ReportOtherDetailData
productList, err = getProductOrderData()
if err != nil {
return nil, err
}
// 查询盘点出入库数据
var changeList []ReportOtherDetailData
changeList, err = getChangeOrderData()
if err != nil {
return nil, err
}
// 查询系统出库数据
var systemList []ReportOtherDetailData
systemList, err = getSystemOutData()
if err != nil {
return nil, err
}
// 合并数据
allData := append(productList, changeList...)
allData = append(allData, systemList...)
var nTotalAllotCount uint32
var nTotalAllotAmount float64
// 创建 map 用于存储汇总数据
summaryMap := make(map[string]*ReportByOtherData)
// 遍历切片
for _, item := range allData {
if item.Type == 3 || item.Type == 4 {
nTotalAllotCount -= 1
nTotalAllotAmount -= item.PurchasePrice
} else {
nTotalAllotCount += 1
nTotalAllotAmount += item.PurchasePrice
}
// 生成键
key := fmt.Sprintf("%d_%d_%d", item.CommodityId, item.StoreId, item.Type)
// 检查是否已经存在该键的汇总数据
if summary, ok := summaryMap[key]; ok {
// 如果已经存在,累加调拨数量和调拨金额
summary.Count += 1
// 假设商品金额在 item.CommodityAmount 中
summary.Amount += item.PurchasePrice
} else {
// 如果不存在,创建新的汇总数据并添加到 map 中
summaryMap[key] = &ReportByOtherData{
StoreId: item.StoreId,
StoreName: item.StoreName,
CommodityId: item.CommodityId,
CommodityName: item.CommodityName,
CategoryID: item.CategoryID,
CategoryName: item.CategoryName,
Type: item.Type,
Count: 1, // 初始化为 1
Amount: item.PurchasePrice,
}
}
}
var summaryList []ReportByOtherData
for i, summary := range summaryMap {
// 添加分类信息
commodityInfo, err := GetCommodity(summary.CommodityId)
if err != nil {
logger.Error("SetCategory err:", logger.Field("err", err))
}
summaryMap[i].CategoryID = commodityInfo.ErpCategoryId
summaryMap[i].CategoryName = commodityInfo.ErpCategoryName
if summary.Type == 3 || summary.Type == 4 {
summaryMap[i].Count = -summaryMap[i].Count
summaryMap[i].Amount = -summaryMap[i].Amount
}
summaryList = append(summaryList, *summary)
}
// 使用排序规则函数对汇总数据进行排序
sortSummaryList(summaryList)
// 计算分页所需的切片索引
startIndex := page * m.PageSize
endIndex := (page + 1) * m.PageSize
if endIndex > len(summaryList) {
endIndex = len(summaryList)
}
resp.Total = len(summaryList)
resp.TotalCount = nTotalAllotCount
resp.TotalAmount = tools.RoundToTwoDecimalPlaces(nTotalAllotAmount)
if m.IsExport == 1 {
resp.List = summaryList
resp.ExportUrl, err = reportOtherExport(resp)
if err != nil {
return nil, err
}
resp.List = []ReportByOtherData{}
resp.TotalCount = 0
resp.TotalAmount = 0
} else {
resp.List = summaryList[startIndex:endIndex]
}
return resp, nil
}
// 排序规则函数
// 排序规则:商品编号小>门店编号小>产品入库>盘点入库>系统出库>盘点出库
func sortSummaryList(summaryList []ReportByOtherData) {
sort.Slice(summaryList, func(i, j int) bool {
// 按 CommodityId 排序
if summaryList[i].CommodityId != summaryList[j].CommodityId {
return summaryList[i].CommodityId < summaryList[j].CommodityId
}
// 如果 CommodityId 相同,则按 StoreId 排序
if summaryList[i].StoreId != summaryList[j].StoreId {
return summaryList[i].StoreId < summaryList[j].StoreId
}
// 如果 StoreId 相同, 按 Type 排序
if summaryList[i].Type != summaryList[j].Type {
return summaryList[i].Type < summaryList[j].Type
}
// 如果 Type 相同,则按 Amount 排序
return summaryList[i].Amount < summaryList[j].Amount
})
}
// reportOtherExport 其他出入库汇总导出excel
func reportOtherExport(req *InventoryReportByOtherResp) (string, error) {
file := excelize.NewFile()
fSheet := "Sheet1"
url := ExportUrl
fileName := time.Now().Format(TimeFormat) + "其他出入库汇总" + ".xlsx"
fmt.Println("url fileName:", url+fileName)
// 组合标题栏数据
title := []interface{}{"门店", "商品名称", "商品分类", "出入库方式", "数量", "金额"}
for i, _ := range title {
cell, _ := excelize.CoordinatesToCellName(1+i, 1)
err := file.SetCellValue(fSheet, cell, title[i])
if err != nil {
logger.Error("file set value err:", logger.Field("err", err))
}
}
var row1 []interface{}
nExcelStartRow := 0
for _, reportData := range req.List {
var inventoryType string
switch reportData.Type {
case 1:
inventoryType = "产品入库"
case 2:
inventoryType = "盘点入库"
case 3:
inventoryType = "系统出库"
case 4:
inventoryType = "盘点出库"
}
row1 = []interface{}{
reportData.StoreName, // 门店
reportData.CommodityName, // 商品名称
reportData.CategoryName, // 商品分类
inventoryType, // 出入库方式
reportData.Count, // 数量
reportData.Amount, // 金额
}
for j, _ := range row1 {
cell, _ := excelize.CoordinatesToCellName(1+j, nExcelStartRow+2)
err := file.SetCellValue(fSheet, cell, row1[j])
if err != nil {
logger.Error("file set value err:", logger.Field("err", err))
}
}
nExcelStartRow++
}
totalData := "记录数:" + strconv.FormatInt(int64(req.Total), 10)
end := []interface{}{totalData, "", "", "", req.TotalCount, req.TotalAmount}
for i, _ := range end {
cell, _ := excelize.CoordinatesToCellName(1+i, nExcelStartRow+2)
err := file.SetCellValue(fSheet, cell, end[i])
if err != nil {
logger.Error("file set value err:", logger.Field("err", err))
}
}
// 设置所有单元格的样式: 居中、加边框
style, _ := file.NewStyle(`{"alignment":{"horizontal":"center","vertical":"center"},
"border":[{"type":"left","color":"000000","style":1},
{"type":"top","color":"000000","style":1},
{"type":"right","color":"000000","style":1},
{"type":"bottom","color":"000000","style":1}]}`)
//设置单元格高度
file.SetRowHeight("Sheet1", 1, 20)
// 设置单元格大小
file.SetColWidth("Sheet1", "A", "A", 28)
file.SetColWidth("Sheet1", "B", "B", 28)
file.SetColWidth("Sheet1", "C", "C", 20)
file.SetColWidth("Sheet1", "D", "D", 20)
endRow := fmt.Sprintf("F"+"%d", nExcelStartRow+2)
// 应用样式到整个表格
_ = file.SetCellStyle("Sheet1", "A1", endRow, style)
fmt.Println("save fileName:", config.ExportConfig.Path+fileName)
if err := file.SaveAs(config.ExportConfig.Path + fileName); err != nil {
fmt.Println(err)
}
return url + fileName, nil
}
// ReportByOtherDetailList 其他出入库明细
func (m *InventoryReportOtherDetailReq) ReportByOtherDetailList(c *gin.Context) (*InventoryReportOtherDetailResp, error) {
// 非管理员才判断所属门店
if !(tools.GetRoleName(c) == "admin" || tools.GetRoleName(c) == "系统管理员") {
sysUser, err := GetSysUserByCtx(c)
if err != nil {
return nil, errors.New("操作失败:" + err.Error())
}
// 返回sysUser未过期的门店id列表
storeList := GetValidStoreIDs(sysUser.StoreData)
if len(storeList) > 0 {
m.StoreId = CompareLists(storeList, m.StoreId)
if len(m.StoreId) == 0 { // 没有匹配的数据,表示入参门店不是用户有权限的门店
return &InventoryReportOtherDetailResp{}, nil
}
} else {
return nil, errors.New("用户未绑定门店")
}
}
resp := &InventoryReportOtherDetailResp{
PageIndex: m.PageIndex,
PageSize: m.PageSize,
}
page := m.PageIndex - 1
if page < 0 {
page = 0
}
if m.PageSize == 0 {
m.PageSize = 10
}
// 查询产品入库数据
var err error
var productList []ReportOtherDetailData
productList, err = getProductOrderData()
if err != nil {
return nil, err
}
// 查询盘点出入库数据
var changeList []ReportOtherDetailData
changeList, err = getChangeOrderData()
if err != nil {
return nil, err
}
// 查询系统出库数据
var systemList []ReportOtherDetailData
systemList, err = getSystemOutData()
if err != nil {
return nil, err
}
// 合并数据
allData := append(productList, changeList...)
allData = append(allData, systemList...)
// 进行条件查询
var startTime time.Time
if m.StartTime != "" { // 出入库开始时间
startTime, err = time.Parse(QueryTimeFormat, m.StartTime)
if err != nil {
logger.Errorf("ReportByOtherDetailList err:", err)
return nil, err
}
}
var endTime time.Time
if m.EndTime != "" { // 出入库结束时间
endTime, err = time.Parse(QueryTimeFormat, m.EndTime)
if err != nil {
logger.Errorf("ReportByOtherDetailList err:", err)
return nil, err
}
}
var totalPurchasePrice, totalEmployeePrice float64
filteredData := make([]ReportOtherDetailData, 0)
for i, data := range allData {
if allData[i].CategoryID == 0 {
// 添加分类信息
commodityInfo, err := GetCommodity(data.CommodityId)
if err != nil {
logger.Error("SetCategory err:", logger.Field("err", err))
}
allData[i].CategoryID = commodityInfo.ErpCategoryId
allData[i].CategoryName = commodityInfo.ErpCategoryName
}
if (len(m.SerialNumber) == 0 || data.SerialNumber == m.SerialNumber) &&
(len(m.StoreId) == 0 || tools.Uint32SliceContains(m.StoreId, data.StoreId)) &&
(len(m.CommodityName) == 0 || tools.StringSliceContains(m.CommodityName, data.CommodityName)) &&
(len(m.CategoryID) == 0 || tools.Uint32SliceContains(m.CategoryID, allData[i].CategoryID)) &&
(m.Type == 0 || m.Type == data.Type) &&
((m.StartTime == "" && m.EndTime == "") || (data.StockTime.After(startTime) && data.StockTime.Before(endTime))) {
if data.Type == 3 || data.Type == 4 { // 系统出库、盘点出库
totalPurchasePrice -= allData[i].PurchasePrice
totalEmployeePrice -= allData[i].EmployeePrice
allData[i].PurchasePrice = -allData[i].PurchasePrice
allData[i].EmployeePrice = -allData[i].EmployeePrice
} else {
totalPurchasePrice += allData[i].PurchasePrice
totalEmployeePrice += allData[i].EmployeePrice
}
filteredData = append(filteredData, allData[i])
}
}
// 进行排序
sort.Slice(filteredData, func(i, j int) bool {
return filteredData[i].StockTime.After(*filteredData[j].StockTime)
})
resp.TotalPurchasePrice = tools.RoundToTwoDecimalPlaces(totalPurchasePrice)
resp.TotalEmployeePrice = tools.RoundToTwoDecimalPlaces(totalEmployeePrice)
if m.IsExport == 1 {
resp.List = filteredData
resp.Total = len(filteredData)
resp.ExportUrl, err = reportOtherDetailExport(resp)
if err != nil {
return nil, err
}
resp.List = []ReportOtherDetailData{}
resp.TotalPurchasePrice = 0
resp.TotalEmployeePrice = 0
} else {
// 进行分页处理
startIndex := page * m.PageSize
endIndex := startIndex + m.PageSize
if endIndex > len(filteredData) {
endIndex = len(filteredData)
}
resp.List = filteredData[startIndex:endIndex]
resp.Total = len(filteredData)
}
return resp, nil
}
// 查询产品入库数据
func getProductOrderData() ([]ReportOtherDetailData, error) {
var productList []ReportOtherDetailData
err := orm.Eloquent.Debug().Table("erp_inventory_product_order").
Select("erp_inventory_product_order.serial_number, "+
"erp_inventory_product_order.store_id, "+
"erp_inventory_product_order.store_name, "+
"erp_inventory_product_order.audit_time as stock_time, "+
"CASE "+
"WHEN erp_inventory_product_order.state = 2 THEN 1 "+
"ELSE erp_inventory_product_order.state "+
"END AS type, "+
"erp_inventory_product_commodity.commodity_id, "+
"erp_inventory_product_commodity.commodity_name, "+
"erp_inventory_product_commodity.supplier_id, "+
"erp_inventory_product_commodity.supplier_name, "+
"erp_inventory_product_commodity.imei_type, "+
"erp_inventory_product_commodity.imei, "+
"erp_inventory_product_commodity.price as purchase_price, "+
"erp_inventory_product_commodity.employee_price as employee_price").
Joins("JOIN erp_inventory_product_commodity "+
"ON erp_inventory_product_commodity.product_order_id = erp_inventory_product_order.id").
Where("erp_inventory_product_order.state = ?", ErpInventoryProductOrderFinished).
Find(&productList).Error // 查询已审核的订单
if err != nil {
return nil, err
}
return productList, nil
}
// 查询盘点出入库数据
func getChangeOrderData() ([]ReportOtherDetailData, error) {
var changeList []ReportOtherDetailData
err := orm.Eloquent.Debug().Table("erp_inventory_change_order").
Select("erp_inventory_change_order.serial_number, "+
"erp_inventory_change_order.store_id, "+
"erp_inventory_change_order.store_name, "+
"erp_inventory_change_order.audit_time as stock_time, "+
"CASE "+
"WHEN erp_inventory_change_order.change_type = 'add' THEN 2 "+
"WHEN erp_inventory_change_order.change_type = 'reduce' THEN 4 "+
"ELSE erp_inventory_change_order.state "+
"END AS type, "+
"erp_inventory_change_commodity.commodity_id, "+
"erp_inventory_change_commodity.commodity_name, "+
"erp_inventory_change_commodity.supplier_id, "+
"erp_inventory_change_commodity.supplier_name, "+
"erp_inventory_change_commodity.imei_type, "+
"erp_inventory_change_commodity.imei, "+
"erp_inventory_change_commodity.price as purchase_price, "+
"erp_inventory_change_commodity.employee_price as employee_price").
Joins("JOIN erp_inventory_change_commodity "+
"ON erp_inventory_change_commodity.change_order_id = erp_inventory_change_order.id").
Where("erp_inventory_change_order.state = ?", ErpInventoryChangeOrderFinished).
Find(&changeList).Error // 查询已审核的订单
if err != nil {
return nil, err
}
return changeList, nil
}
// 查询系统出库数据
func getSystemOutData() ([]ReportOtherDetailData, error) {
var stockCommodities []ErpStockCommodity
err := orm.Eloquent.Table("erp_stock_commodity").
Where("state = ?", SystemOut).Find(&stockCommodities).Error
if err != nil {
return nil, err
}
var systemOutList []ReportOtherDetailData
for _, item := range stockCommodities {
var systemOutData ReportOtherDetailData
systemOutData.CommodityId = item.ErpCommodityId
systemOutData.CommodityName = item.ErpCommodityName
systemOutData.CategoryID = item.ErpCategoryId
systemOutData.CategoryName = item.ErpCategoryName
systemOutData.IMEIType = item.IMEIType
systemOutData.IMEI = item.IMEI
systemOutData.StoreId = item.StoreId
systemOutData.StoreName = item.StoreName
systemOutData.SupplierId = item.ErpSupplierId
systemOutData.SupplierName = item.ErpSupplierName
systemOutData.StockTime = &item.UpdatedAt
systemOutData.Type = 3
systemOutData.PurchasePrice = item.WholesalePrice
systemOutData.EmployeePrice = item.WholesalePrice + item.StaffCostPrice
systemOutList = append(systemOutList, systemOutData)
}
return systemOutList, nil
}
// reportOtherDetailExport 其他出入库明细导出excel
func reportOtherDetailExport(req *InventoryReportOtherDetailResp) (string, error) {
file := excelize.NewFile()
fSheet := "Sheet1"
url := ExportUrl
fileName := time.Now().Format(TimeFormat) + "其他出入库明细" + ".xlsx"
fmt.Println("url fileName:", url+fileName)
// 组合标题栏数据
title := []interface{}{"商品名称", "商品分类", "是否串码", "商品串码", "所属门店", "供应商", "出/入库时间", "方式", "单据编号",
"入库采购价", "入库员工成本价"}
for i, _ := range title {
cell, _ := excelize.CoordinatesToCellName(1+i, 1)
err := file.SetCellValue(fSheet, cell, title[i])
if err != nil {
logger.Error("file set value err:", logger.Field("err", err))
}
}
var row1 []interface{}
nExcelStartRow := 0
for _, reportData := range req.List {
var inventoryType string
switch reportData.Type {
case 1:
inventoryType = "产品入库"
case 2:
inventoryType = "盘点入库"
case 3:
inventoryType = "系统出库"
case 4:
inventoryType = "盘点出库"
}
var IMEIType string
switch reportData.IMEIType {
case 1:
IMEIType = "非串码"
case 2, 3:
IMEIType = "串码类"
}
var auditTime string
if reportData.StockTime != nil {
auditTime = reportData.StockTime.Format(TimeFormat)
}
row1 = []interface{}{
reportData.CommodityName, // 商品名称
reportData.CategoryName, // 商品分类
IMEIType, // 是否串码
reportData.IMEI, // 商品串码
reportData.StoreName, // 所属门店
reportData.SupplierName, // 供应商
auditTime, // 出/入库时间
inventoryType, // 方式
reportData.SerialNumber, // 单据编号
reportData.PurchasePrice, // 入库采购价
reportData.EmployeePrice, // 入库员工成本价
}
for j, _ := range row1 {
cell, _ := excelize.CoordinatesToCellName(1+j, nExcelStartRow+2)
err := file.SetCellValue(fSheet, cell, row1[j])
if err != nil {
logger.Error("file set value err:", logger.Field("err", err))
}
}
nExcelStartRow++
}
totalData := "记录数:" + strconv.FormatInt(int64(req.Total), 10)
end := []interface{}{totalData, "", "", "", "", "", "", "", "", req.TotalPurchasePrice, req.TotalEmployeePrice}
for i, _ := range end {
cell, _ := excelize.CoordinatesToCellName(1+i, nExcelStartRow+2)
err := file.SetCellValue(fSheet, cell, end[i])
if err != nil {
logger.Error("file set value err:", logger.Field("err", err))
}
}
// 设置所有单元格的样式: 居中、加边框
style, _ := file.NewStyle(`{"alignment":{"horizontal":"center","vertical":"center"},
"border":[{"type":"left","color":"000000","style":1},
{"type":"top","color":"000000","style":1},
{"type":"right","color":"000000","style":1},
{"type":"bottom","color":"000000","style":1}]}`)
//设置单元格高度
file.SetRowHeight("Sheet1", 1, 20)
// 设置单元格大小
file.SetColWidth("Sheet1", "A", "A", 28)
file.SetColWidth("Sheet1", "B", "B", 15)
file.SetColWidth("Sheet1", "D", "D", 18)
file.SetColWidth("Sheet1", "E", "E", 28)
file.SetColWidth("Sheet1", "G", "G", 18)
file.SetColWidth("Sheet1", "I", "I", 18)
endRow := fmt.Sprintf("K"+"%d", nExcelStartRow+2)
// 应用样式到整个表格
_ = file.SetCellStyle("Sheet1", "A1", endRow, style)
fmt.Println("save fileName:", config.ExportConfig.Path+fileName)
if err := file.SaveAs(config.ExportConfig.Path + fileName); err != nil {
fmt.Println(err)
}
return url + fileName, nil
}

View File

@ -114,3 +114,23 @@ func ConvertTimeToStringByPoint(t *time.Time) string {
func RoundToTwoDecimalPlaces(num float64) float64 {
return math.Round(num*100) / 100
}
// Uint32SliceContains 检查 uint32 切片中是否包含特定的值
func Uint32SliceContains(slice []uint32, val uint32) bool {
for _, item := range slice {
if item == val {
return true
}
}
return false
}
// StringSliceContains 检查 string 切片中是否包含特定的值
func StringSliceContains(slice []string, val string) bool {
for _, item := range slice {
if item == val {
return true
}
}
return false
}