Indexing firebase objects - javascript

How am I able to create an index for the object data that I am passing into Firebase?
I am using the .$add function in the AngularFire library to push the data. This is the filter and controller that I am using:
angular.module('bestDay', ["firebase"]).factory("GreatService", ["$firebase", function($firebase) {
var ref = new Firebase("https://quickjournal.firebaseIO.com/");
return $firebase(ref);
}])
.controller("bdctrl", ["$scope", "GreatService",
function($scope, greatService) {
$scope.theval = "Val " + Math.round(Math.random()*101);
$scope.daylist = greatService;
$scope.addDayGood = function() {
$scope.daylist.$add({
desc: $scope.newDay.desc,
date: $scope.newDay.date,
value: $scope.theval
});
$scope.newDay.desc = "";
$scope.newDay.date = "";
};
}
]);
As you can see, I was attempting to use a unique value when passing the objects in, but it was only generating the same number every time (13). If it isn't apparent, I am semi-new to programming.
I would also like to be able to write a function that will remove the data by that index. Since I am unable to conquer the prior task, I may need assistance in doing this as well.
I am writing my code with the angularjs library.
I have combed through the firebase and angularfire library documentation with no results. If you could point me to a URL with the documentation on this, it would be much appreciated.

Firebase should do the indexing, as this makes it easier if you have more than one user accessing the same data.
Relevant to your question, you should look up https://www.firebase.com/docs/ordered-data.html for working with lists in firebase.
More the point, the push() function provided makes for easy chronological sorting, and if you need more complex sorting you can look at the setWithPriority() function.
angular.module('bestDay', ["firebase"])
.controller("bdctrl", ['$scope', '$firebase',
function($scope,$firebase) {
var daysRef = new Firebase("https://quickjournal.firebaseIO.com/daylist/");
$scope.dayList = $firebase(daysRef);
$scope.dayLocationInFirebase = daysRef.push();
$scope.addDayGood = function(){
// Setdata to the generated location
$scope.dayLocationInFirebase.set({
desc: $scope.newDay.desc,
date: $scope.newDay.date
});
//holds reference to location the object was pushed to, for direct manipulation of the value. Pass it to the scope or an array if you need it for later
var pushedName = $scope.dayLocationInFirebase.name();
alert(pushedName);
$scope.newDay.desc = "";
$scope.newDay.date = "";
}
}
]);

Related

SSIS Reading Columns from an Object Variable

I have an object variable which is from a SQL Query. This essentially contains two columns: RecordID and Description. I'm not familiar with JavaScript. But how do I read the specific columns and assign them to a local javascript variable?
Here's the sample code I would like to use with the new User::MyObject structure of multiple columns:
task.run = function () {
var myID = task.variables["User::MyObject"].value;
var myDesc = task.variables["User::MyObject"].value;
alert(myID);
alert(myDesc);
return ScriptResults.Success;
};
EDIT: I am using COZYROC that's why I have a JavaScript Task available in my toolbox. The result set is currently set to Full Result Set and the object is being pushed to User::MyObject via a preceeding SQL Task.
Here's a code from when my User::MyObject was a single result set with single row and single column return (just the Description).
task.run = function () {
var myDesc = task.variables["User::MyObject"].value;
alert(myDesc);
return ScriptResults.Success;
};
I know for VB.NET/C# you can use something like myVariable.Rows[0][1].ToString() but i'm really not sure how that translates to JavaScript.
Within your task function:
1. Set a variable to the object
var MyObject= task.variables["User::MyObject"].value;
2 Access the ID property of your object
MyObject.ID
Complete example to get ID:
task.run = function () {
var MyObject = task.variables["User::MyObject"].value;
alert(MyObject.ID);
return ScriptResults.Success;
};
Example from crazycroc documentation https://desk.cozyroc.com/portal/en/kb/articles/how-c

Firebase: Can I combine a push with a multi-location update?

