I am trying to learn Firebase. I made a very simple ReactApp along with a very simple database in Firebase. I am so beyond confused as to how to access a field's value. I'm sure this is an extremely simple question, but somehow, I am missing how to find the solution.
My database looks as such:
https://imgur.com/a/3LczlwI
I really would like to know how to access the "Speed" field value.
I have tried
const db = firebase.database.ref();
const speedRef =
db.child('react').child('mySpeed').once('value').then(snap =>{
if (snap.val()){
this.setState({ speed: snap.val().speed });
} else {
console.log('error');
}
})
Along with
const speedRef = firebase.database().ref().child('mySpeed').child('speed');
speedRef.on('value', snap => {
this.setState({ speed: snap.val() });
})
To no avail. I really hope someone can help me understand this. Thank you in advance.
*try to use this: *
const react = firebase.database().ref("react");
react.child("mySpeed").child("speed").once("value").then(data => {
if(data.val() !== null){
console.log(data.val());
}
});
Related
I am very new to Firebase and JS itself as well, and it is not the easiest thing to understand.
So, I have a Firebase real time databse set up with dummy "users" profiles, that each contain different properties.
i am trying to call user's properties.
I have managed to achieved it with the following approach:
let installDateRef = database.ref(`users/${userAccount}/installationDate`);
let lastUsedDateRef = database.ref(`users/${userAccount}/lastUsed`);
installDateRef.on('value', function(snapshot) {
installationDate.innerText = (snapshot.val());
}, function (error) {
installationDate.innerText = `Error: ${error.code}`
});
lastUsedDateRef.on('value', function(snapshot) {
lastUsedDate.innerText = (snapshot.val());
}, function (error) {
lastUsedDate.innerText = `Error: ${error.code}`
});
But in my application I want to display all of the user information, so copying this ".on" function seems like overkill.
Someone said that there is cleaner approach like this below
const firebasePromises = [
database.ref(`users/${userAccount}/installationDate`),
database.ref(`users/${userAccount}/lastUsed`)
];
Promise.all(firebasePromises).then(([_installationDate, _lastUsed]) => {
installationDate.innerText = (_installationDate.val());
lastUsedDate.innerText = (_lastUsed.val());
})
But I honest to God cannot make it work. It either returns undefined or returns array of my promises const.
.val() does not work at all even, saying that this is not a function.
Any help would on the best and working practice would be soooo much appreciated.
Thank you
#Doug Stevenson thank you! This is exactly what was needed:
const firebasePromises = [
database.ref(`users/${userAccount}/installationDate`).once('value'),
database.ref(`users/${userAccount}/lastUsed`).once('value'),
];
Promise.all(firebasePromises).then(snap => {
installationDateHTML.innerText = snap[0].val();
lastUsedDateHTML.innerText = snap[1].val();
})
I'm starting to learn firebase with firestore.
I have spent more hours than I would've like understanding the reference type and trying to get it to work with a simple query that references a portfolio's category.
This is the code:
try {
const portfolioSnap = await db.collection("portfolio").get();
let portfolioDoc = portfolioSnap.docs;
let categoriesRef = [];
portfolioDoc.forEach(p => {
categoriesRef.push(p.data().category.get());
});
let categories = await Promise.all(categoriesRef);
let portfolio = [];
portfolioDoc.map((p, i) => {
let portfolioObject = {
...p.data(),
category: categories[i].data().name
};
portfolio.push(portfolioObject);
});
return portfolio;
} catch (error) {
console.warn("ERROR: ", error);
}
I'm not sure if this makes sense.
I'm trying to get the category for each portfolio document but I feel this is over-engineered or I'm totally doing it the wrong way.
And this is not counting if I have references for images or files which I feel would make things... well, not pretty.
Nothing strange here. This is the way that nosql databases work (since there is no join operation, nor is there any explicit relationships between documents other than what you define).
I have been trying to use Firebase Functions to write a simple method, but I am unfamiliar with JS.
Below is the structure of my Realtime Database
-spots
---is_hidden: false
---likes
------like_id_1: true
---dislikes
------dislike_id_1: true
I am trying to write a simple method that does the following: Whenever an entry is added to dislikes, count the likes and the dislikes.
If the number of dislikes is larger than the number of ( likes + 5 ),
change the value of is_hidden to true
This is my attempt to solving the problem
exports.checkHiddenStatus = functions.database.ref('/spots/{spotid}').onWrite(
(change, context) => {
const collectionRef = change.after.ref;
const isHiddenRef = collectionRef.child('is_hidden');
const likesRef = collectionRef.child('likes');
const dislikesRef = collectionRef.child('dislikes');
if(isHiddenRef.before.val()) return;
let likeCount = likesRef.numChildren();
let dislikeCount = dislikesRef.numChildren();
let isHidden = false;
if( dislikeCount >= (likeCount + 5))
isHidden = true;
if(!isHidden) return;
// Return the promise from countRef.transaction() so our function
// waits for this async event to complete before it exits.
return isHiddenRef.transaction((current) => {
return isHidden;
}).then(() => {
return console.log('Counter updated.');
});
});
Sadly, because I have no experience with JS I keep getting stuck with error messages I don't understand. The most recent being
TypeError: Cannot read property 'val' of undefined
at exports.checkHiddenStatus.functions.database.ref.onWrite (/user_code/index.js:28:28)
Can somebody please help me write this function? Thank you!
It looks like you're trying to treat a database Reference object like a Change object. Change has before and after properties, but a reference does not.
If you have a database reference object, and you want the value of the database at that location, you need to query it with its once() method.
Read more about reading and writing data using the Admin SDK.
I need to make some if statements for advanced filter search and also some if conditions to make a table filterable. Is there any way to make if statements based on Firebase. I need to make the output from Firebase true and false to replace with archived and display it in a dynamic table.
Thank you in advance.
e.g.
var usersRef = firebase.database().ref("users");
var query = usersRef.orderByChild("disabled").equalTo(true);
query.on("value", function(snapshot) {
snapshot.forEach(function(user) {
if (user.disabled != true) {
$('#ArchiveLabel').text("Archived");
} else {
$('#ArchiveLabel').text("");
}
}); });
You're looking for something along these lines:
var usersRef = firebase.database().ref("users");
var query = usersRef.orderByChild("something").equalTo(true);
query.on("value", function(snapshot) {
snapshot.forEach(function(user) {
console.log(user.key, user.val());
});
});
I highly recommend that you spend some time in the Firebase documentation, for example its section on ordering and filtering data. You also might benefit from taking the Firebase codelab for web developers.
I have a firebase database and I am currently trying to use cloud functions to perform an operation when a value in my database changes. So far, it successfully triggers code to run when the value in my database changes. However, when the database value changes, I now need to check another value to determine it's status, and then perform an action after that. The problem is that I have ~0 experience with JS and I have no way of debugging my code other than deploying, changing the value in my database, and looking at the console log.
Is there any way to look up another value in the database and read it? How about look up a value and then set a value for it? Here is the code:
exports.determineCompletion =
functions.database.ref('/Jobs/{pushId}/client_job_complete')
.onWrite(event => {
const status = event.data.val();
const other = functions.database.ref('/Jobs/' + event.params.pushId + '/other_job_complete');
console.log('Status', status, other);
if(status == true && **other.getValueSomehow** == true) {
return **setAnotherValue**;
}
});
This code partially works, it successfully gets the value associated with client_job_complete and stores it in status. But how do I get the other value?
Additionally, if anyone has any JS or firebase documentation that they think would help me, please share! I have read a bunch on firebase here : https://firebase.google.com/docs/functions/database-events but it only talks about events and is very brief
Thank you for your help!
When writing a database trigger function, the event contains two properties that are references to the location of the data that changed:
event.data.ref
event.data.adminRef
ref is limited to the permissions of the user who triggered the function. adminRef has full access to the database.
Each of those Reference objects has a root property which gives you a reference to the root of your database. You can use that reference to build a path to a reference in another part of your database, and read it with the once() method.
You can also use the Firebase admin SDK.
There are lots of code samples that you should probably look at as well.
I'm maybe a bit late, but I hope my solution can help some people:
exports.processJob = functions.database.ref('/Jobs/{pushId}/client_job_complete').onWrite(event => {
const status = event.data.val();
return admin.database().ref('Jobs/' + event.params.pushId + '/other_job_complete').once('value').then((snap) => {
const other = snap.val();
console.log('Status', status, other);
/** do something with your data here, for example increase its value by 5 */
other = (other + 5);
/** when finished with processing your data, return the value to the {{ admin.database().ref(); }} request */
return snap.ref.set(other).catch((error) => {
return console.error(error);
});
});
});
But take notice of your firebase database rules.
If no user should have access to write Jobs/pushId/other_job_complete, except Your cloud function admin, You need to initialize Your cloud function admin with a recognizable, unique uid.
For example:
const functions = require('firebase-functions');
const admin = require('firebase-admin');
const adminCredentials = require('path/to/admin/credentials.json');
admin.initializeApp({
credential: admin.credential.cert(adminCredentials),
databaseURL: "https://your-database-url-com",
databaseAuthVariableOverride: {
uid: 'super-special-unique-firebase-admin-uid'
}
});
Then Your firebase database rule should look something like this:
"client_job_complete": {
".read": "auth !== null",
".write": "auth.uid === 'super-special-unique-firebase-admin-uid'"
}
Hope it helps!
You have to wait on the promise from a once() on the new ref, something like:
exports.processJob = functions.database.ref('/Jobs/{pushId}/client_job_complete')
.onWrite(event => {
const status = event.data.val();
const ref = event.data.adminRef.root.child('Jobs/'+event.params.pushId+'/other_job_complete');
ref.once('value').then(function(snap){
const other = snap.val();
console.log('Status', status, other);
if(status && other) {
return other;
}
});
});
Edit to fix the error that #Doug Stevenson noticed (I did say "something like")