Files
iotlcm/openapi/internal/logic/query/traffic_cutoff_config.go

202 lines
5.8 KiB
Go

package query
import (
"context"
"strings"
"github.com/gogf/gf/v2/errors/gerror"
"git.5iot.com/iotlcm-public/iotlcm-openapi/internal/dao"
"git.5iot.com/iotlcm-public/iotlcm-openapi/internal/model"
"git.5iot.com/iotlcm-public/iotlcm-openapi/internal/model/entity"
"git.5iot.com/iotlcm-public/iotlcm-openapi/internal/service"
)
const queryTrafficCutoffConfigMaxCards = 1000
type trafficCutoffIdentifier struct {
Msisdn string
Iccid string
Imsi string
}
func validateTrafficCutoffIdentifier(item trafficCutoffIdentifier) error {
count := 0
if item.Msisdn != "" {
count++
}
if item.Iccid != "" {
count++
}
if item.Imsi != "" {
count++
}
if count == 0 {
return gerror.New("msisdn、iccid、imsi至少传一个")
}
return nil
}
func trafficCutoffIdentifierKey(item trafficCutoffIdentifier) string {
if item.Iccid != "" {
return "iccid:" + item.Iccid
}
if item.Msisdn != "" {
return "msisdn:" + item.Msisdn
}
return "imsi:" + item.Imsi
}
func trafficCutoffCardMatchesIdentifier(card *entity.TSimCardInfo, identifier trafficCutoffIdentifier) bool {
if card == nil {
return false
}
if identifier.Iccid != "" && strings.TrimSpace(card.Iccid) != identifier.Iccid {
return false
}
if identifier.Msisdn != "" && strings.TrimSpace(card.Msisdn) != identifier.Msisdn {
return false
}
if identifier.Imsi != "" && strings.TrimSpace(card.Imsi) != identifier.Imsi {
return false
}
return true
}
func (s *sQuerySim) QueryTrafficCutoffConfig(ctx context.Context, in *model.QueryTrafficCutoffConfigParam) (*model.QueryTrafficCutoffConfigOutput, error) {
if in == nil {
return nil, gerror.New("查询参数不能为空")
}
if strings.TrimSpace(in.AppId) == "" {
return nil, gerror.New("appId不能为空")
}
if len(in.Cards) == 0 {
return nil, gerror.New("查询卡不能为空")
}
if len(in.Cards) > queryTrafficCutoffConfigMaxCards {
return nil, gerror.Newf("单次最多查询%d张卡", queryTrafficCutoffConfigMaxCards)
}
identifiers := make([]trafficCutoffIdentifier, 0, len(in.Cards))
seen := make(map[string]struct{}, len(in.Cards))
for _, item := range in.Cards {
identifier := trafficCutoffIdentifier{Msisdn: strings.TrimSpace(item.Msisdn), Iccid: strings.TrimSpace(item.Iccid), Imsi: strings.TrimSpace(item.Imsi)}
if err := validateTrafficCutoffIdentifier(identifier); err != nil {
return nil, err
}
key := trafficCutoffIdentifierKey(identifier)
if _, ok := seen[key]; ok {
return nil, gerror.Newf("卡片标识重复:%s", key)
}
seen[key] = struct{}{}
identifiers = append(identifiers, identifier)
}
cardMap, err := loadTrafficCutoffCards(ctx, identifiers)
if err != nil {
return nil, err
}
output := &model.QueryTrafficCutoffConfigOutput{Total: len(identifiers), Items: make([]model.QueryTrafficCutoffConfigItem, 0, len(identifiers))}
for _, identifier := range identifiers {
result := model.QueryTrafficCutoffConfigItem{}
card := cardMap[trafficCutoffIdentifierKey(identifier)]
if !trafficCutoffCardMatchesIdentifier(card, identifier) {
result.ErrorCode = "CARD_NOT_FOUND"
result.ErrorMessage = "卡片不存在或无权限"
output.NotFoundCount++
output.Items = append(output.Items, result)
continue
}
result.Matched = true
result.Iccid = strings.TrimSpace(card.Iccid)
result.TrafficCutoffStatus = card.TrafficCutoffStatus
result.TrafficCutoffStatusName = trafficCutoffStatusName(card.TrafficCutoffStatus)
result.TrafficCutoffThreshold = card.TrafficCutoffThreshold
if result.TrafficCutoffStatus == 0 {
result.TrafficCutoffThreshold = 0
}
result.TrafficCutoffThresholdUnit = "MB"
if in.IncludeUsage {
packageTotalFlowMb := card.PackageTotalFlowMb
usedFlowMb := card.UsedFlowMb
remainingFlowMb := maxFloat(packageTotalFlowMb-usedFlowMb, 0)
result.PackageTotalFlowMb = &packageTotalFlowMb
result.UsedFlowMb = &usedFlowMb
result.RemainingFlowMb = &remainingFlowMb
}
output.MatchedCount++
output.Items = append(output.Items, result)
}
return output, nil
}
func loadTrafficCutoffCards(ctx context.Context, identifiers []trafficCutoffIdentifier) (map[string]*entity.TSimCardInfo, error) {
columns := dao.TSimCardInfo.Columns()
result := make(map[string]*entity.TSimCardInfo, len(identifiers))
lookup := func(field string, values []string) error {
if len(values) == 0 {
return nil
}
var cards []*entity.TSimCardInfo
err := service.IotTSimCardInfo().Model(ctx).
Fields(columns.Iccid, columns.Msisdn, columns.Imsi, columns.PackageTotalFlowMb, columns.UsedFlowMb, columns.TrafficCutoffStatus, columns.TrafficCutoffThreshold).
WhereIn(field, values).Scan(&cards)
if err != nil {
return gerror.Wrap(err, "查询达量断网配置失败")
}
for _, card := range cards {
if card == nil {
continue
}
if card.Iccid != "" {
result["iccid:"+strings.TrimSpace(card.Iccid)] = card
}
if card.Msisdn != "" {
result["msisdn:"+strings.TrimSpace(card.Msisdn)] = card
}
if card.Imsi != "" {
result["imsi:"+strings.TrimSpace(card.Imsi)] = card
}
}
return nil
}
iccidValues, msisdnValues, imsiValues := make([]string, 0), make([]string, 0), make([]string, 0)
for _, item := range identifiers {
switch {
case item.Iccid != "":
iccidValues = append(iccidValues, item.Iccid)
case item.Msisdn != "":
msisdnValues = append(msisdnValues, item.Msisdn)
default:
imsiValues = append(imsiValues, item.Imsi)
}
}
if err := lookup(columns.Iccid, iccidValues); err != nil {
return nil, err
}
if err := lookup(columns.Msisdn, msisdnValues); err != nil {
return nil, err
}
if err := lookup(columns.Imsi, imsiValues); err != nil {
return nil, err
}
return result, nil
}
func trafficCutoffStatusName(status int) string {
switch status {
case 1:
return "已开启"
case 2:
return "已关闭"
default:
return "删除"
}
}
func maxFloat(value, floor float64) float64 {
if value < floor {
return floor
}
return value
}