I need to create a new object with a generated key and update some other locations, and it should be atomic. Is there some way to do a push with a multi-location update, or do I have to use the old transaction method? This applies for any client platform, but here's an example in JavaScript.
var newData = {};
newData['/users/' + uid + '/last_update'] = Firebase.ServerValue.TIMESTAMP;
newData['/notes/' + /* NEW KEY ??? */] = {
user: uid,
...
};
ref.update(newData);
There are two ways to invoke push in Firebase's JavaScript SDK.
using push(newObject). This will generate a new push id and write the data at the location with that id.
using push(). This will generate a new push id and return a reference to the location with that id. This is a pure client-side operation.
Knowing #2, you can easily get a new push id client-side with:
var newKey = ref.push().key(); // on newer versions ref.push().key;
You can then use this key in your multi-location update.
I'm posting this to save some of future readers' time.
Frank van Puffelen 's answer (many many thanks to this guy!) uses key(), but it should be key.
key() throws TypeError: ref.push(...).key is not a function.
Also note that key gives the last part of a path, so the actual ref that you get it from is irrelevant.
Here is a generic example:
var ref = firebase.database().ref('this/is/irrelevant')
var key1 = ref.push().key // L33TP4THabcabcabcabc
var key2 = ref.push().key // L33TP4THxyzxyzxyzxyz
var updates = {};
updates['path1/'+key1] = 'value1'
updates['path2/'+key2] = 'value2'
ref.update(updates);
that would create this:
{
'path1':
{
'L33TP4THabcabcabcabc': 'value1'
},
'path2':
{
'L33TP4THxyzxyzxyzxyz': 'value2'
}
}
I'm new to firebase, please correct me if I'm wrong.

Parse.com issues while querying array of pointers, .include not getting nested pointer data in cloud code

