从Firebase通过ID获取数据

时间:2019-12-11 09:54:53

标签: node.js database firebase firebase-realtime-database

我在node.js上使用firebase。

我给定的结构应如下所示:

{
...
batch-1:
        id-1(suppose):
                     name:...
                     phone:...
        id-2:
             ...
        id-3:
             ...
batch-2:
        ...
batch-3:
        ...
...


batch-n:
       ...
}

在这样的体系结构中,如何通过其标识符获取id-1对象? 数据库是否必须遍历所有批次? 有更好的解决方案吗? 主要任务:创建包含许多对象的批处理,这些对象将具有SHORT和UNIQUE标识符,并以此标识符最佳地接收数据

2 个答案:

答案 0 :(得分:0)

要搜索作为未知ID列表的子代的特定ID,您需要使用orderByChild()。在您的用例中,您正在批次ID列表中寻找特定的ID。如果您在此列表上使用了orderByChild(),则即使每个批次ID都没有您想要的ID,您也会获得结果。这是因为结果中甚至包括了null(不存在)值(并在开始时对其进行了排序)。要获取所需ID的数据,您将获取查询的最后结果的数据(如果存在)为sorted to the end of the list。请注意,如果所需的ID不存在,则最后一个结果(如果有任何结果)将具有null值。要仅返回查询的最后结果,可以使用limitToLast(1)

将所有内容放在一起,给出以下代码:

let idToFind = "unique-id-1";

let batchesRef = firebase.database().ref(); // parent key of "batch-1", "batch-2", etc.
                                            // assumed to be the database root here

batchesRef.orderByChild(idToFind).limitToLast(1).once('value')
  .then((querySnapshot) => {
    if (!querySnapshot.numChildren()) { // handle rare no-results case
      throw new Error('expected at least one result');
    }
    let dataSnapshot; 
    querySnapshot.forEach((snap) => dataSnapshot = snap); // get the snapshot we want out of the query's results list

    if (!dataSnapshot.exists()) { // value may be null, meaning idToFind doesn't exist
      throw new Error(`Entry ${idToFind} not found.`);
    }

    // do what you want with dataSnapshot
    console.log(`Entry ${idToFind}'s data is:`, dataSnapshot.val());
  })
  .catch((error) => {
    console.log("Unexpected error:", error);
  })

对于小型数据集,上面的代码可以正常工作。但是,如果批次列表开始变得越来越大,您可能希望建立一个索引,将特定的ID映射到包含该ID的批次ID。

答案 1 :(得分:0)

这是我的方法,它允许您按 id 搜索或按键值搜索,例如 email uniqueemail

// gets primary key
const getSnapshotValKey = snapshot => (Object.keys(snapshot).length > 0 ? Object.keys(snapshot)[0] : null)

const getUser = async ({ id, key, value }) => {
  let user = null

  const ref = id ? '/users/' + id : 'users'
  const userRef = admin.database().ref(ref)

  const valueRef = id ? userRef : await userRef.orderByChild(key).equalTo(value)
  const snapshot = await valueRef.once('value')

  const val = snapshot.val()
  if (val) {
    const key = id || getSnapshotValKey(val)

    user = {
      id: key,
      ...(id ? val : val[key]),
    }
  }

  return user
}