项目技术栈
微信原生小程序+云开发。为什么选择微信原生小程序进行开发呢?因为能够直接应用它的云开发能力吖。
我这里主要使用了云开发能力中的小程序端SDK,说白了就是在javascript中就能直接操作数据库。
本篇前言
基于云开发的答题活动小程序v2.0的源码地址,以及手把手教你搭建答题活动小程序v1.0系列文章目录,均在【基于云开发的答题活动小程序v2.0,终于赶在11月最后一天完成了】这篇文章的底部。
还记得我在答题活动小程序v1.0的时候,是怎么实现用云开发实现查询题库功能吗?不记得的话,可以重温一下这篇文章【手把手教你搭建消防安全答题小程序-用云开发实现查询题库功能】,这种是顺序出题的方式。
现在答题活动小程序v2.0版本,要换成随机出题方式,所以,我使用了云开发的聚合能力实现从题库中随机出题功能。
先查文档
通读文档,我们先对实现原理有个大概了解。有针对性的简单地看看几个相关的概念,暂时看不懂也没关系,可以只关注后面的实战部分。
1、数据库聚合能力说明
聚合是一种数据批处理的操作。有了聚合能力,可以方便的解决很多没有聚合能力时无法实现或只能低效实现的场景,这类场景的例子有:分组查询、随机选取、去重......
2、数据库Aggregate
Aggregate,数据库集合的聚合操作实例。
3、涉及到的方法
(1)Collection.aggregate(): Aggregate
发起聚合操作,定义完聚合流水线阶段之后需调用 end 方法标志结束定义并实际发起聚合操作。
(2)Aggregate.match(object: Object): Aggregate
聚合阶段。根据条件过滤文档,并且把符合条件的文档传递给下一个流水线阶段。
(3)Aggregate.sample(size: number): Aggregate
聚合阶段。随机从文档中选取指定数量的记录。
(4)Aggregate.end(): Promise
标志聚合操作定义完成,发起实际聚合操作。
4、特别关注sample
以上那些方法是我这次涉及到的几个API,这里特别关注一下.sample()这个API。
Aggregate.sample(size: number): Aggregate
聚合阶段。随机从文档中选取指定数量的记录。
API 说明
sample 的形式如下:
sample({
size: <正整数>
})
请注意:size 是正整数,否则会出错。
示例
假设文档 users 有以下记录:
{ "name": "a" }
{ "name": "b" }
随机选取
如果现在进行抽奖活动,需要选出一名幸运用户。那么 sample 的调用方式如下:
db.collection('users')
.aggregate()
.sample({
size: 1
})
.end()
返回了随机选中的一个用户对应的记录,结果如下:
{ "_id": "696529e4-7e82-4e7f-812e-5144714edff6", "name": "b" }
来实战吧
这段代码实现了随机出题的功能,直接上代码,稍微简单解读一下。
// 获取题库-函数定义
getQuestionList() {
// 数据库集合的聚合操作实例
activityQuestion
.aggregate()
.match({ //类似于where,对记录进行筛选
true: _.exists(true)
})
.sample({
size: 20
})
.end()
.then(res => {
// 在控制台打印数据
console.log(res.list)
let data = res.list || [];
// 将数据从逻辑层发送到视图层,通俗的说,也就是更新数据到页面展示
this.setData({
questionList:data
});
})
}
再看效果
可以在控制台中看到[云数据库] [activityQuestion] 查询成功了,返回了20条从题库中随机选取的题目数据。
本篇小结
可以看到,云开发能力,真的极大地提升了开发效率。其实不仅仅是在答题小程序中,会存在这样或那样的需求,需要在题库中随机出题。还有上面提到的,如果进行抽奖活动,需要选出一名或多名幸运用户。实践证明,那么 sample ,就是最佳选择之一了。