I am having trouble getting data from the nested pointers in my array of pointers from a query. I have an array of pointers like so: [{"__type":"Pointer","className":"QuizData","objectId":"rmwJrV55c7"},{"__type":"Pointer","className":"QuizData","objectId":"2132q8i9np”}, etc…]
That QuizData class also has a column named “ad” which is a Pointer to the “Ads” class. I can get the QuizData in a query using the following include statements on my query like so:
var __quizAdQueueQuery = new Parse.Query(QuizAdQueue);
__quizAdQueueQuery.equalTo("user", __request.user);
__quizAdQueueQuery.include("quizAdArr”);
__quizAdQueueQuery.include(["quizAdArr.QuizData"]);
BUT Neither of these or both combined don’t work as when I try to get column data from the ad it’s always undefined:
__quizAdQueueQuery.include(["quizAdArr.QuizData.ad"]);
__quizAdQueueQuery.include(["quizAdArr.QuizData.Ads"]);
This is my return from that query, where the column data "mediaType" that I am trying to access is always undefined:
return __quizAdQueueQuery.first().then(function(__resultsObj)
{
__quizQueueObj = __resultsObj;
__userQuizQueueArr = __quizQueueObj.get("quizAdArr");
var __quiz;
var __ad;
var __seenAd;
var __lengthInt = __userQuizQueueArr.length;
var __mediaTypeStr = __request.params.mediaType;
var __matchedQuizzesArr = [];
for (var __i = 1; __i < __lengthInt; __i++)
{
__quiz = __userQuizQueueArr[__i];
// console.log('__quiz.get("name") = '+__quiz.get("name"));
__ad = __quiz.get("ad");
// console.log("__ad.id = "+__ad.id);
//THE MEDIA TYPE IS ALWAYS RETURNING UNDEFINED HERE!!!
console.log('__ad.get("mediaType") = '+__ad.get("mediaType")+', __mediaTypeStr = '+__mediaTypeStr);
if (__ad.get("mediaType") == __mediaTypeStr)
{
//put all matches in array to be sorted
__matchedQuizzesArr.push(__userQuizQueueArr[__i]);
console.log("__matchedQuizzesArr.length = "+__matchedQuizzesArr.length);
}
}
return __matchedQuizzesArr;
});
Thanks for any help you can give! I also posted this as a bug in the Parse/Facebook issue reporter but was redirected here, so if this is a bug I can reopen it: https://developers.facebook.com/bugs/923988310993165/
EDIT Here is the updated, working query with nested includes for clarity:
var __quizAdQueueQuery = new Parse.Query(QuizAdQueue);
__quizAdQueueQuery.equalTo("user", __request.user);
__quizAdQueueQuery.include('quizAdArr');
__quizAdQueueQuery.include('quizAdArr.ad');
This should work (you only need to list the column names):
query.include('quizAdArr.ad');
Here's why:
You're querying QuizAdQueue so you don't need to list that
The QuizAdQueue class has an array in quizAdArr so you include it: query.include('quizAdArr');
Each quizAdArr element is a QuizData with an ad so you include it: query.include('quizAdArr.ad');
The issue was that you were including QuizData which is the name of a class and not a column name

How to use Ember's getters/setters on properties with dots?

In my webapp, I have a model with properties whose names are dynamically generated based on data from the server. For example, I would normally reference this by doing something like this from my controller:
var str1 = 'property.name.with.dots'; // String from server
this.get('model.someProperty')[str1].integer = 2;
this.get('model.someProperty')[str1].integer += 1;
But Ember doesn't like this - it says I should use a set or get function. Which makes sense. So I want to do something like this in place of the last line above:
this.get('model.someProperty.' + str1).incrementProperty('integer');
This would work fine out of the box if str1 didn't have dots. It does, though, so what can I do to get Ember's getters to work? I tried
this.get('model.someProperty')[str1].incrementProperty('integer');
but it doesn't work - the subobjects don't get Ember's methods by default.
Definitely
Massage the data before handing it off to Ember, having dots in your name will just cause a plethora of chaining problems.
Clean the data, I chose _ (this isn't deep cleaning, exercise for your fun)
App.cleanData = function(result){
var response = {},
re = new RegExp('\\.', 'g'),
newKey;
for(var key in result){
newKey = key.replace(re, '_');
response[newKey] = result[key];
}
return response;
};
Use the cleaned data instead of the server data
App.FooRoute = Em.Route.extend({
model: function(){
return $.getJSON('/foo').then(function(result){
return App.cleanData(result);
}
}
});

AngularJS is removing my $_parent property when the object is passed back to the controller function

I have a linked list of JavaScript objects that I want to generate breadcrumbs from.
Because I'm using the list in recursive directive I need to use $_prev and $_next (instead of prev and next) so I won't get JSON.parse error about circular reference.
var myapp = angular.module('myApp', []);
var data00 = { id: 0, label: 'label_0' }
var data01 = { id: 1, label: 'label_1' }
var data02 = { id: 2, label: 'label_2' }
data00.$_next = data01;
data01.$_next = data02;
data01.$_prev = data00;
data02.$_prev = data01;
myapp.controller('testController', function($scope){
$scope.data = data02;
$scope.getBreadCrumbs = function(branch){
var crumbs = branch.label;
while(branch.$_prev){
branch = branch.$_prev;
crumbs = branch.label + ' \\ ' + crumbs;
}
return crumbs;
}
});
jsFiddle
Everything works in chrome, but in IE8 inside getBreadCrumbs function $_prev property does not exist.
Any input how I can debug the issue would be greatly appreciated.
I'm not sure about your IE8 problem but IMHO your approach is not very good. I believe that by using a better approach you will cut down future development/maintenance and quite possibly get rid of your IE8 bug. What I would do is put all your dataxx objects into a single array and then either use a function or a angular directive(s) to create your breadcrumbs from that array.
I strongly discourage you from doing something like this
data00.$_next = data01;
data01.$_next = data02;
data01.$_prev = data00;
data02.$_prev = data01;
Because as you add more data points it'll be more unnecessary work. You can either use the length of the array to see if you are on the first/last breadcrumb on or use the $first $last property that angular gives you on an ng-repeat

Categories