Angular $parse在过滤/排序以整数开头的哈希值时出错
Angular $parse error when filtering/ordering on hash values that start with integers
我有一个相当复杂的角order过滤器结构,它工作得非常好,除了当表达式传递给过滤器函数以以整数开头的散列开始时。
这里有一个小提琴,可以很好地捕捉到这个问题。
在:
结构中使用数组[{'ced8d91c7921a884a131fcc7086239':{'value':'somevalue1'},
'0a9308d3092d092718e457d927f110': {'value':'anotherval'}},
{'ced8d91c7921a884a131fcc7086239':{'value':'axxfi'},
'0a9308d3092d092718e457d927f110': {'value':'zziojasf'}}];
和'somehash结构中的过滤器谓词。如果散列以字母开头,Value '将仅起作用。
我过滤哈希id而不是一个更容易读懂的结构的原因是,数据是动态的,angular不知道它需要过滤的属性名称是什么。
当尝试在JS中使用$filter.
进行过滤时,这个错误仍然存在。查看调用堆栈,问题似乎发生在Lexer.lex
函数中,特别是在这里:
else if (this.isNumber(ch) || ch === '.' && this.isNumber(this.peek())) {
this.readNumber();
有什么解决办法吗?
编写自定义哈希键过滤器
我将始终使用自定义过滤器,而不是与Lexer或$parse抗争。这样我们就可以绕过Lexer并修复我们的问题,然后直接向Angular团队提交一个bug。
注意:这适用于AngularJS 1.2.1,也就是你所选择的版本。我不确定它是否能与任何当前版本的AngularJS一起工作。
这只是一个简单的psuedo关联数组排序器,它接受一个谓词字符串表达式来钻取要比较的值。
我们需要将arrOfObjects
中的值压入到我们的输出arr
中以避免引用。我们不能用angular.copy
,因为它会燃烧到许多消化循环,嗯…呕吐。
下面是过滤器,这里是一个更新的小提琴。
angular.module('orderByFail').filter('orderByHashKey', [
function orderByHashKeyFilter() {
// params: array of objects, the property expression as predicate
// and reverse
// NOTE: the property expression is not an Angular expression
// it is a dot-notation property string expression (ex: obj.key1.key2)
return function(arrOfObjects, propertyExp, reverse) {
// if there is no predicate then just return the array
// the whole reason we are using this is for hash key predicates
if (typeof propertyExp === 'undefined') return arrOfObjects;
propertyExp = propertyExp.split('.');
var len = propertyExp.length;
var arr = [];
for (var i = 0; i < arrOfObjects.length; i++) { arr.push(arrOfObjects[i]); }
arr.sort(function (a, b) {
var i = 0;
// drill down to the values we want
while( i < len ) {
a = a[propertyExp[i]];
b = b[propertyExp[i]];
i++;
}
// this is just a slightly faster bitwise solution
// you can comment this out and use the ternary form below if you prefer
if (a < b) {
return -!reverse | 1;
} else if (a > b) {
return -!!reverse | 1;
} else {
return 0;
}
/*
if (a < b) {
return reverse ? 1 : -1;
} else if (a > b) {
return reverse ? -1 : 1;
} else {
return 0;
}
*/
});
return arr;
}
}
]);
您可以编写getter函数而不是指定谓词。例如http://jsfiddle.net/c6Ldmphu/2/
(function () {
angular.module( 'orderByFail', [
]);
function MyCtrl($scope, $filter, $log) {
$scope.reverse = true;
$scope.sortColumn2 = '0a9308d3092d092718e457d927f110.value';
$scope.entries = [{'ced8d91c7921a884a131fcc7086239':{'value':'somevalue1'},
'0a9308d3092d092718e457d927f110': {'value':'anotherval'}
},
{'ced8d91c7921a884a131fcc7086239':{'value':'axxfi'},
'0a9308d3092d092718e457d927f110': {'value':'zziojasf'}
}];
$scope.sort1 = function() {
$scope.reverse = !$scope.reverse;
$scope.sortColumn1 = 'ced8d91c7921a884a131fcc7086239.value'
}
$scope.sort2 = function() {
$scope.reverse = !$scope.reverse;
$scope.sortColumn2 = '0a9308d3092d092718e457d927f110.value'
}
$scope.sort = function(val) {
var cols = $scope.sortColumn2.split('.');
angular.forEach(cols, function(col, colKey) {
val = val[col];
});
return val;
}
}
angular
.module('orderByFail')
.controller('MyCtrl', MyCtrl)
;
})();
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.1/angular.min.js"></script>
<div ng-app="orderByFail">
<div ng-controller="MyCtrl">
<button ng-click="sort1()">This sort works</button>
<div ng-repeat="entry in entries | orderBy:sortColumn1:reverse">{{entry['ced8d91c7921a884a131fcc7086239'].value}}</div>
<button ng-click="sort2()">This sort will error in console</button>
<div ng-repeat="entry in entries | orderBy: sort:reverse">{{entry['0a9308d3092d092718e457d927f110'].value}}</div>
</div>
</div>
相关文章:
- 如何使用js将SNAPSHOT内部版本号转换为3位数的整数
- 对id以某个字符串开头的元素进行计数
- 检测个位数整数时正在转换毫秒
- 如果元素's的ID以数字开头
- 限制javascript变量的最小/最大整数
- 如何在 Javascript 中将变量的值从字符串转换为整数
- 正则表达式只允许 x 个整数
- 我想在AngularJS应用程序中创建一个输入数字框,用户不应该在该框上键入十进制数字.(一个整数输入框)
- 如何在Chartjs中制作整数比例
- 减去两个索引不同但值相同的整数
- 使用jquery从整数中减去
- 有效地获取两个区间之间的随机整数
- 为什么我的javascript程序没有将其转换为整数而不是字符串
- 带静态字符e输入的文本框数字和带javascript的负整数
- Javascript-当存在's是一个整数标记
- parseInt()方法如何返回整数
- jquery如何生成一个While,该While获取所有以String开头的元素并获取最后2个整数
- 在JQuery中检索字符串开头的整数
- 对于以整数开头的id,无法识别的表达式出现错误
- Angular $parse在过滤/排序以整数开头的哈希值时出错