chore: 并入 iotlcm-admin-svr 历史到 admin-svr/(原提交 49818c6)

This commit is contained in:
MiFaZhan
2026-11-02 13:27:59 +08:00
1250 changed files with 154111 additions and 0 deletions
@@ -0,0 +1,178 @@
package outbound
import (
"context"
"fmt"
"strings"
)
func validateRows(ctx context.Context, rows []*Row, opts PreviewOptions, repo *Repository) error {
identityFirstRow := make(map[string]*Row, len(rows))
iccids := make([]string, 0, len(rows))
msisdns := make([]string, 0, len(rows))
imsis := make([]string, 0, len(rows))
for _, row := range rows {
row.Iccid = strings.TrimSpace(row.Iccid)
row.Msisdn = strings.TrimSpace(row.Msisdn)
row.Imsi = strings.TrimSpace(row.Imsi)
row.RangeCodeType = rowIdentityCodeType(row)
key := rowIdentityKey(row)
if key == "" {
row.AddReason(rowIdentityLabel(row.RangeCodeType) + "不能为空")
continue
}
identityKey := row.RangeCodeType + ":" + key
if firstRow, ok := identityFirstRow[identityKey]; ok {
label := rowIdentityLabel(row.RangeCodeType)
row.AddReason(fmt.Sprintf("%s与第%d行重复", label, firstRow.RowNo))
firstRow.AddReason(fmt.Sprintf("%s与第%d行重复", label, row.RowNo))
continue
}
identityFirstRow[identityKey] = row
switch row.RangeCodeType {
case "msisdn":
msisdns = append(msisdns, key)
case "imsi":
imsis = append(imsis, key)
default:
iccids = append(iccids, key)
}
}
stockByIccid, err := repo.GetStockCardsByIccids(ctx, iccids)
if err != nil {
return err
}
stockByMsisdn, err := repo.GetStockCardsByMsisdns(ctx, msisdns)
if err != nil {
return err
}
stockByImsi, err := repo.GetStockCardsByImsis(ctx, imsis)
if err != nil {
return err
}
rowStock := make(map[*Row]*StockCard, len(rows))
resolvedIccidFirstRow := make(map[string]*Row, len(rows))
resolvedIccids := make([]string, 0, len(rows))
for _, row := range rows {
if !row.Valid() {
continue
}
stock := stockForRow(row, stockByIccid, stockByMsisdn, stockByImsi)
if stock == nil {
row.AddReason(rowIdentityLabel(row.RangeCodeType) + "不存在库存记录")
continue
}
providedIccid := row.Iccid
providedMsisdn := row.Msisdn
providedImsi := row.Imsi
row.Iccid = strings.TrimSpace(stock.Iccid)
row.Msisdn = chooseString(row.Msisdn, stock.Msisdn)
row.Imsi = chooseString(row.Imsi, stock.Imsi)
if row.Iccid == "" {
row.AddReason("库存卡ICCID为空")
continue
}
if firstRow, ok := resolvedIccidFirstRow[row.Iccid]; ok {
row.AddReason(fmt.Sprintf("ICCID与第%d行指向同一库存卡", firstRow.RowNo))
firstRow.AddReason(fmt.Sprintf("ICCID与第%d行指向同一库存卡", row.RowNo))
continue
}
resolvedIccidFirstRow[row.Iccid] = row
if stock.CreatedDept != opts.DeptId {
row.AddReason("ICCID不属于当前机构库存")
continue
}
if opts.StrictStockIdentity {
if providedIccid != "" && providedIccid != strings.TrimSpace(stock.Iccid) {
row.AddReason("ICCID与库存记录不一致")
continue
}
if providedMsisdn != "" && providedMsisdn != strings.TrimSpace(stock.Msisdn) {
row.AddReason("MSISDN与库存记录不一致")
continue
}
if providedImsi != "" && providedImsi != strings.TrimSpace(stock.Imsi) {
row.AddReason("IMSI与库存记录不一致")
continue
}
}
row.SourceBatchNo = strings.TrimSpace(stock.BatchNo)
rowStock[row] = stock
resolvedIccids = append(resolvedIccids, row.Iccid)
}
formalByIccid, err := repo.GetExistingFormalIccids(ctx, resolvedIccids)
if err != nil {
return err
}
for _, row := range rows {
if !row.Valid() || rowStock[row] == nil {
continue
}
if formalByIccid[row.Iccid] {
row.AddReason("ICCID已存在正式卡记录")
}
}
return nil
}
func rowIdentityCodeType(row *Row) string {
if row == nil {
return "iccid"
}
if codeType := normalizeRangeCodeType(row.RangeCodeType); codeType != "" {
return codeType
}
switch {
case strings.TrimSpace(row.Iccid) != "":
return "iccid"
case strings.TrimSpace(row.Msisdn) != "":
return "msisdn"
case strings.TrimSpace(row.Imsi) != "":
return "imsi"
default:
return "iccid"
}
}
func rowIdentityKey(row *Row) string {
if row == nil {
return ""
}
switch row.RangeCodeType {
case "msisdn":
return strings.TrimSpace(row.Msisdn)
case "imsi":
return strings.TrimSpace(row.Imsi)
default:
return strings.TrimSpace(row.Iccid)
}
}
func rowIdentityLabel(codeType string) string {
switch codeType {
case "msisdn":
return "MSISDN"
case "imsi":
return "IMSI"
default:
return "ICCID"
}
}
func stockForRow(row *Row, stockByIccid, stockByMsisdn, stockByImsi map[string]*StockCard) *StockCard {
if row == nil {
return nil
}
switch row.RangeCodeType {
case "msisdn":
return stockByMsisdn[strings.TrimSpace(row.Msisdn)]
case "imsi":
return stockByImsi[strings.TrimSpace(row.Imsi)]
default:
return stockByIccid[strings.TrimSpace(row.Iccid)]
}
}