feat(运营报表): AUG26-015 设备激活与套餐续费日报快照、查询趋势与受控导出
All checks were successful
构建并部署到测试环境(无 SSH) / build-and-deploy (push) Successful in 15m33s
All checks were successful
构建并部署到测试环境(无 SSH) / build-and-deploy (push) Successful in 15m33s
- 新增成对迁移 000231 与三张快照表:日级头行、设备粒度激活行、到期事件粒度续费行,以快照日期为唯一键 - 新增每日 03:30(Asia/Shanghai)日报快照生成任务与幂等整日替换,失败重试沿用同一目标日 - 新增六条受控入口:两张报表的汇总、日/月趋势与受控导出,配套查询层只读快照事实 - 新增 operations_activation 与 operations_renewal 两个导出场景,创建期冻结筛选与可见店铺范围、派发期冻结表头、执行期只按冻结值复核资格 - 采购数量口径按系统内未删除设备数实施并在 PRD 标注,附实测差额依据 - 同步证据链 requirement-evidence.json 与入口能力矩阵、ARCHITECTURE 与验证记录 - 归档 change add-operations-reports 并新建主 Spec openspec/specs/operations-report/spec.md
This commit is contained in:
@@ -4,7 +4,7 @@ import "time"
|
||||
|
||||
// CreateExportTaskRequest 创建导出任务请求。
|
||||
type CreateExportTaskRequest struct {
|
||||
Scene string `json:"scene" validate:"required,oneof=device iot_card order package agent_wallet_transaction agent_recharge refund exchange commission_record package_traffic_alert expiring_asset" required:"true" description:"导出场景 (device:设备, iot_card:IoT卡, order:订单, package:套餐, agent_wallet_transaction:代理主钱包流水, agent_recharge:代理充值, refund:退款, exchange:换货, commission_record:佣金明细, package_traffic_alert:套餐真流量达量预警, expiring_asset:临期资产)"`
|
||||
Scene string `json:"scene" validate:"required,oneof=device iot_card order package agent_wallet_transaction agent_recharge refund exchange commission_record package_traffic_alert expiring_asset operations_activation operations_renewal" required:"true" description:"导出场景 (device:设备, iot_card:IoT卡, order:订单, package:套餐, agent_wallet_transaction:代理主钱包流水, agent_recharge:代理充值, refund:退款, exchange:换货, commission_record:佣金明细, package_traffic_alert:套餐真流量达量预警, expiring_asset:临期资产, operations_activation:设备激活情况报表, operations_renewal:套餐续费情况报表)"`
|
||||
Format string `json:"format" validate:"required,oneof=xlsx csv" required:"true" description:"导出格式 (xlsx:Excel, csv:CSV)"`
|
||||
Query map[string]interface{} `json:"query,omitempty" description:"导出筛选参数(JSON对象,可选);时间筛选固定使用 filters.start_time 与 filters.end_time,取值必须为带显式时区的 RFC3339 秒级时间"`
|
||||
}
|
||||
@@ -22,7 +22,7 @@ type CreateExportTaskResponse struct {
|
||||
type ListExportTaskRequest struct {
|
||||
Page int `json:"page" query:"page" validate:"omitempty,min=1" minimum:"1" description:"页码"`
|
||||
PageSize int `json:"page_size" query:"page_size" validate:"omitempty,min=1,max=100" minimum:"1" maximum:"100" description:"每页数量"`
|
||||
Scene string `json:"scene" query:"scene" validate:"omitempty,oneof=device iot_card order package agent_wallet_transaction agent_recharge refund exchange commission_record package_traffic_alert expiring_asset" description:"导出场景 (device:设备, iot_card:IoT卡, order:订单, package:套餐, agent_wallet_transaction:代理主钱包流水, agent_recharge:代理充值, refund:退款, exchange:换货, commission_record:佣金明细, package_traffic_alert:套餐真流量达量预警, expiring_asset:临期资产)"`
|
||||
Scene string `json:"scene" query:"scene" validate:"omitempty,oneof=device iot_card order package agent_wallet_transaction agent_recharge refund exchange commission_record package_traffic_alert expiring_asset operations_activation operations_renewal" description:"导出场景 (device:设备, iot_card:IoT卡, order:订单, package:套餐, agent_wallet_transaction:代理主钱包流水, agent_recharge:代理充值, refund:退款, exchange:换货, commission_record:佣金明细, package_traffic_alert:套餐真流量达量预警, expiring_asset:临期资产, operations_activation:设备激活情况报表, operations_renewal:套餐续费情况报表)"`
|
||||
Status *int `json:"status" query:"status" validate:"omitempty,min=1,max=5" minimum:"1" maximum:"5" description:"任务状态 (1:待处理, 2:处理中, 3:已完成, 4:已失败, 5:已取消)"`
|
||||
StartTime string `json:"start_time" query:"start_time" description:"创建时间起始(带时区的 RFC3339 秒级时间,闭区间含该时刻,如 2026-09-01T00:00:00+08:00)"`
|
||||
EndTime string `json:"end_time" query:"end_time" description:"创建时间结束(带时区的 RFC3339 秒级时间,闭区间含该时刻,如 2026-09-30T23:59:59+08:00)"`
|
||||
@@ -33,7 +33,7 @@ type ExportTaskItem struct {
|
||||
ID uint `json:"id" description:"任务ID"`
|
||||
TaskID uint `json:"task_id" description:"任务ID"`
|
||||
TaskNo string `json:"task_no" description:"任务编号"`
|
||||
Scene string `json:"scene" description:"导出场景 (device:设备, iot_card:IoT卡, order:订单, package:套餐, agent_wallet_transaction:代理主钱包流水, agent_recharge:代理充值, refund:退款, exchange:换货, commission_record:佣金明细, package_traffic_alert:套餐真流量达量预警)"`
|
||||
Scene string `json:"scene" description:"导出场景 (device:设备, iot_card:IoT卡, order:订单, package:套餐, agent_wallet_transaction:代理主钱包流水, agent_recharge:代理充值, refund:退款, exchange:换货, commission_record:佣金明细, package_traffic_alert:套餐真流量达量预警, operations_activation:设备激活情况报表, operations_renewal:套餐续费情况报表)"`
|
||||
Format string `json:"format" description:"导出格式 (xlsx:Excel, csv:CSV)"`
|
||||
Status int `json:"status" description:"任务状态 (1:待处理, 2:处理中, 3:已完成, 4:已失败, 5:已取消)"`
|
||||
StatusName string `json:"status_name" description:"任务状态名称(中文)"`
|
||||
|
||||
120
internal/model/dto/operations_report_dto.go
Normal file
120
internal/model/dto/operations_report_dto.go
Normal file
@@ -0,0 +1,120 @@
|
||||
package dto
|
||||
|
||||
// OperationsActivationSummaryRequest 是设备激活情况汇总查询请求。
|
||||
// 时间筛选只接受带显式时区的 RFC3339 秒级时间与闭区间;快照日期按「零点落入区间」判定。
|
||||
type OperationsActivationSummaryRequest struct {
|
||||
StartTime string `json:"start_time" query:"start_time" description:"快照日期起始(带时区的 RFC3339 秒级时间,闭区间含该时刻,如 2026-09-01T00:00:00+08:00)"`
|
||||
EndTime string `json:"end_time" query:"end_time" description:"快照日期结束(带时区的 RFC3339 秒级时间,闭区间含该时刻,如 2026-09-01T00:00:00+08:00)"`
|
||||
GroupBy string `json:"group_by" query:"group_by" validate:"omitempty,oneof=device_name device_model manufacturer business_user_group agent shop business_owner" description:"分组维度 (device_name:设备名称, device_model:设备型号, manufacturer:制造商, business_user_group:用户组, agent:代理, shop:店铺, business_owner:业务员);不传则汇总为一行「全部」"`
|
||||
}
|
||||
|
||||
// OperationsActivationTrendRequest 是设备激活情况趋势查询请求。
|
||||
type OperationsActivationTrendRequest struct {
|
||||
StartTime string `json:"start_time" query:"start_time" description:"快照日期起始(带时区的 RFC3339 秒级时间,闭区间含该时刻,如 2026-09-01T00:00:00+08:00)"`
|
||||
EndTime string `json:"end_time" query:"end_time" description:"快照日期结束(带时区的 RFC3339 秒级时间,闭区间含该时刻,如 2026-09-30T00:00:00+08:00)"`
|
||||
Granularity string `json:"granularity" query:"granularity" validate:"omitempty,oneof=day month" description:"趋势粒度 (day:按日, month:按月);不传按日"`
|
||||
GroupBy string `json:"group_by" query:"group_by" validate:"omitempty,oneof=device_name device_model manufacturer business_user_group agent shop business_owner" description:"分组维度;不传则每个期返回一行「全部」"`
|
||||
}
|
||||
|
||||
// OperationsRenewalSummaryRequest 是套餐续费情况汇总查询请求。
|
||||
type OperationsRenewalSummaryRequest struct {
|
||||
StartTime string `json:"start_time" query:"start_time" description:"快照日期起始(带时区的 RFC3339 秒级时间,闭区间含该时刻,如 2026-09-01T00:00:00+08:00)"`
|
||||
EndTime string `json:"end_time" query:"end_time" description:"快照日期结束(带时区的 RFC3339 秒级时间,闭区间含该时刻,如 2026-09-01T00:00:00+08:00)"`
|
||||
GroupBy string `json:"group_by" query:"group_by" validate:"omitempty,oneof=package_series package_name business_user_group agent shop business_owner" description:"分组维度 (package_series:套餐系列, package_name:套餐名称, business_user_group:用户组, agent:代理, shop:店铺, business_owner:业务员);不传则汇总为一行「全部」"`
|
||||
}
|
||||
|
||||
// OperationsRenewalTrendRequest 是套餐续费情况趋势查询请求。
|
||||
type OperationsRenewalTrendRequest struct {
|
||||
StartTime string `json:"start_time" query:"start_time" description:"快照日期起始(带时区的 RFC3339 秒级时间,闭区间含该时刻,如 2026-09-01T00:00:00+08:00)"`
|
||||
EndTime string `json:"end_time" query:"end_time" description:"快照日期结束(带时区的 RFC3339 秒级时间,闭区间含该时刻,如 2026-09-30T00:00:00+08:00)"`
|
||||
Granularity string `json:"granularity" query:"granularity" validate:"omitempty,oneof=day month" description:"趋势粒度 (day:按日, month:按月);不传按日"`
|
||||
GroupBy string `json:"group_by" query:"group_by" validate:"omitempty,oneof=package_series package_name business_user_group agent shop business_owner" description:"分组维度;不传则每个期返回一行「全部」"`
|
||||
}
|
||||
|
||||
// OperationsActivationSummaryItem 是设备激活情况的一行指标。
|
||||
// 累计类与其派生指标取所选结束日的快照;结束日无快照时全部为空值(不回退更早快照)。
|
||||
// 分母为零的比率与卡均为空值;新增激活数允许为负,不设零下限。
|
||||
type OperationsActivationSummaryItem struct {
|
||||
GroupValue string `json:"group_value" description:"分组列值(未选择分组维度时为「全部」)"`
|
||||
PurchasedDeviceCount *int64 `json:"purchased_device_count" description:"采购数量:截至快照日系统内未删除的设备数"`
|
||||
ActivatedDeviceCount *int64 `json:"activated_device_count" description:"累计激活数:任一当前有效关联卡已实名的设备数"`
|
||||
ActivationRate *float64 `json:"activation_rate" description:"激活率:累计激活数 / 采购数量,保留两位小数;采购数量为零时为空"`
|
||||
NewActivatedDeviceCount *int64 `json:"new_activated_device_count" description:"新增激活数:结束日累计减去基期累计,允许为负"`
|
||||
OnlineDeviceCount *int64 `json:"online_device_count" description:"累计在网数:已实名且存在有效主套餐的设备数"`
|
||||
ActiveDeviceCount *int64 `json:"active_device_count" description:"活跃用户数:真流量合计大于零的设备数"`
|
||||
TotalRealTrafficGB *float64 `json:"total_real_traffic_gb" description:"累计用量(GB):按 1 GB = 1024 MB 折算,保留两位小数"`
|
||||
PerUserAverageGB *float64 `json:"per_user_average_gb" description:"单用户卡均(GB):累计用量 / 累计在网数,保留两位小数;在网数为零时为空"`
|
||||
ForecastAverageIncludingZeroGB *float64 `json:"forecast_average_including_zero_gb" description:"含零预测卡均(GB):按累计在网数为分母、结束日所在当月年化"`
|
||||
ForecastAverageExcludingZeroGB *float64 `json:"forecast_average_excluding_zero_gb" description:"不含零预测卡均(GB):按活跃用户数为分母、结束日所在当月年化"`
|
||||
}
|
||||
|
||||
// OperationsActivationSummaryResponse 是设备激活情况汇总响应。
|
||||
// HasSnapshot 表示所选结束日是否存在快照;SnapshotDates 是区间内实际命中的快照日期集合。
|
||||
type OperationsActivationSummaryResponse struct {
|
||||
HasSnapshot bool `json:"has_snapshot" description:"结束日是否存在快照;为 false 时累计类与派生指标为空且分组行为空集"`
|
||||
SnapshotDates []string `json:"snapshot_dates" description:"区间内实际命中的快照日期(yyyy-MM-dd)"`
|
||||
GroupBy string `json:"group_by" description:"分组维度编码;空表示未分组"`
|
||||
GroupName string `json:"group_name" description:"分组维度中文名;未分组时为「全部」"`
|
||||
Totals *OperationsActivationSummaryItem `json:"totals" description:"头行合计;结束日无快照时为空"`
|
||||
Items []OperationsActivationSummaryItem `json:"items" description:"分组行;未选择分组维度时只有一行「全部」"`
|
||||
}
|
||||
|
||||
// OperationsActivationTrendPoint 是设备激活情况趋势的一个期点。
|
||||
// 累计类指标取该期最后一个有快照日的快照值;新增激活数取相邻期同口径之差,任一侧无快照时为空。
|
||||
type OperationsActivationTrendPoint struct {
|
||||
Period string `json:"period" description:"期标识(按日为 yyyy-MM-dd,按月为 yyyy-MM)"`
|
||||
OperationsActivationSummaryItem
|
||||
}
|
||||
|
||||
// OperationsActivationTrendResponse 是设备激活情况趋势响应。
|
||||
// 无快照的期不出现;后端只返回数据,图表渲染由前端负责。
|
||||
type OperationsActivationTrendResponse struct {
|
||||
Granularity string `json:"granularity" description:"趋势粒度 (day|month)"`
|
||||
GroupBy string `json:"group_by" description:"分组维度编码;空表示未分组"`
|
||||
GroupName string `json:"group_name" description:"分组维度中文名;未分组时为「全部」"`
|
||||
Points []OperationsActivationTrendPoint `json:"points" description:"趋势点;无快照的期不出现"`
|
||||
}
|
||||
|
||||
// OperationsRenewalSummaryItem 是套餐续费情况的一行指标。
|
||||
// 到期与续费均按资产去重,续费资产恒为到期资产的子集,续费率不超过 100% 由构造保证。
|
||||
type OperationsRenewalSummaryItem struct {
|
||||
GroupValue string `json:"group_value" description:"分组列值(未选择分组维度时为「全部」)"`
|
||||
DueAssetCount *int64 `json:"due_asset_count" description:"到期资产数:未退款主套餐到期日为统计期的资产数(按资产去重)"`
|
||||
RenewedAssetCount *int64 `json:"renewed_asset_count" description:"续费资产数:到期资产中已续费的资产数(按资产去重)"`
|
||||
RenewalRate *float64 `json:"renewal_rate" description:"续费率:续费资产数 / 到期资产数,保留两位小数;到期数为零时为空"`
|
||||
NewUnrenewedAssetCount *int64 `json:"new_unrenewed_asset_count" description:"新增未续费数:到期资产数减续费资产数,不小于零"`
|
||||
}
|
||||
|
||||
// OperationsRenewalSummaryResponse 是套餐续费情况汇总响应。
|
||||
type OperationsRenewalSummaryResponse struct {
|
||||
HasSnapshot bool `json:"has_snapshot" description:"结束日是否存在快照;为 false 时全部指标为空且分组行为空集"`
|
||||
SnapshotDates []string `json:"snapshot_dates" description:"区间内实际命中的快照日期(yyyy-MM-dd)"`
|
||||
GroupBy string `json:"group_by" description:"分组维度编码;空表示未分组"`
|
||||
GroupName string `json:"group_name" description:"分组维度中文名;未分组时为「全部」"`
|
||||
Totals *OperationsRenewalSummaryItem `json:"totals" description:"头行合计;结束日无快照时为空"`
|
||||
Items []OperationsRenewalSummaryItem `json:"items" description:"分组行;未选择分组维度时只有一行「全部」"`
|
||||
}
|
||||
|
||||
// OperationsRenewalTrendPoint 是套餐续费情况趋势的一个期点。
|
||||
// 到期与续费都是期内流式指标:期内同一资产多次到期或多条续费各计一次。
|
||||
type OperationsRenewalTrendPoint struct {
|
||||
Period string `json:"period" description:"期标识(按日为 yyyy-MM-dd,按月为 yyyy-MM)"`
|
||||
OperationsRenewalSummaryItem
|
||||
}
|
||||
|
||||
// OperationsRenewalTrendResponse 是套餐续费情况趋势响应。
|
||||
type OperationsRenewalTrendResponse struct {
|
||||
Granularity string `json:"granularity" description:"趋势粒度 (day|month)"`
|
||||
GroupBy string `json:"group_by" description:"分组维度编码;空表示未分组"`
|
||||
GroupName string `json:"group_name" description:"分组维度中文名;未分组时为「全部」"`
|
||||
Points []OperationsRenewalTrendPoint `json:"points" description:"趋势点;无快照的期不出现"`
|
||||
}
|
||||
|
||||
// ExportOperationsReportRequest 是设备激活情况与套餐续费情况报表的受控导出请求。
|
||||
// 时间边界在创建期冻结为 UTC RFC3339 秒级字符串,执行期只按冻结值严格解析。
|
||||
type ExportOperationsReportRequest struct {
|
||||
Format string `json:"format" validate:"required,oneof=xlsx csv" required:"true" description:"导出格式 (xlsx:Excel, csv:CSV)"`
|
||||
StartTime string `json:"start_time" description:"快照日期起始(带时区的 RFC3339 秒级时间,闭区间含该时刻,如 2026-09-01T00:00:00+08:00)"`
|
||||
EndTime string `json:"end_time" description:"快照日期结束(带时区的 RFC3339 秒级时间,闭区间含该时刻,如 2026-09-30T00:00:00+08:00)"`
|
||||
GroupBy string `json:"group_by" description:"分组维度编码;不传则导出唯一一行「全部」"`
|
||||
}
|
||||
97
internal/model/operations_report.go
Normal file
97
internal/model/operations_report.go
Normal file
@@ -0,0 +1,97 @@
|
||||
package model
|
||||
|
||||
import "time"
|
||||
|
||||
// OperationsReportSnapshot 运营报表日级快照头行。
|
||||
//
|
||||
// 一个上海自然日一行,同时承担三件事:①「该日是否有快照」的唯一判定;
|
||||
// ②日/月趋势与新增指标的序列来源(O(1) 读取,不必扫明细行);
|
||||
// ③合计行与分组行不变量校验的权威值。整日幂等替换,因此不设软删除列。
|
||||
type OperationsReportSnapshot struct {
|
||||
ID uint `gorm:"column:id;primaryKey;autoIncrement" json:"id"`
|
||||
SnapshotDate time.Time `gorm:"column:snapshot_date;type:date;not null" json:"snapshot_date"`
|
||||
PurchasedDeviceCount int64 `gorm:"column:purchased_device_count;type:bigint;not null;default:0" json:"purchased_device_count"`
|
||||
ActivatedDeviceCount int64 `gorm:"column:activated_device_count;type:bigint;not null;default:0" json:"activated_device_count"`
|
||||
OnlineDeviceCount int64 `gorm:"column:online_device_count;type:bigint;not null;default:0" json:"online_device_count"`
|
||||
ActiveDeviceCount int64 `gorm:"column:active_device_count;type:bigint;not null;default:0" json:"active_device_count"`
|
||||
TotalRealTrafficMB float64 `gorm:"column:total_real_traffic_mb;type:numeric(20,2);not null;default:0" json:"total_real_traffic_mb"`
|
||||
RenewalDueAssetCount int64 `gorm:"column:renewal_due_asset_count;type:bigint;not null;default:0" json:"renewal_due_asset_count"`
|
||||
RenewalRenewedAssetCount int64 `gorm:"column:renewal_renewed_asset_count;type:bigint;not null;default:0" json:"renewal_renewed_asset_count"`
|
||||
GeneratedAt time.Time `gorm:"column:generated_at;type:timestamp;not null" json:"generated_at"`
|
||||
CreatedAt time.Time `gorm:"column:created_at;type:timestamp;not null;default:CURRENT_TIMESTAMP" json:"created_at"`
|
||||
UpdatedAt time.Time `gorm:"column:updated_at;type:timestamp;not null;default:CURRENT_TIMESTAMP" json:"updated_at"`
|
||||
}
|
||||
|
||||
// TableName 指定运营报表日级快照头行表名。
|
||||
func (OperationsReportSnapshot) TableName() string {
|
||||
return "tb_operations_report_snapshot"
|
||||
}
|
||||
|
||||
// OperationsReportActivationRow 运营报表设备激活快照行。
|
||||
//
|
||||
// 设备粒度,一行对应一台未删除设备,冻结生成时刻的设备属性、归属与四项指标。
|
||||
// 归属(店铺、业务员、用户组与代理的两个取值)是一次性冻结值,不因后续变化被改写。
|
||||
type OperationsReportActivationRow struct {
|
||||
ID uint `gorm:"column:id;primaryKey;autoIncrement" json:"id"`
|
||||
SnapshotDate time.Time `gorm:"column:snapshot_date;type:date;not null" json:"snapshot_date"`
|
||||
DeviceID uint `gorm:"column:device_id;type:bigint;not null" json:"device_id"`
|
||||
VirtualNo string `gorm:"column:virtual_no;type:varchar(100);not null;default:''" json:"virtual_no"`
|
||||
DeviceName string `gorm:"column:device_name;type:varchar(255);not null;default:''" json:"device_name"`
|
||||
DeviceModel string `gorm:"column:device_model;type:varchar(100);not null;default:''" json:"device_model"`
|
||||
Manufacturer string `gorm:"column:manufacturer;type:varchar(255);not null;default:''" json:"manufacturer"`
|
||||
ShopID *uint `gorm:"column:shop_id;type:bigint" json:"shop_id,omitempty"`
|
||||
ShopName string `gorm:"column:shop_name;type:varchar(100);not null;default:''" json:"shop_name"`
|
||||
RootShopID *uint `gorm:"column:root_shop_id;type:bigint" json:"root_shop_id,omitempty"`
|
||||
RootShopName string `gorm:"column:root_shop_name;type:varchar(100);not null;default:''" json:"root_shop_name"`
|
||||
AgentAccountID *uint `gorm:"column:agent_account_id;type:bigint" json:"agent_account_id,omitempty"`
|
||||
AgentAccountName string `gorm:"column:agent_account_name;type:varchar(255);not null;default:''" json:"agent_account_name"`
|
||||
BusinessOwnerAccountID *uint `gorm:"column:business_owner_account_id;type:bigint" json:"business_owner_account_id,omitempty"`
|
||||
BusinessOwnerName string `gorm:"column:business_owner_name;type:varchar(255);not null;default:''" json:"business_owner_name"`
|
||||
BusinessUserGroupID *uint `gorm:"column:business_user_group_id;type:bigint" json:"business_user_group_id,omitempty"`
|
||||
BusinessUserGroupName string `gorm:"column:business_user_group_name;type:varchar(100);not null;default:''" json:"business_user_group_name"`
|
||||
Purchased bool `gorm:"column:purchased;type:boolean;not null;default:false" json:"purchased"`
|
||||
Realnamed bool `gorm:"column:realnamed;type:boolean;not null;default:false" json:"realnamed"`
|
||||
Online bool `gorm:"column:online;type:boolean;not null;default:false" json:"online"`
|
||||
Active bool `gorm:"column:active;type:boolean;not null;default:false" json:"active"`
|
||||
RealTrafficMB float64 `gorm:"column:real_traffic_mb;type:numeric(20,2);not null;default:0" json:"real_traffic_mb"`
|
||||
CreatedAt time.Time `gorm:"column:created_at;type:timestamp;not null;default:CURRENT_TIMESTAMP" json:"created_at"`
|
||||
}
|
||||
|
||||
// TableName 指定运营报表设备激活快照行表名。
|
||||
func (OperationsReportActivationRow) TableName() string {
|
||||
return "tb_operations_report_activation_row"
|
||||
}
|
||||
|
||||
// OperationsReportRenewalRow 运营报表套餐续费快照行。
|
||||
//
|
||||
// 到期事件粒度,一行对应一条在快照日到期的主套餐使用记录;
|
||||
// 「续费」是该到期资产在生成时刻是否已存在另一条未退款主套餐的事实,因此挂在到期行上。
|
||||
type OperationsReportRenewalRow struct {
|
||||
ID uint `gorm:"column:id;primaryKey;autoIncrement" json:"id"`
|
||||
SnapshotDate time.Time `gorm:"column:snapshot_date;type:date;not null" json:"snapshot_date"`
|
||||
AssetType string `gorm:"column:asset_type;type:varchar(20);not null" json:"asset_type"`
|
||||
AssetID uint `gorm:"column:asset_id;type:bigint;not null" json:"asset_id"`
|
||||
AssetIdentifier string `gorm:"column:asset_identifier;type:varchar(100);not null;default:''" json:"asset_identifier"`
|
||||
ExpiredUsageID uint `gorm:"column:expired_usage_id;type:bigint;not null" json:"expired_usage_id"`
|
||||
PackageID uint `gorm:"column:package_id;type:bigint;not null" json:"package_id"`
|
||||
PackageName string `gorm:"column:package_name;type:varchar(255);not null;default:''" json:"package_name"`
|
||||
SeriesID *uint `gorm:"column:series_id;type:bigint" json:"series_id,omitempty"`
|
||||
SeriesName string `gorm:"column:series_name;type:varchar(255);not null;default:''" json:"series_name"`
|
||||
ShopID *uint `gorm:"column:shop_id;type:bigint" json:"shop_id,omitempty"`
|
||||
ShopName string `gorm:"column:shop_name;type:varchar(100);not null;default:''" json:"shop_name"`
|
||||
RootShopID *uint `gorm:"column:root_shop_id;type:bigint" json:"root_shop_id,omitempty"`
|
||||
RootShopName string `gorm:"column:root_shop_name;type:varchar(100);not null;default:''" json:"root_shop_name"`
|
||||
AgentAccountID *uint `gorm:"column:agent_account_id;type:bigint" json:"agent_account_id,omitempty"`
|
||||
AgentAccountName string `gorm:"column:agent_account_name;type:varchar(255);not null;default:''" json:"agent_account_name"`
|
||||
BusinessOwnerAccountID *uint `gorm:"column:business_owner_account_id;type:bigint" json:"business_owner_account_id,omitempty"`
|
||||
BusinessOwnerName string `gorm:"column:business_owner_name;type:varchar(255);not null;default:''" json:"business_owner_name"`
|
||||
BusinessUserGroupID *uint `gorm:"column:business_user_group_id;type:bigint" json:"business_user_group_id,omitempty"`
|
||||
BusinessUserGroupName string `gorm:"column:business_user_group_name;type:varchar(100);not null;default:''" json:"business_user_group_name"`
|
||||
Renewed bool `gorm:"column:renewed;type:boolean;not null;default:false" json:"renewed"`
|
||||
CreatedAt time.Time `gorm:"column:created_at;type:timestamp;not null;default:CURRENT_TIMESTAMP" json:"created_at"`
|
||||
}
|
||||
|
||||
// TableName 指定运营报表套餐续费快照行表名。
|
||||
func (OperationsReportRenewalRow) TableName() string {
|
||||
return "tb_operations_report_renewal_row"
|
||||
}
|
||||
Reference in New Issue
Block a user