这是我参与「第五届青训营 」伴学笔记创作活动的第 11 天
一、本堂课重点内容:
- 项目实践
二、详细知识点介绍:
- 项目实践
4.5 组件工具
Go Mod:
go mod init
go get gopkg.in/gin-gonic/gin.v1@v1.3.0
4.6 Repository
数据格式:
- Topic
{
"id":1,
"title":"青训营来啦!",
"content":"小姐姐,快到碗里来~",
"create_time":1650437625
}
- Post
{
"id":1,
"parent_id":1,
"content":"小姐姐快来1",
"create_time":1650437616
}
对于这两个结构体,我们在Repository层需要实现两个基本的查询操作:
- QueryTopicById:通过话题的ID查询话题
- QueryPostsByParentId:通过话题ID查询话题关联的所有帖子列表
4.6 Repository——index
因为数据以文件形式存储,所以我们可以采用全扫描遍历的方式来获取需要的数据,类似于MySQL中的全表扫描。
但这样并非是最高效的方式,因此我们引入索引的概念。
索引类似于目录,通过目录我们可以快速定位想要查找的结果。
根据我们的需求,我们将数据行映射成内存中的Map来实现内存的索引。
var (
topicIndexMap map[int64]*Topic
postIndexMap map[int64][]*Post
}
下面是初始化话题内存索引的一个实例:
4.6 Repository——查询
下面是一个查询的实例:
其中,索引为话题ID,数据为话题。
这里利用了一个sync.Once的关键字,这个Once主要适合在高并发场景下只执行一次的场景,即单例模式,可以减少存储的浪费。
4.7 Service
实体:
type PageInfo struct{
Topic *repository.Topic
PostList []*repository.Post
}
流程:
代码流程编排:
checkParam:校验ID
perpareInfo:从Repository中两个查询方法获取相应的数据
因为获取话题信息和回帖信息都依赖于TopicID,两个流程没有前后的相互依赖,对于这种情况我们考虑使用并行执行,提高执行效率。
4.8 Controller
Code:一个状态码,代表成功或其他情况
msg:具体状态信息
data:数据
4.9 Router
业务逻辑已经完成,下面通过Gin搭建外部框架。
- 初始化数据索引:
Init("./data/")
- 初始化引擎配置
r := gin.Default()
- 构建路由
r.GET("/community/page/get/:id",func(c *gin.Context){
topicId := c.Param("id")
data := cotroller.QueryPageInfo(topicId)
c.JSON(200,data)
})
- 启动服务
r.Run()
4.10 运行
通过go run server.go启动服务。
与服务器与客户端交互一般是暴露一些HTTP接口,客户端拿到这些JSON化的responce来渲染页面。
三、引用参考: