传入的对象的每个 构成一个筛选条件,有多个 <key, value> 则表示需同时满足这些条件,是的关系,如果需要关系,可使用 command.or)

    比如找出未完成的进度 50 的待办事项:

    假设在集合中有如下一个记录:

    1. {
    2. "style": {
    3. "color": "red"
    4. }
    5. }

    如果我们想要找出集合中 style.colorred 的记录,那么可以传入相同结构的对象做查询条件或使用 ”点表示法“ 查询:

    1. // 方式一
    2. db.collection('todos').where({
    3. style: {
    4. color: 'red'
    5. }
    6. }).get()
    7. // 方式二
    8. db.collection('todos').where({
    9. 'style.color': 'red'
    10. }).get()

    # 匹配数组

    假设在集合中有如下一个记录:

    1. {
    2. "numbers": [10, 20, 30]
    3. }

    可以传入一个完全相同的数组来筛选出这条记录:

    1. db.collection('todos').where({
    2. }).get()

    # 匹配数组中的元素

    如果想找出数组字段中数组值包含某个值的记录,那可以在匹配数组字段时传入想要匹配的值。如对上面的例子,可传入一个数组中存在的元素来筛选出所有 numbers 字段的值包含 20 的记录:

    1. db.collection('todos').where({
    2. numbers: 20
    3. }).get()

    # 匹配数组第 n 项元素

    如果想找出数组字段中数组的第 n 个元素等于某个值的记录,那在 <key, value> 匹配中可以以 字段.下标key,目标值为 value 来做匹配。如对上面的例子,如果想找出 number 字段第二项的值为 20 的记录,可以如下查询(注意:数组下标从 0 开始):

    更新也是类似,比如我们要更新 _idtest 的记录的 numbers 字段的第二项元素至 30:

    1. db.collection('todos').doc('test').update({
    2. data: {
    3. 'numbers.1': 30
    4. },

    # 结合查询指令进行匹配

    1. const _ = db.command
    2. db.collection('todos').where({
    3. numbers: _.gt(25)
    4. }).get()

    查询指令也可以通过逻辑指令组合条件,比如找出所有 numbers 数组中存在包含大于 25 的值、同时也存在小于 15 的值的记录:

    1. const _ = db.command
    2. db.collection('todos').where({
    3. numbers: _.gt(25).and(_.lt(15))
    4. }).get()

    # 匹配并更新数组中的元素

    如果想要匹配并更新数组中的元素,而不是替换整个数组,除了指定数组下标外,还可以:

    1. 更新数组中第一个匹配到的元素

    更新数组字段的时候可以用 字段路径.$ 的表示法来更新数组字段的第一个满足查询匹配条件的元素。注意使用这种更新时,查询条件必须包含该数组字段。

    假如有如下记录:

    1. {
    2. "_id": "doc1",
    3. "scores": [10, 20, 30]
    4. }
    5. {
    6. "_id": "doc2",
    7. "scores": [20, 20, 40]
    8. }

    让所有 scores 中的第一个 20 的元素更新为 25:

    1. // 注意:批量更新需在云函数中进行
    2. const _ = db.command
    3. db.collection('todos').where({
    4. scores: 20
    5. }).update({
    6. data: {
    7. 'scores.$': 25
    8. }
    9. })

    如果记录是对象数组的话也可以做到,路径如 字段路径.$.字段路径

    注意事项:

    • 不支持用在数组嵌套数组
    • 如果用 unset 更新操作符,不会从数组中去除该元素,而是置为 null
    • 如果数组元素不是对象、且查询条件用了 neqnotnin,则不能使用 $

    2. 更新数组中所有匹配的元素

    假如有如下记录:

    比如让 scores.math 字段所有数字加 10:

    1. const _ = db.command
    2. data: {
    3. 'scores.math.$[]': _.inc(10)
    4. }

    更新后 scores.math 数组从 [10, 20, 30] 变为 [20, 30, 40]

    如果数组是对象数组也是可以的,假如有如下记录:

    1. {
    2. "_id": "doc1",
    3. "scores": {
    4. "math": [
    5. { "examId": 1, "score": 10 },
    6. { "examId": 2, "score": 20 },
    7. { "examId": 3, "score": 30 }
    8. ]
    9. }
    10. }

    可以更新 scores.math 下各个元素的 score 原子自增 10:

    1. const _ = db.command
    2. db.collection('todos').doc('doc1').update({
    3. data: {
    4. 'scores.math.$[].score': _.inc(10)
    5. }
    6. })

    上面所讲述的所有规则都可以嵌套使用的,假设我们在集合中有如下一个记录:

    1. {
    2. "root": {
    3. "objects": [
    4. {
    5. "numbers": [10, 20, 30]
    6. },
    7. {
    8. "numbers": [50, 60, 70]
    9. }
    10. ]
    11. }
    12. }

    我们可以如下找出集合中所有的满足 root.objects 字段数组的第二项的 numbers 字段的第三项等于 70 的记录:

    1. db.collection('todos').where({
    2. 'root.objects.1.numbers.2': 70
    3. }).get()

    注意,指定下标不是必须的,比如可以如下找出集合中所有的满足 root.objects 字段数组中任意一项的 numbers 字段包含 30 的记录:

    更新操作也是类似,比如我们要更新 _idtestroot.objects 字段数组的第二项的 numbers 字段的第三项 为 80:

    1. db.collection('todos').doc('test').update({
    2. data: {
    3. 'root.objects.1.numbers.2': 80
    4. })