34

I have a block in my angular JS template a la

<a href="#/foos/{{foo.id}}">{{foo.name}}</a>

However, the foo.id property can sometimes contain funky characters ('/'). I want to do something like this:

<a href="#/foos/{{encodeURIComponent(foo.id)}}">{{foo.name}}</a>

but it doens't work? How can I fix this?

1
  • I saw this answer - stackoverflow.com/a/14512986/775359 - and I was wondering - why I cannot use encodeURIComponent directly in the template... Apparently a filter is required. Commented Aug 9, 2016 at 8:50

3 Answers 3

70

You could create a filter that calls encodeURIComponent

E.g.

var app = angular.module('app', []);
app.filter('encodeURIComponent', function() {
    return window.encodeURIComponent;
});

Then do

<a href="#/foos/{{foo.id | encodeURIComponent}}">{{foo.name}}</a>

Running example: http://jsfiddle.net/YApdK/

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

4 Comments

jimr beat me, but it's also worth noting that you should use ng-href instead of href to be sure that links are rendered by angular before they can be clicked.
This feels wrong just to use one function but it worked immediately.
Thanks, very impressive example providing javascript to html with a very short syntax
As @RickJolly pointed out, you should use ng-hrefinstead of href to be sure that links are rendered by angular before they can be clicked. You should also probably inject $window into the filter instead of using window directly.
15

Reworked @jimr's code, taking into account @aj-richardson's recommendations.

You can use filters within expressions to format data before rendering it.

Create a filter:

var app = angular.module('app', []);
app.filter('encodeURIComponent', function($window) {
    return $window.encodeURIComponent;
});

Then apply the filter:

<a ng-href="#/foos/{{foo.id | encodeURIComponent}}">{{foo.name}}</a>
  • ng-href is used instead of href to be sure that links are rendered by AngularJS before they can be clicked.
  • $window is injected into the filter instead of using window directly.

    You should refer to global window through the $window service, so it may be overridden, removed or mocked for testing.


References:

  1. AngularJS API: $window
  2. AngularJS Developer Guide: filters
  3. AngularJS Developer Guide: expressions

Comments

0

If you want to handle malformed URI error, then you have to write a filter function and then use try-catch around the encodeURIComponent.

var app = angular.module('app', []);
app.filter('encodeURIComponent', function($window) {
    return function (path) {
        try {
            return $window.encodeURIComponent(path);
        } catch(e) {
            return path;
        }
    }
});

Comments

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.