根据Angularfire文档,在处理通过$asObject()
返回的对象时,您可以通过在对象上定义$priority
属性然后使用$save()
来设置所述对象的优先级。
我的代码效果很好,但$priority
并没有做任何事情。这里有一些代码在评论中有完整的解释:
app.factory('MyService', function($rootScope, $firebase) {
// The complete Firebase url
var ref = *obfuscated*;
// Returning the dataset as an object containing objects
var data = $firebase(ref).$asObject;
// This object is what's returned by MyService
var Data = {
// Method to create a new object within the data set,
// keyed by myId. Attempting to set priority for the
// record via $priority. returnData.uid is a valid string.
create: function(returnData, myId) {
data[myId] = {
myId: myId,
$priority: returnData.uid
};
// No need to explain the stuff between here and the
// $rootScope listener below, just added for context
data.$save().then(function() {
setMyId(myId);
});
},
findByMyId: function(myId) {
if (myId) {
return data[myId];
}
}
};
function setMyId(myId) {
$rootScope.myId = User.findByMyId(myId);
}
// This event listener works fine, fires
// at user login and returns data
$rootScope.$on('$firebaseSimpleLogin:login', function(e, returnData) {
// returnData.uid has the correct value - this
// function should return the object(aka record) with
// a priority matching returnData.uid
var query = $firebase(ref.startAt(returnData.uid).endAt(returnData.uid)).$asObject();
// console shows an object with the normal $firebase
// properties, but no records. If I define query without
// limiting the set ($firebase(ref).$asObject()), it returns
// the full set just fine. The priority on all records is still
// null.
console.log(query);
query.$loaded(function() {
setData(query.myId);
});
});
return Data;
});
是的,我正在关注Thinkster.io的教程和我在第7章。不,这不是关于该章的其他问题的重复,我已经找到了解决方法他们的例子中出现的前Angularfire 0.8代码,只是无法设置优先权,到目前为止,我花了大约5个小时试图通过自己的努力和网络找到解决方案。
任何参赛者?
答案 0 :(得分:3)
根据JavaScript如何处理对象(即无序),JSON如何处理对象(即无序),并考虑到AngularFire的$asObject()
方法的预期for storing key/value pairs, and singular records that are not used as a collection,这开始有道理。
在内部,同步对象的$save
方法会调用Firebase的setWithPriority。在set
或setWithPriority
调用中,将替换子节点。这些孩子的优先级等元数据都会被替换。
在AngularFire中,$asArray
旨在处理有序集合,并提供在子节点上设置$priority
的能力(当然,只有一级深度,因为它将其子节点视为单个记录,不是自己的收藏品。)
因为在你的情况下,你想要使用固定键而不是push id,你可能想要使用$ extendFactory覆盖$ add方法并执行以下操作:
angular.module(MY_APP).factory('FixedKeysFactory', function($FirebaseArray, $firebaseUtils) {
return $FirebaseArray.$extendFactory({
$add: function(data) {
this._assertNotDestroyed('$add');
if( angular.isObject(data) && typeof data.$id === 'string' ) {
return this.$inst().$set(data.$id, $firebaseUtils.toJSON(data));
}
else {
return this.$inst().$push($firebaseUtils.toJSON(data));
}
}
});
});
然后,您可以将其传递到$ firebase实例中,而不是默认工厂:
var list = $firebase(ref, {arrayFactory: FixedKeysFactory}).$asArray();
一个更简单但不那么awesomatic™的解决方案是手动将对象添加到数组中,手动给它们一个$ id,然后调用$ save:
var list = $firebase(ref).$asArray();
var i = list.length;
list.push({ foo: 'bar', $id: 'kato' });
list.$save(i);
关于未来的一些注释:很快就可以使用任何字段作为排序标准,并且不需要设置优先级(耶!)。一旦我用其他开发者(如0.8.3版本)清除它,就可以在AngularFire中的同步数组上调用$ add之前设置自己的$ id。