简体   繁体   中英

Firebase.firestore() is not a function?

We are trying to convert this json object timestamp:

Object {
  "_nanoseconds": 725000000,
  "_seconds": 1621386976,
}

to a firebase timestamp:

t {
  "nanoseconds": 725000000,
  "seconds": 1621386976,
}

Our code where the error is being thrown:

const lastItemIndex = thoughts.length - 1;
console.log(thoughts[lastItemIndex].date_created); // <--- logs Object timestamp

const seconds = thoughts[lastItemIndex].date_created._seconds;
console.log(seconds); // <--- logs seconds

const nanoseconds = thoughts[lastItemIndex].date_created._nanoseconds;
console.log(nanoseconds); // <---- logs nanoseconds

const lastDate = Firebase.firestore().Timestamp(seconds, nanoseconds); // <--- error
console.log(lastDate);

We are importing Firebase in our file like so:

import Firebase from '../../firebase';

And within the firebase.js file:

import * as firebase from 'firebase/app';

// Optionally import the services that you want to use
import 'firebase/firestore';

The warning we get:

[Unhandled promise rejection: TypeError: _firebase.default.firestore().Timestamp is not a function. (In '_firebase.default.firestore().Timestamp(seconds, nanoseconds)', '_firebase.default.firestore().Timestamp' is undefined)]

We have also tried the following:

const lastDate = new Firebase.firestore.Timestamp(seconds, nanoseconds);

and get the following error:

[Unhandled promise rejection: TypeError: undefined is not a constructor (evaluating 'new _firebase.default.firestore.Timestamp(seconds, nanoseconds)')]

We are following the docs to no avail. How can we convert this correctly?

Edit

exporting both Time_stamp and Firebase breaks the app [ the rest of the app does not recognize the Firebase export ]

export default Firebase makes everything back to normal. But the issue of converting the timestamp still remains

// Initialize Firebase

export const Firebase = firebase.initializeApp(firebaseConfig);
export const Time_stamp = firebase.firestore.Timestamp();

// export default Firebase;

The problem lies in how you are importing & exporting the library.

Reviewing your code

If this is where you are importing from the main library, you also need to make sure you are exporting it correctly. Looking at your current firebase.js file:

import * as firebase from 'firebase/app';

// Optionally import the services that you want to use
import 'firebase/firestore';

/* ... */

// Initialize Firebase

const Firebase = firebase.initializeApp(firebaseConfig);

export default Firebase; // <- this is a firebase.app.App not firebase itself

You are exporting an instance of firebase.app.App instead of firebase (the whole firebase library & namespace).

When you have an firebase.app.App instance, you can access Firestore of that app using app.firestore() . Because you import this app instance as Firebase in your main code, you confuse this with the normal firebase.firestore() which does something else.

To help illustrate the difference, take a look at this:

import * as firebase from "firebase/app";
import "firebase/firestore";

const config = { /* ... */ };

const defaultFirebaseApp = firebase.initializeApp(config);

// the instance of Firestore for the default app
const dbApp = defaultFirebaseApp.firestore();

// the instance of Firestore for the default app
const dbDefault = firebase.firestore();
// OR
// const dbDefault = firebase.firestore(dbApp);

console.log(dbApp === dbDefault); // -> true

const namedFirebaseApp = firebase.initializeApp(config, "something");

const dbNamedApp = namedFirebaseApp.firestore(); // returns instance of Firestore for the named app
// OR
// const dbNamedApp = firebase.firestore(dbNamedApp);

console.log(dbDefault === dbNamedApp); // -> false

Recommended export style

To properly export the Firebase library from firebase.js , you need to (and should) be using:

import firebase from 'firebase/app';
import 'firebase/firestore';

/* ... */

// Initialize Firebase

firebase.initializeApp(firebaseConfig);

export default firebase; // re-export firebase library & namespace

By re-exporting the library this way, you can use it in the same way as all the code samples you encounter:

import firebase from '../../firebase';

const {_nanoseconds, _seconds} = thoughts[lastItemIndex].date_created;
const dateCreatedAsTimestamp = new firebase.firestore.Timestamp(_nanoseconds, _seconds);

const db = firebase.firestore();

db.doc("collection/doc")
  .set({
    date_created: dateCreatedAsTimestamp
  })
  .then(
    () => console.log("success"),
    (err) => console.error("failed", err);
  );

Alternative export style

If you intend to add some utility functions to firebase.js , the way you import stuff changes slightly

import firebase from 'firebase/app';
import 'firebase/firestore';

/* ... */

// Initialize Firebase

export const defaultApp = firebase.initializeApp(firebaseConfig);

export function castToTimestamp(timestampLikeObject) {
  const {_nanoseconds, _seconds} = timestampLikeObject;
  return new firebase.firestore.Timestamp(_nanoseconds, _seconds);
}

export default firebase; // re-export firebase library & namespace as the default

With the above file, you would instead import it as:

// you can import this normally like in the other example, but we'll
// include some of the other exports (like the utility function)
import firebase, { castToTimestamp } from '../../firebase';

const {_nanoseconds, _seconds} = thoughts[lastItemIndex].date_created;
const dateCreatedAsTimestamp = new firebase.firestore.Timestamp(_nanoseconds, _seconds);
// OR
// const dateCreatedAsTimestamp = castToTimestamp(thoughts[lastItemIndex].date_created);

const db = firebase.firestore();

db.doc("collection/doc")
  .set({
    date_created: dateCreatedAsTimestamp
  })
  .then(
    () => console.log("success"),
    (err) => console.error("failed", err);
  );

The following works:

export const timestamp = firebase.firestore.Timestamp;
let bob = new timestamp();
console.log("bob, bob);

NOTE:

firebase.firestore.Timestamp()

NOT

firebase.firestore().Timestamp()

https://firebase.google.com/docs/reference/js/firebase.firestore.Timestamp

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM