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,248 @@
package logic
import (
"context"
"fmt"
"git.5iot.com/iotlcm-public/iotlcm-admin-svr/internal/dao"
"git.5iot.com/iotlcm-public/iotlcm-admin-svr/internal/library/contexts"
"git.5iot.com/iotlcm-public/iotlcm-admin-svr/internal/model"
"git.5iot.com/iotlcm-public/iotlcm-admin-svr/internal/service"
"time"
"github.com/gogf/gf/v2/frame/g"
"github.com/gogf/gf/v2/os/gtime"
)
type sHome struct{}
func NewHome() *sHome {
return &sHome{}
}
func init() {
service.RegisterHome(NewHome())
}
func (s *sHome) GetCardStatistics(ctx context.Context) (stats *model.CardStatistics, err error) {
stats = new(model.CardStatistics)
deptId := contexts.GetDeptId(ctx)
table := dao.TSimCardInfo.Table()
// 1. TotalCount - 卡总数
totalCount, err := g.DB().Model(table).Ctx(ctx).Where("dept_id", deptId).Count()
if err != nil {
return nil, err
}
stats.TotalCount = int64(totalCount)
// 正确的日期处理:先转为本月1号,再加1个月,彻底规避月底溢出 Bug
now := gtime.Now()
monthStartStr := now.Format("Y-m-01 00:00:00")
monthEndStr := now.AddDate(0, 1, 0).Format("Y-m-01 00:00:00")
// 2. MonthlyNewCount - 本月新增
monthlyNewCount, err := g.DB().Model(table).Ctx(ctx).
Where("dept_id", deptId).
Where("boss_activate_at >= ?", monthStartStr).
Where("boss_activate_at < ?", monthEndStr).
Count()
if err != nil {
return nil, err
}
stats.MonthlyNewCount = int64(monthlyNewCount)
// 3. MonthlyFlowUsage - 本月流量使用
var flowResult struct {
Total float64
}
err = g.DB().Model(table).Ctx(ctx).
Fields("IFNULL(SUM(used_flow_mb), 0) as total").
Where("dept_id", deptId).
Scan(&flowResult)
if err != nil {
return nil, err
}
stats.MonthlyFlowUsage = int64(flowResult.Total)
// 4. MonthlyActiveCount - 本月活跃卡数
monthlyActiveCount, err := g.DB().Model(table).Ctx(ctx).
Where("dept_id", deptId).
Where("used_flow_mb > 0").
Count()
if err != nil {
return nil, err
}
stats.MonthlyActiveCount = int64(monthlyActiveCount)
return stats, nil
}
// GetCardStatusStatistics 获取卡状态统计
func (s *sHome) GetCardStatusStatistics(ctx context.Context) (stats *model.CardStatusStatistics, err error) {
stats = new(model.CardStatusStatistics)
deptId := contexts.GetDeptId(ctx)
table := dao.TSimCardInfo.Table()
// 卡状态统计
// 待激活(1)
pendingActivationCount, _ := g.DB().Model(table).Ctx(ctx).Where("dept_id", deptId).Where("boss_card_status", 1).Count()
stats.PendingActivationCount = int64(pendingActivationCount)
// 已激活(2)
activatedCount, _ := g.DB().Model(table).Ctx(ctx).Where("dept_id", deptId).Where("boss_card_status", 2).Count()
stats.ActivatedCount = int64(activatedCount)
// 停机(4)
stoppedCount, _ := g.DB().Model(table).Ctx(ctx).Where("dept_id", deptId).Where("boss_card_status", 4).Count()
stats.StoppedCount = int64(stoppedCount)
// 可测试(6)
testableCount, _ := g.DB().Model(table).Ctx(ctx).Where("dept_id", deptId).Where("boss_card_status", 6).Count()
stats.TestableCount = int64(testableCount)
// 库存(7)
inventoryCount, _ := g.DB().Model(table).Ctx(ctx).Where("dept_id", deptId).Where("boss_card_status", 7).Count()
stats.InventoryCount = int64(inventoryCount)
// 预销户(8)
preCancelCount, _ := g.DB().Model(table).Ctx(ctx).Where("dept_id", deptId).Where("boss_card_status", 8).Count()
stats.PreCancelCount = int64(preCancelCount)
// 已销户(9)
canceledCount, _ := g.DB().Model(table).Ctx(ctx).Where("dept_id", deptId).Where("boss_card_status", 9).Count()
stats.CanceledCount = int64(canceledCount)
// 未知(0)
unknownCount, _ := g.DB().Model(table).Ctx(ctx).Where("dept_id", deptId).Where("boss_card_status", 0).Count()
stats.UnknownCount = int64(unknownCount)
return stats, nil
}
// GetDeptFlowUsageChart 获取部门流量使用图表数据,用于折线图展示
// period: 7d 前7天, 1m 前6个月
func (s *sHome) GetDeptFlowUsageChart(ctx context.Context, period string) (*model.FlowUsageChartData, error) {
deptId := contexts.GetDeptId(ctx)
table := dao.TDeptFlowDaily.Table()
// 使用标准库 time 获取当前时间
now := time.Now()
var (
startDateStr string
endDateStr string
groupBy string // SQL 分组字段
labels = make([]string, 0)
values = make([]int64, 0)
)
switch period {
case "7d":
// 前7天:包含今天在内的过去7天
startDateStr = now.AddDate(0, 0, -6).Format("2006-01-02")
endDateStr = now.Format("2006-01-02")
groupBy = "stat_date" // 按天分组
case "1m":
// 前6个月:从6个月前的1号开始,方便按月对齐
startDateStr = now.AddDate(0, -5, 0).Format("2006-01-01")
endDateStr = now.Format("2006-01-02")
// 使用 MySQL 的 DATE_FORMAT 函数按月聚合
groupBy = "DATE_FORMAT(stat_date, '%Y-%m')"
default:
// 默认当月(按天)
startDateStr = now.Format("2006-01-01")
endDateStr = now.Format("2006-01-02")
groupBy = "stat_date"
}
// 1. 从数据库查询聚合数据
var list []struct {
TimeKey string `json:"time_key"`
UsedFlowMb int64 `json:"used_flow_mb"`
}
fields := fmt.Sprintf("%s as time_key, IFNULL(SUM(total_used_flow_mb), 0) as used_flow_mb", groupBy)
err := g.DB().Model(table).Ctx(ctx).
Fields(fields).
Where("dept_id", deptId).
Where("stat_date >= ? AND stat_date <= ?", startDateStr, endDateStr).
Group(groupBy).
Order("time_key ASC").
Scan(&list)
if err != nil {
return nil, err
}
// 2. 将查询结果转换为 Map,方便 O(1) 复杂度查找
dataMap := make(map[string]int64)
for _, item := range list {
dataMap[item.TimeKey] = item.UsedFlowMb
}
// 3. 核心:将字符串转回标准 time.Time 对象,用来做连续日期循环
startTime, _ := time.Parse("2006-01-02", startDateStr)
endTime, _ := time.Parse("2006-01-02", endDateStr)
if period == "1m" {
// 【6个月模式】:按月循环
for t := startTime; !t.After(endTime); t = t.AddDate(0, 1, 0) {
// 匹配数据库返回的 key 格式 "2026-06"
mapKey := t.Format("2006-01")
// 放入返回的 Labels 数组 (格式要求:2026-06)
labels = append(labels, mapKey)
// 提取数据或补 0
if val, exists := dataMap[mapKey]; exists {
values = append(values, val)
} else {
values = append(values, 0)
}
}
} else {
// 【7天/默认模式】:按天循环
for t := startTime; !t.After(endTime); t = t.AddDate(0, 0, 1) {
// 匹配数据库返回的 key 格式 "2026-06-25"
mapKey := t.Format("2006-01-02")
// 放入返回的 Labels 数组 (格式要求:06-25)
labels = append(labels, t.Format("01-02"))
// 提取数据或补 0
if val, exists := dataMap[mapKey]; exists {
values = append(values, val)
} else {
values = append(values, 0)
}
}
}
return &model.FlowUsageChartData{
Labels: labels,
Values: values,
}, nil
}
// GetTopUsageCardsYesterday 获取前一天流量使用前五名的卡片
func (s *sHome) GetTopUsageCardsYesterday(ctx context.Context) ([]model.TopUsageCard, error) {
return service.TrafficUsage().GetTopUsageCardsYesterday(ctx)
}
// GetFlowPoolUsageList 获取该用户下所有流量池的流量使用情况
func (s *sHome) GetFlowPoolUsageList(ctx context.Context) ([]model.FlowPoolUsageItem, error) {
deptId := contexts.GetDeptId(ctx)
var pools []model.FlowPoolUsageItem
err := g.DB().Model("t_sim_flow_pool").
Fields("flow_pool_code, total_flow_mb, used_flow_mb").
Where("dept_id", deptId).
Where("pool_status", 0).
Scan(&pools)
if err != nil {
return nil, err
}
return pools, nil
}