68

This is my template:

<div class="span12">
  <ng:view></ng:view>
</div>

and this is my view template:

<h1>{{stuff.title}}</h1>

{{stuff.content}}

I am getting the content as html and I want to display that in a view, but all I am getting is raw html code. How can I render that HTML?

7
  • 2
    Where is the HTML coming from? Under different circumstances, you'll want ngBindHtmlUnsafe, ngSanitize, or a custom directive. Commented Apr 2, 2013 at 1:14
  • The html is coming from my database Commented Apr 2, 2013 at 1:37
  • 1
    Is the content absolutely trusted? Commented Apr 2, 2013 at 1:41
  • 1
    For example, if the HTML contains a script tag the browser would execute it. This type of "injection" attack is a common way of damaging apps and stealing user data. AngularJS has a separate module called ngSanitize that you can use to strip the HTML of any dangerous tags; it also has a directive called ngBindHtml that works just like ngBindHtmlUnsafe, but strips the dangerous tags for you. If the content is entirely yours - and doesn't come from users or third parties - then you don't need it. Commented Apr 2, 2013 at 3:45
  • 1
    possible duplicate of Insert HTML into view using AngularJS Commented Oct 3, 2014 at 13:42

5 Answers 5

100

Use-

<span ng-bind-html="myContent"></span>

You need to tell angular to not escape it.

Sign up to request clarification or add additional context in comments.

7 Comments

API has changed in AngularJS 1.2. stackoverflow.com/questions/18340872/…
amccausl has saved new angular users countless hours of debugging due to angular "hell docs", ng-bind-html-unsafe is deprecated and please refer to the link located in the comment above to solve the answer.
I just inserted <span ng-bind-html="myHtmlFragment"></span> into my template and without doing anything else it worked great. I didn't have to inject $sce. Here's the docs: docs.angularjs.org/api/ng/directive/ngBindHtml
ngSanitize -one thing that was missing for me when using the answers here(you can get from the angular docs on ng-bind-html) is you need to make sure your app includes the ngSanitize module. Without that it did not work.
ng-bind-html alone worked, without using trustAsHtml
|
50

To do this, I use a custom filter.

In my app:

myApp.filter('rawHtml', ['$sce', function($sce){
  return function(val) {
    return $sce.trustAsHtml(val);
  };
}]);

Then, in the view:

<h1>{{ stuff.title}}</h1>

<div ng-bind-html="stuff.content | rawHtml"></div>

3 Comments

This is an excellent solution @Daniel. If I am using the $sce.trustAsHtml, I dont need to include the ngSanitize dependency to the app module? I am using Angular 1.3
Can we use ng-include to achieve this?
this does not work for me, i am using angular 7. Kindly suggest the solution. Thanks.
4

In angular 4+ we can use innerHTML property instead of ng-bind-html.

In my case, it's working and I am using angular 5.

<div class="chart-body" [innerHTML]="htmlContent"></div>

In.ts file

let htmlContent = 'This is the `<b>Bold</b>` text.';

Comments

3

You shoud follow the Angular docs and use $sce - $sce is a service that provides Strict Contextual Escaping services to AngularJS. Here is a docs: http://docs-angularjs-org-dev.appspot.com/api/ng.directive:ngBindHtmlUnsafe

Let's take an example with asynchroniously loading Eventbrite login button

In your controller:

someAppControllers.controller('SomeCtrl', ['$scope', '$sce', 'eventbriteLogin', 
  function($scope, $sce, eventbriteLogin) {

    eventbriteLogin.fetchButton(function(data){
      $scope.buttonLogin = $sce.trustAsHtml(data);
    });
  }]);

In your view just add:

<span ng-bind-html="buttonLogin"></span>

In your services:

someAppServices.factory('eventbriteLogin', function($resource){
   return {
        fetchButton: function(callback){
            Eventbrite.prototype.widget.login({'app_key': 'YOUR_API_KEY'}, function(widget_html){
                callback(widget_html);
            })
      }
    }
});

Comments

2

So maybe you want to have this in your index.html to load the library, script, and initialize the app with a view:

<html>
  <body ng-app="yourApp">
    <div class="span12">
      <div ng-view=""></div>
    </div>
    <script src="http://code.angularjs.org/1.2.0-rc.2/angular.js"></script>
    <script src="script.js"></script>
  </body>
</html>

Then yourView.html could just be:

<div>
  <h1>{{ stuff.h1 }}</h1>
  <p>{{ stuff.content }}</p>
</div>

scripts.js could have your controller with data $scope'd to it.

angular.module('yourApp')
    .controller('YourCtrl', function ($scope) {
      $scope.stuff = {
        'h1':'Title',
        'content':"A paragraph..."
      };
    });

Lastly, you'll have to config routes and assign the controller to view for it's $scope (i.e. your data object)

angular.module('yourApp', [])
.config(function ($routeProvider) {
  $routeProvider
    .when('/', {
      templateUrl: 'views/yourView.html',
      controller: 'YourCtrl'
    });
});

I haven't tested this, sorry if there's a bug but I think this is the Angularish way to get data

2 Comments

What if I want this same behavior but not depend on routeProvider?
It's the same using ui-router, only it's $stateProvider instead of $routeProvider and .state( 'yourState', { url:'/', templateUrl: 'yourView.html', controller: 'YourCtrl' });

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.