How to navigate an object and insert it into an array
What am I working with
- angular2
- firebase
What do I have
- Returned object
- Each element of the object has a URL property
What i would like to do
- Loop through each item in the object and get the URL property
- Pass this to firebase storage variable
- Push the URL property into an array to make it available to my HTML
note: I have a url hardcoding job, I just need object related help to get other urls in the object.
Component.ts
'this.imagesToDisplay' will return an object object (image below)
this.activatedRoute.data
.subscribe((
data: { issueData: any, issueImageData: any }) => {
this.issueToDisplay = data.issueData;
this.imagesToDisplay = data.issueImageData;
this.testing(this.imageToDisplayArray);
});
TS Component - Test Method
So this is hardcoded and pushes the hardcoded url into an array and renders correctly via HTML data binding. Cool. However, I would like to go through the imagesToDisplay object and get both returned urls.
testing(imageToDisplayArray) {
// this works with one url
var storage = firebase.storage().ref().child("image/-Kosd82P-bmh4SFetuf3/-Kosd8HhGmFiUhYMrlvw/30DD9F39-4684-4AA0-9DBF-3B0F0C3450A4.jpg");
storage.getDownloadURL().then(function(url) {
imageToDisplayArray.push(url);
console.log(imageToDisplayArray);
});
}
Any help here would be widely appreciated.
Note . I think this question is what I am trying to do, I am just not sure how to integrate it into my current code. Any help would be awesome. Stack overflow question in firebase database storage loop
UPDATE
So, now I'm incredibly close. I only have one problem. The following code lists the returned data and retrieves the URL properties. I am using url properties to connect to firebase store and return download urls. Both are recorded to the console! Awesome. Now I have the URLs I need! The problem I am facing is simply letting me output these values ββto a local array. In this case "var array". I need to click on an array that is outside the "activateRoute" method. Every time I do this, it returns as undefined.
this.activatedRoute.data
.subscribe((
data: { issueData: any, issueImageData: any }) => {
this.issueToDisplay = data.issueData;
this.imagesToDisplay = data.issueImageData;
var array = [];
data.issueImageData.forEach(image => {
// Reference to the image URL
var image = image.url;
// Firebase storage
var storage = firebase.storage();
// Path reference
var imagePathReference = storage.ref().child(image);
// Get Download URL
imagePathReference.getDownloadURL().then(function (url) {
console.log(url);
array.push(url);
})
});
});
source to share
So it works. Not really sure how clean it is. But it works.
this.activatedRoute.data
.subscribe((
data: { issueData: any, issueImageData: any }) => {
this.issueToDisplay = data.issueData;
this.imagesToDisplay = data.issueImageData;
var localImageArray = [];
data.issueImageData.forEach(image => {
// Reference to the image URL
var image = image.url;
// Firebase storage
var storage = firebase.storage();
// Path reference
var imagePathReference = storage.ref().child(image);
// Get Download URL
imagePathReference.getDownloadURL().then(function (url) {
localImageArray.push(url);
})
this.getIssueImageArray(localImageArray);
});
});
}
// Get Image Array
getIssueImageArray(array) {
this.imageToDisplayArray = array;
}
source to share
I would recommend that you use the functions it rxjs
provides you with:
this.activatedRoute.data.switchMap(data => {
let parsedData = {
issueToDisplay: data.issueData,
imagesToDisplay: data.issueImageData
}
let imageUrls$ = data.issueImageData.map(image => {
var imagePathReference = storage.ref().child(image);
return Observable.fromPromise(imagePathReference.getDownloadURL())
});
return Observable.forkJoin(imageUrls$).map((...urls) => {
return Object.assign(parsedData, { urls });
})
}).subscribe(data => {
/*
data looks like this:
{
issueToDisplay: any,
imagesToDisplay: any,
urls: string[]
}
*/
});
source to share
If I am correct, you are looking for a solution to map an array of objects to an actual array of objects.
Here's how to do it:
var object = {
'0': {
"url": "url1",
"name": "obj1",
"data": 1234
},
'1': {
"url": "url2",
"name": "obj2",
"data": 5678
},
'length': 2
}
var sliced = Array.prototype.slice.call( object, 0 );
console.log(sliced)
A couple of notes:
-
If you are wondering how it works check out this post .
-
The alternative syntax you might have come across looks like
[].slice.call()
-
If you want to perform operations on an array, you can probably do it right away with
Array.prototype.<METHOD>.call(object, <CALLBACK>
-
For example:
Array.prototype.map.call(object, function(el) { // return your enhanced element })
source to share