# Querying Data

The get method is provided for both records and collections to get data of a single record or of multiple records in a collection.

Suppose we have a todos collection, which contains records of the following format:

[
  {
    _id: 'todo-identifiant-aleatoire',
    _openid: 'user-open-id', // Assume the user's openid is user-open-id
    description: "learn cloud database",
    due: Date("2018-09-01"),
    progress: 20,
    tags: [
      "cloud",
      "database"
    ],
    style: {
      color: 'white',
      size: 'large'
    },
    location: Point(113.33, 23.33), // 113.33°E, 23.33°N
    done: false
  },
  {
    _id: 'todo-identifiant-aleatoire-2',
    _openid: 'user-open-id', // Assume the user's openid is user-open-id
    description: "write a novel",
    due: Date("2018-12-25"),
    progress: 50,
    tags: [
      "writing"
    ],
    style: {
      color: 'yellow',
      size: 'normal'
    },
    location: Point(113.22, 23.22), // 113.22°E, 23.22°N
    done: false
  }
  // more...
]

# Getting the Data of a Record

Let's first look at how to get the data of a record. Suppose we have a record with the ID todo-identifiant-aleatoire in the "todos" collection. We can get the data of this to-do list by calling the get method via the reference in that record.

db.collection('todos').doc('todo-identifiant-aleatoire').get({
  success: function(res) {
    // res.data contains the data of that record
    console.log(res.data)
  }
})

It can also be called using Promise style:

db.collection('todos').doc('todo-identifiant-aleatoire').get().then(res => {
  // res.data contains the data of that record
  console.log(res.data)
})

# Getting the Data of Multiple Records

We can also get multiple records at a time. Specify the query condition by calling the where method on the collection. Then, call the get method to return the records that meet the specified query condition. For example, to get all unfinished to-dos from a user:

db.collection('todos').where({
  _openid: 'user-open-id',
  done: false
})
.get({
  success: function(res) {
    // res.data is an array containing the two records defined above
    console.log(res.data)
  }
})

The where method receives an object parameter, in which each field and its value constitute a matching condition that must be satisfied. The relationship among the fields is "and", which means these matching conditions must be satisfied at the same time. In this example, we query the records in the "todos" collection that have _openid equal to user-open-id and done equal to false. In the query condition, we can also specify that the records must match the value of a nested field. For example, to find your own to-dos marked in yellow:

db.collection('todos').where({
  _openid: 'user-open-id',
  style: {
    color: 'yellow'
  }
})
.get({
  success: function(res) {
    console.log(res.data)
  }
})

Nested fields can be expressed using "dot notation":

db.collection('todos').where({
  _openid: 'user-open-id',
  'style.color': 'yellow'
})
.get({
  success: function(res) {
    console.log(res.data)
  }
})

# Getting Data from a Collection

To get the data from a collection, for example, to get all the records in the "todos" collection, the get method can be used. However, we do not recommend this approach. In the Mini Program, we need to avoid getting too much data at a time and only get the necessary data. To prevent incorrect operations and protect the Mini Program user experience, the server only returns a maximum of 20 records at a time when getting collection data. For cloud functions, this value is 100. Developers may specify the number of records (no more than 20 for Mini Programs or 100 for cloud functions) to be obtained using the limit method.

db.collection('todos').get({
  success: function(res) {
    // res.data refers to the data of all records (no more than 20) to which the user has access permission in the collection
    console.log(res.data)
  }
})

It can also be called using Promise style:

db.collection('todos').get().then(res => {
  // res.data refers to the data of all records (no more than 20) to which the user has access permission in the collection
  console.log(res.data)
})

In the example below, a cloud function gets all records in a collection. Because the cloud function cannot get more than 100 records at a time, a single request may not be able to get all the data, so you must get the data in batches:

const cloud = require('wx-server-sdk')
cloud.init()
const db = cloud.database()
const MAX_LIMIT = 100
exports.main = async (event, context) => {
  // Get the total number of the collection records first
  const countResult = await db.collection('todos').count()
  const total = countResult.total
  // Calculate in how many times you can get it
  const batchTimes = Math.ceil(total / 100)
  // Carry all the promise arrays with read
  const tasks = []
  for (let i = 0; i < batchTimes; i++) {
    const promise = db.collection('todos').skip(i * MAX_LIMIT).limit(MAX_LIMIT).get()
    tasks.push(promise)
  }
  // Wait all
  return (await Promise.all(tasks)).reduce((acc, cur) => {
    return {
      data: acc.data.concat(cur.data),
      errMsg: acc.errMsg,
    }
  })
}