CMS—作品点赞、粉丝关注设计

一、需求分析 

CMS—作品点赞、粉丝关注设计_第1张图片

1.1、需求整理 

1.社区主页瀑布流分页时显示点赞总数 
2.作品明细展示显示点赞总数、可点赞、可取消 
3.进入自己个人中心显示自己点赞作品(可取消)
4.进入他人个人中心显示他人点赞作品 
5.可查看作品下的点赞用户列表(分页、倒排)

1.2、特性分析 

1.总数与明细都要记录 
2.查频率高、写并发高 
3.回显实时性要求高 
4.传输数据量小 
5.数据是单体小,整体范围大、量多 
6.数据价值低 

1.3、难点分析 

1.点接口并发高 
2.新增数据量大范围广 
3.查询点赞量频繁 

二、表、接口设计 

2.1、表结构设计 

2.1.1、点赞表设计

CREATE TABLE `work_likes` (
	`id` bigint NOT NULL AUTO_INCREMENT COMMENT '主键ID',
	`work_id` bigint DEFAULT NULL COMMENT '评论ID',
	`user_id` bigint DEFAULT NULL COMMENT '点赞人ID',
	`status` tinyint(1) DEFAULT '0' COMMENT '状态(0点赞 1取消)',
	`like_time` datetime DEFAULT NULL COMMENT '点赞时间',
	PRIMARY KEY (`id`) USING BTREE,
	UNIQUE KEY `work_user_index` (`work_id`,`user_id`) USING BTREE
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='作品点赞记录表';

2.1.2、粉丝关注表设计

CREATE TABLE `fans_follow` (
  `id` bigint NOT NULL AUTO_INCREMENT,
  `followed_id` bigint DEFAULT '0' COMMENT '被关注者ID',
  `fans_id` bigint DEFAULT '0' COMMENT '粉丝ID',
  `status` tinyint(1) DEFAULT '0' COMMENT '关注状态(0关注,1取消)',
  `follow_time` datetime DEFAULT NULL COMMENT '创建时间',
  PRIMARY KEY (`id`),
  UNIQUE KEY `fans_followed_index` (`fans_id`,`followed_id`)
) ENGINE=InnoDB AUTO_INCREMENT=6 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='粉丝-关注-关系表';

2.2、接口设计 

2.2.1、点赞接口

1.新增作品点赞(作品ID、用户ID、时间戳)
2.取消作品点赞(作品ID、用户ID)
3.瀑布流查看作品连带赞数 
4.作品详情页面查询带出点赞数 
5.个人中心分页查出自己点赞作品 
6.他人个人中心分页查出他人点赞作品 

2.2.2、粉丝接口

1.新增关注(批量)、取消关注(批量)
2.查看粉丝(倒序、相互关注特显)
3.查看关注(倒序、相互关注特显)

三、使用案例 

3.1、点赞、取消

private final RedisTemplate redisTemplate;

/**
 * 作品点赞/取消
 */
@GetMapping("/workLikeOrCancel")
public R workLikeOrCanal(@RequestBody Work work){
	// 作品ID 
	Long workId = works.getId();
	// 用户ID 
	Long userId = works.getUserId();
	// 作品点赞 key 
	String workLikeKey = "workLikeKey:" + workId;
	// 用户点赞 key 
	String userLikeKey = "userLikeKey:" + userId;
	
	boolean workFlag = redisTemplate.hasKey(workLikeKey);
	if(!workFlag){
		// Redis无数据,到DB里拉取数据
		// DB数据无数据,Redis中设置为 0 
	}
	boolean userFlag = redisTemplate.hasKey(userLikeKey);
	if(!userFlag){
		// Redis无数据,到DB里拉取数据
		// DB数据无数据,Redis中设置为 0 
	}
	// 判断此用户是否已点赞
	boolean falg = redisTemplate.opsForHash().hasKey(userId,workId);
	// 执行取消点赞逻辑
	if(falg){
		// 作品-总点赞记录-减
		redisTemplate.opsForSet().members(workLikeKey).remove(userId);
		// 用户-个人赞记录-减
		redisTemplate.opsForHash().delete(userLikeKey,workId);
		// 获取作品-总点赞
		Long size = redisTemplate.opsForSet().size(workLikeKey);
		return R.ok("Success",size);
	}else { // 执行点赞逻辑
		// 作品-总点赞记录-加
		redisTemplate.opsForSet().add(workLikeKey,userId);
		// 用户-个人点赞记录-加
		redisTemplate.opsForHash().put(userLikeKey,workId,new Date());
		// 获取作品-总点赞
		Long size = redisTemplate.opsForSet().size(workLikeKey);
		return R.ok("Success",size);
	}
}

3.2、同步点赞数据

1.个人点赞明细同步
触发时机:
进入作品首页、刷新作品、分页1000次时
执行逻辑:取出Redis里个人点赞数据 mapRe;DB查出旧数据 mapDb;mapRe 比 mapDb 多出的数据为新增点赞;mapDb 比 mapRe 多出的数据为取消点赞。

2.作品点赞总数同步
空闲时间定时执行

3.3、查询作品点赞接口

/**
 * Redis、DB双向查询
 */
@GetMapping("/queryWorkLikes")
public R workUnLike(@RequestBody Comment work){
	Long workId = work.getWorkId();
	String workLikeKey = "workLikeKey:"+ workId;
    // 获取作品-总点赞
	Long size = redisTemplate.opsForSet().size(workLikeKey);
	// Redis 无数据再查DB......略
	return R.ok("Success",size);
}

3.4、查询个人点赞作品接口 

/**
 * DB、Redis 双向查询
 */
@GetMapping("/queryUserkLikes")
public R queryUserkLikes(@RequestBody Comment work){
	Long userId = work.getUserId();
	String userKey = "userKey:"+ userId;
    // 获取用户-总点赞
	Long size =  redisTemplate.opsForHash().size(userKey);
	// Redis 无数据再查DB......略
	return R.ok("Success",size);
}

你可能感兴趣的:(数据库)