feat: 实现 IoT 卡轮询系统(支持千万级卡规模)
All checks were successful
构建并部署到测试环境(无 SSH) / build-and-deploy (push) Successful in 6m35s

实现功能:
- 实名状态检查轮询(可配置间隔)
- 卡流量检查轮询(支持跨月流量追踪)
- 套餐检查与超额自动停机
- 分布式并发控制(Redis 信号量)
- 手动触发轮询(单卡/批量/条件筛选)
- 数据清理配置与执行
- 告警规则与历史记录
- 实时监控统计(队列/性能/并发)

性能优化:
- Redis 缓存卡信息,减少 DB 查询
- Pipeline 批量写入 Redis
- 异步流量记录写入
- 渐进式初始化(10万卡/批)

压测工具(scripts/benchmark/):
- Mock Gateway 模拟上游服务
- 测试卡生成器
- 配置初始化脚本
- 实时监控脚本

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
2026-02-05 17:32:44 +08:00
parent b11edde720
commit 931e140e8e
104 changed files with 16883 additions and 87 deletions

View File

@@ -157,3 +157,91 @@ func RedisCommissionStatsLockKey() string {
func RedisShopSeriesAllocationKey(shopID, seriesID uint) string {
return fmt.Sprintf("shop_series_alloc:%d:%d", shopID, seriesID)
}
// ========================================
// 轮询系统相关 Redis Key
// ========================================
// RedisPollingQueueRealnameKey 生成实名检查轮询队列的 Redis 键
// 用途Sorted Set 存储待检查实名状态的卡Score 为下次检查的 Unix 时间戳
// 过期时间:无(持久化数据)
func RedisPollingQueueRealnameKey() string {
return "polling:queue:realname"
}
// RedisPollingQueueCarddataKey 生成卡流量检查轮询队列的 Redis 键
// 用途Sorted Set 存储待检查流量的卡Score 为下次检查的 Unix 时间戳
// 过期时间:无(持久化数据)
func RedisPollingQueueCarddataKey() string {
return "polling:queue:carddata"
}
// RedisPollingQueuePackageKey 生成套餐检查轮询队列的 Redis 键
// 用途Sorted Set 存储待检查套餐的卡Score 为下次检查的 Unix 时间戳
// 过期时间:无(持久化数据)
func RedisPollingQueuePackageKey() string {
return "polling:queue:package"
}
// RedisPollingCardInfoKey 生成卡信息缓存的 Redis 键
// 用途Hash 存储卡的基本信息和轮询状态
// 过期时间7 天
func RedisPollingCardInfoKey(cardID uint) string {
return fmt.Sprintf("polling:card:%d", cardID)
}
// RedisPollingConfigsCacheKey 生成轮询配置缓存的 Redis 键
// 用途String 存储所有轮询配置JSON 格式)
// 过期时间10 分钟
func RedisPollingConfigsCacheKey() string {
return "polling:configs"
}
// RedisPollingConfigCardsKey 生成配置匹配索引的 Redis 键
// 用途Set 存储匹配该配置的所有卡 ID
// 过期时间1 小时
func RedisPollingConfigCardsKey(configID uint) string {
return fmt.Sprintf("polling:config:cards:%d", configID)
}
// RedisPollingConcurrencyConfigKey 生成并发控制配置的 Redis 键
// 用途String 存储任务类型的最大并发数
// 过期时间:无(持久化配置)
func RedisPollingConcurrencyConfigKey(taskType string) string {
return fmt.Sprintf("polling:concurrency:config:%s", taskType)
}
// RedisPollingConcurrencyCurrentKey 生成并发控制当前值的 Redis 键
// 用途String 存储任务类型的当前并发数(计数器)
// 过期时间:无(实时数据)
func RedisPollingConcurrencyCurrentKey(taskType string) string {
return fmt.Sprintf("polling:concurrency:current:%s", taskType)
}
// RedisPollingManualQueueKey 生成手动触发队列的 Redis 键
// 用途List 存储手动触发的卡 IDFIFO 队列)
// 过期时间:无(临时队列)
func RedisPollingManualQueueKey(taskType string) string {
return fmt.Sprintf("polling:manual:%s", taskType)
}
// RedisPollingManualDedupeKey 生成手动触发去重的 Redis 键
// 用途Set 存储已加入手动触发队列的卡 ID用于去重
// 过期时间1小时
func RedisPollingManualDedupeKey(taskType string) string {
return fmt.Sprintf("polling:manual:dedupe:%s", taskType)
}
// RedisPollingStatsKey 生成监控统计的 Redis 键
// 用途Hash 存储监控指标(成功数、失败数、总耗时等)
// 过期时间:无(持久化统计)
func RedisPollingStatsKey(taskType string) string {
return fmt.Sprintf("polling:stats:%s", taskType)
}
// RedisPollingInitProgressKey 生成初始化进度的 Redis 键
// 用途Hash 存储初始化进度信息(总数、已处理数、状态)
// 过期时间:无(初始化完成后自动删除)
func RedisPollingInitProgressKey() string {
return "polling:init:progress"
}