无法使用时间戳从Firebase获取数据

时间:2019-11-08 23:03:14

标签: javascript firebase google-cloud-firestore

我正在尝试使用createdAt属性(它是一个时间戳)从我的集合中获取一个值。 这大致就是我的查询的样子:

function getDataFromYesterdayToNow (db){
  const now = new Date()
  const yesterday = new Date(now.setDate(now.getDate() - 1))
  yesterday.setHours(0, 0, 0, 0)

  const { Timestamp } = firebase.firestore

  return db
    .collection('myData')
    .where('createdAt', '>=', Timestamp.fromDate(yesterday))
    .where('createdAt', '<=', Timestamp.fromDate(now))
    .get()
}

但是,当我运行它时,出现以下错误:

  

错误为'FirebaseError:[code = invalid-argument]:函数Query.where()用无效数据调用。不支持的字段值:自定义时间戳对象。 Stacktrace是'FirebaseError:函数Query.where()用无效数据调用。不支持的字段值:自定义的时间戳记对象

我很困惑,我一直在使用其他集合中的Timestamp对象来获取数据,如果我尝试仅使用date对象,它将无法正常工作。我忘记了什么吗?

编辑:根据要求,以下是我的文档的示例:

{
  name: "My Data Name", // (string)
  createdAt: November 9, 2018 at 8:40:45 PM // (Timestamp)
}

1 个答案:

答案 0 :(得分:1)

我有同样的问题。您需要检查两件事。

1。我在使用正确的SDK吗?

您知道您可以使用两种不同的firebase SDK吗?一个是客户端SDK firebase-js-sdk,又名firebase包),另一个是firebase 服务器SDK nodejs-firestore。aka @google-cloud/firebase包)。这两个库在firestore.Timestamp类上有自己的实现,并且它们不兼容

一些其他NPM软件包的依赖关系如下:

"@firebase/firestore" (*)
  -> "firebase" (client SDK which imports all @firebase/* except @firebase/testing)
    -> "@angular/fire" (and other client libraries with firebase binding)
    -> "@firebase/testing" (mocking Firestore client)

"@google-cloud/firebase" (*) (server SDK)
  -> "firebase-admin"
    -> "firebase-functions-test"

(*)表示firestore.Timestamp定义的位置。

简而言之,您应该使用相应的时间戳记。

情况1.仅使用客户端SDK

import { firestore, initializeApp } from 'firebase';
import { config } from './my-firebase-config';

const app = initializeApp(config);
app.firestore().collection('users')
  .where('createdAt', '<=', firestore.Timestamp.fromDate(new Date()))
  .get();

案例2。仅使用服务器SDK

import { firestore, initializeApp } from 'firebase-admin';

const app = initializeApp();
app.firestore().collection('users')
  .where('createdAt', '<=', firestore.Timestamp.fromDate(new Date()))
  .get();

案例3。混合SDK

有时候,当您测试在服务器上运行的代码(例如firebase函数)时,需要使用客户端SDK(特别是@firebase/testing

// server.ts
import { firestore, initializeApp } from 'firebase-admin';

const app = initializeApp();
app.firestore().collection('users')
  .where('createdAt', '<=', fs.Timestamp.fromDate(new Date()))
  .get();
// server.test.ts
import { firestore } from 'firebase';
import { initializeAdminApp } from '@firebase/testing';

// Replace server sdk with client sdk
jest.mock('firebase-admin', () => ({
  firestore,
  initializeApp: () => initializeAdminApp()
}));

2。我使用的版本正确吗?

如果您使用的是正确的SDK,那么接下来要检查的是您是否使用了相同版本的Timestamp实现。例如,如果您使用的是Client SDK,则应检查package-lock.json是否具有唯一版本的firebase

对于我来说,我在不同的时间安装了@firebase/testingfirebase,并且由于firebase@firebase/testing的版本依赖性不同,所以我有两个不同的{{ 1}}软件包同时安装。您可以更新旧软件包来解决此问题。