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
Related
// db.js file
import * as firebase from "firebase/app"
import "firebase/database"
const config = {
apiKey: "" ...
}
const db = firebase.initializeApp(config)
export default db
// App.vue file
import { reactive, onMounted, ref } from 'vue'
import db from "./db.js";
const SendMessage = () => {
const messagesRef = db.database().ref("messages")
if(inputMessage.value === "" || inputMessage.value === null) {
return
}
const message = {
username: state.username,
content: inputMessage.value
}
messagesRef.push(message)
inputMessage.value = ""
}
I try to make a little chat app with Vue.js and Firebase.
So i don't understand because i receive this when i try to send a message :
db_js__WEBPACK_IMPORTED_MODULE_1_.default.database is not a function
at Proxy.SendMessage (App.vue?3dfd:63:1)
I think it's about the import but i try to change for the V9 of firebase but that's didn't work.
Firebase V9 is build in functional aproach. Im working with firestore usually give me a sign if some thing not working.
db.js
import { initializeApp } from 'firebase/app';
import { getDatabase, ref, push, child, serverTimestamp } from 'firebase/database'
const config = {
apiKey: "" ...
}
const firebase = initializeApp(config)
const db = getDatabase()
function addMessage(path, message) {
message.createAt = serverTimestamp() // On database side database will assign current
// timestamp to this field so you will be able to order data
// from newest to oldest for example.
return push(child(ref(db, path)), message)
}
export { addMessage }
App.vue file
import { reactive, onMounted, ref } from 'vue'
import { addMessage } from "./db.js";
const SendMessage = async () => {
if (!inputMessage.value) return
// line above will check are value is "" or null by throwing
// false and using ! in front you changing it to true.
const message = {
username: state.username,
content: inputMessage.value
}
const result = await addMessage('path to data in tree', message)
// async/await will await until data is saved in database and then will do code bellow.
console.log(result.key) // If you await you can read result if result is not void.
inputMessage.value = ""
}
If you use ref() in .vue files make database operations outside of vue files database have same ref() function but they work different. You can allso change name of one function in import line import { ref as dbRef } from 'firebase/database'
Inside my index.js file:
export function postArticleAPI(payload) {
return(dispatch) => {
const upload = storage
.ref(`images/${payload.image.name}`)
.put(payload.image);
upload.on("state_changed", (snapshot) => {
const progress = (
(snapshot.BytesTransferred / snapshot.totalBytes) * 100);
console.log(`Progress: ${progress}%`);
if(snapshot.state === "RUNNING") {
console.log(`Progress: ${progress}%`);
}
},
(error) => console.log(error.code),
async() => {
const downloadURL = await upload.snapshot.ref.getDownloadURL();
db.collection("articles").add({
...
});
});
}
};
}
I look in the docs provided by firebase but I am unsure how to implement that. When I run the code above, I get "TypeError: firebase__WEBPACK_IMPORTED_MODULE_0_.storage.ref is not a function" error.
I messed around with the code and I've also gotten other errors such as: "...storage.put is not a function," I've gotten errors with upload, as well as db.collection error.
Here's my firebase.js:
import { initializeApp } from 'firebase/app';
import { getAuth, GoogleAuthProvider } from 'firebase/auth';
import { getStorage } from "firebase/storage";
import { getFirestore } from "firebase/firestore";
const firebaseConfig = {
...
}
const firebaseApp = initializeApp(firebaseConfig);
const db = getFirestore(firebaseApp);
const auth = getAuth();
const provider = new GoogleAuthProvider();
const storage = getStorage(firebaseApp);
export { auth, provider, storage };
export default db;
Any help would be appreciated (and this is my first post, so please let me know if I need to add anything else). Thanks!
Since you're using the v9 syntax for importing top-level functions, there is no longer a storage.ref() method. Instead, as shown in the documentation on getting a reference and uploading files, you can do:
const ref = ref(storage, `images/${payload.image.name}`)
const upload = uploadBytes(ref, payload.image);
I am using React and trying to fetch an image URL from firebase Storage, displaying the image.
but
'ref' is not defined no-undef
is occurred.
https://firebase.google.com/docs/storage/web/create-reference
the official says "ref() is used to get image URL"
firebaseconfig.js
import firebase from 'firebase/app'
import 'firebase/firestore'
import 'firebase/auth'
import "firebase/storage"
// Your web app's Firebase configuration
// For Firebase JS SDK v7.20.0 and later, measurementId is optional
var firebaseConfig = {
//connection information
};
// Initialize Firebase
firebase.initializeApp(firebaseConfig);
firebase.firestore();
export const storage = firebase.storage();
const getImage = () =>{
ref = storage.ref().child('/img/thumbs/super_potato.jpeg');
ref.getDownloadURL().then((url) => {
document.getElementById('image').src = url;
});
}
return (
<div className="container section project-details">
<img id = "iamge" />
</div>
You didn't define ref before assigning a value to it.
Change:
ref = storage.ref().child('/img/thumbs/super_potato.jpeg');
to
let ref = storage.ref().child('/img/thumbs/super_potato.jpeg');
You can read more about no-undef on eslint
So, I'm working on a React project which uses Firebase to achieve lots of functionalities.
And now I'm trying to use some HTTPS callable functions in it.
But it seems like the way I import the 'firebase/functions' module is not correct. And it's giving me this error:
TypeError: Cannot read property 'httpsCallable' of undefined
Below is how I do the import and set up:
import app from 'firebase/app';
import 'firebase/auth';
import 'firebase/firestore';
import 'firebase/functions';
const config = {
// the config info here
};
class Firebase {
constructor() {
app.initializeApp(config);
this.auth = app.auth();
this.db = app.firestore();
this.functions = app.functions();
}
// trying to call the function
doCreatePlanner = this.functions.httpsCallable('createPlanner')
Can anyone point me to the right direction?
You are trying to access this.functions before you defined it in the constructor. To get rid of the error message, you could move the call to httpsCallable into the constructor:
constructor() {
app.initializeApp(config);
this.auth = app.auth();
this.db = app.firestore();
this.functions = app.functions();
const doCreatePlanner = this.functions.httpsCallable('createPlanner')
}
This is probably not exactly what you want to do, but in any event, you can't use this.functions until after you define it.
I am writing firebase functions with https, auth, and datastore triggers, so I would like to factor them out to different files. I have factored out the https functions but I am not sure how to factor out the auth function. My index.ts is currently:
import * as express from 'express';
import * as functions from 'firebase-functions';
import { spiceAdmin } from './base';
import { spiceServer } from './spiceServer'
import { server } from './api-routes/api'
exports.app = functions.https.onRequest(server);
/**
#Use: send verification email on new user creation
*/
exports.onCreate = functions.auth.user().onCreate( user => {
spiceAdmin.auth().createUser({
email : 'user-auth-ts#gmail.com'
, emailVerified : false
, password : 'Sup3rSafe'
})
.then((userRecord : any) => console.log('created new user'))
.catch((err : string) => console.log(`failed to create new user with ${err}`))
});
Specifically, if I had a file user_auth.ts with triggers onCreate and onChange, how would I syntactically write those functions, export then, and exports.... them in index.ts?
index.ts
import { myFunction } from './myfunction'
export const myFunction_export = myFunction
myfunction.ts
import * as functions from 'firebase-functions'
export const myFunction = functions.firestore.document(...).onCreate(...)