历史榜单的存储策略

由于我们要解决的是数据过多问题,因此分表的方式选择水平分表。具体来说,就是按照赛季拆分,每一个赛季是一个独立的表,如图:

不过这里我们可以做一些简化:

  • 我们可以将id作为排名,排名字段就不需要了。

  • 不同赛季用不同表,那么赛季字段就不需要了。

综上,最终表结构可以是这样:

不过这就存在一个问题,每个赛季要有不同的表,这些表什么时候创建呢?

显然,应该在每个赛季刚开始的时候(月初)来创建新的赛季榜单表。每个月的月初执行一个创建表的任务,我们可以利用定时任务来实现。

由于表的名称中包含赛季id,因此在定时任务中我们还要先查询赛季信息,获取赛季id,拼接得到表名,最后创建表。

大概流程如图:

 CREATE TABLE IF NOT EXISTS `points_board_X`
 (
    `id`      BIGINT NOT NULL AUTO_INCREMENT COMMENT '榜单id',
    `user_id` BIGINT NOT NULL COMMENT '学生id',
    `points`  INT    NOT NULL COMMENT '积分值',
    PRIMARY KEY (`id`) USING BTREE,
    INDEX `idx_user_id` (`user_id`) USING BTREE
 )
    COMMENT ='学霸天梯榜'
    COLLATE = 'utf8mb4_0900_ai_ci'
    ENGINE = InnoDB
    ROW_FORMAT = DYNAMIC
 ;

表名称的前缀是points_board_,我们应该将其定义为常量。在tj-learning模块中定义: 

 

表中的字段少了2个(rank、season),因此我们需要修改对应的实体类: 

2.3.定时任务生成榜单表

接下来,我们通过SpringTask定义一个定时任务,在每月初动态生成赛季榜单表。

2.3.1.定时任务

首先,在tj-learning模块下定义一个任务处理类:

 

package com.tianji.learning.handler;

import com.tianji.common.utils.CollUtils;
import com.tianji.common.utils.DateUtils;
import com.tianji.learning.service.IPointsBoardSeasonService;
import com.tianji.learning.service.IPointsBoardService;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Component;

import java.time.LocalDateTime;
import java.util.List;

import static com.tianji.learning.constants.LearningConstants.POINTS_BOARD_TABLE_PREFIX;

@Component
@RequiredArgsConstructor
public class PointsBoardPersistentHandler {

    private final IPointsBoardSeasonService seasonService;

    private final IPointsBoardService pointsBoardService;

    @Scheduled(cron = "0 0 3 1 * ?") // 每月1号,凌晨3点执行
    public void createPointsBoardTableOfLastSeason(){
        // 1.获取上月时间
        LocalDateTime time = LocalDateTime.now().minusMonths(1);
        // 2.查询赛季id
        Integer season = seasonService.querySeasonByTime(time);
        if (season == null) {
            // 赛季不存在
            return;
        }
        // 3.创建表
        pointsBoardService.createPointsBoardTableBySeason(season);
    }
}

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值