据我了解Angular中的$sce
,默认行为是:
AngularJS将自动对[敏感HTML]运行安全检查 (清理,白名单,取决于上下文
另外,据我所知,白名单(通过$sceDelegateProvider.resourceUrlWhitelist
)会阻止消毒。
基本上,我已经有了一个全局启用trustasresourceurl的应用程序(see accepted answer)。现在,我想从这个全局信任中排除1个控制器。换句话说,我希望将此内容显示为纯文本,而没有任何样式绑定到ng-bind-html
:
<span style="font-family: Arial; font-size: 24px;"> A wizard is never late hardcode.</span>
我可能需要创建一个过滤器来手动删除任何HTML,但我讨厌这样做只是为了回到默认的角度行为。用正则表达式解析HTML是丑陋而脆弱的。你有什么建议?
This code接近我想要的,但无论什么样式被删除,所以它无法正确重现问题。我猜测白名单失败了,所以它仍然被消毒了。
var mainMod = angular.module('MainApp', ['ngSanitize']);
mainMod.controller('MainCtrl', ['$scope',
function ($scope) {
$scope.text = '<p>Hello! <a href="#">Link</a></p>';
$scope.htmlContent = '<span style="font-family: Arial; font-size: 24px;"> A wizard is never late.</span>';
}]);
angular.module('MainCtrl', []).config(function($sceDelegateProvider) {
$sceDelegateProvider.resourceUrlWhitelist([
// Allow same origin resource loads.
'self',
// Allow loading from our assets domain. Notice the difference between * and **.
'https://codepen.io/**'
]);
// The blacklist overrides the whitelist so the open redirect here is blocked. I don't want to blocklist the whole resource. Just this one controller.
$sceDelegateProvider.resourceUrlBlacklist([
''
]);
});
&#13;
body{
padding:20px;
}
.search{
margin-left:10px;
}
&#13;
<script src="https://code.angularjs.org/1.5.11/angular.min.js"></script>
<script src="https://code.angularjs.org/1.5.11/angular-sanitize.min.js"></script>
<body ng-app='MainApp'>
<div ng-controller="MainCtrl">
<div ng-bind-html="htmlContent"></div>
<div ng-bind-html='text'></div>
<span style="font-family: Arial; font-size: 24px;"> A wizard is never late hardcode. In real app this is what I get. </span>
</div>
</body>
&#13;
Angular 1.5.11
答案 0 :(得分:1)
过滤以从HTML获取文字:
mainMod.filter('get_text', ['$sce', function($sce){
return function(text) {
console.log("actual HTML",text)
var doc = new DOMParser().parseFromString(text, "text/html");
var textVal= doc.documentElement.textContent;
console.log(textVal,"Only Text")
return $sce.trustAsHtml(textVal)
};
}]);
并在HTML中:
<div ng-bind-html="htmlContent|get_text"></div>
var mainMod = angular.module('MainApp', ['ngSanitize']);
mainMod.filter('get_text', ['$sce', function($sce){
return function(text) {
console.log("actual HTML",text)
var doc = new DOMParser().parseFromString(text, "text/html");
var textVal= doc.documentElement.textContent;
console.log(textVal,"Only Text")
return $sce.trustAsHtml(textVal)
};
}]);
mainMod.controller('MainCtrl', ['$scope',
function ($scope) {
$scope.text = '<p>Hello! <a href="#">Link</a></p>';
$scope.htmlContent = '<span style="font-family: Arial; font-size: 24px;"> A wizard is never late.</span>';
}]);
angular.module('MainCtrl', []).config(function($sceDelegateProvider) {
$sceDelegateProvider.resourceUrlWhitelist([
// Allow same origin resource loads.
'self',
// Allow loading from our assets domain. Notice the difference between * and **.
'https://codepen.io/**'
]);
// The blacklist overrides the whitelist so the open redirect here is blocked. I don't want to blocklist the whole resource. Just this one controller.
$sceDelegateProvider.resourceUrlBlacklist([
''
]);
});
body{
padding:20px;
}
.search{
margin-left:10px;
}
<script src="https://code.angularjs.org/1.5.11/angular.min.js"></script>
<script src="https://code.angularjs.org/1.5.11/angular-sanitize.min.js"></script>
<body ng-app='MainApp'>
<div ng-controller="MainCtrl">
<div ng-bind-html="htmlContent|get_text"></div>
<div ng-bind-html='text'></div>
<span style="font-family: Arial; font-size: 24px;"> A wizard is never late hardcode. In real app this is what I get. </span>
</div>
</body>
答案 1 :(得分:0)
如果您需要更多向后兼容性以及格式错误的HTML的灵活性,那么以下过滤器也可以使用:
mainMod.filter('get_text', ['', function(){
//A more forgiving HTML to text conversion
//Wrap the content in a div and get inner text
return function(text) {
var doc = document.createElement('div');
doc.innerHTML = text;
return doc.textContent;//no need to trustAsHtml because always plain text
};
}]);