Skip to content
This repository has been archived by the owner on Apr 12, 2024. It is now read-only.

Commit

Permalink
feat($interpolate): add optional allOrNothing param
Browse files Browse the repository at this point in the history
  • Loading branch information
btford committed May 2, 2014
1 parent 2b6c2c5 commit c2362e3
Show file tree
Hide file tree
Showing 2 changed files with 42 additions and 5 deletions.
42 changes: 37 additions & 5 deletions src/ng/interpolate.js
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,26 @@ function $InterpolateProvider() {
* expect(exp({name:'Angular'}).toEqual('Hello ANGULAR!');
* ```
*
* `$interpolate` takes an optional fourth argument, `allOrNothing`. If `allOrNothing` is
* `true`, the interpolation function will return `undefined` unless all embedded expressions
* evaluate to a value other than `undefined`.
*
* ```js
* var $interpolate = ...; // injected
* var context = {greeting: 'Hey', name: undefined };
*
* // default "forgiving" mode
* var exp = $interpolate('{{greeting}} {{name}}!');
* expect(exp(context)).toEqual('Hello !');
*
* // "allOrNothing" mode
* exp = $interpolate('{{greeting}} {{name}}!', false, null, true);
* expect(exp(context, true)).toBeUndefined();
* context.name = 'Angular';
* expect(exp(context, true)).toEqual('Hello Angular!');
* ```
*
* `allOrNothing` is useful for interpolating URLs. `ngSrc` and `ngSrcset` use this behavior.
*
* @param {string} text The text with markup to interpolate.
* @param {boolean=} mustHaveExpression if set to true then the interpolation string must have
Expand All @@ -114,12 +134,15 @@ function $InterpolateProvider() {
* result through {@link ng.$sce#getTrusted $sce.getTrusted(interpolatedResult,
* trustedContext)} before returning it. Refer to the {@link ng.$sce $sce} service that
* provides Strict Contextual Escaping for details.
* @param {boolean=} allOrNothing if `true`, then the returned function returns undefined
* unless all embedded expressions evaluate to a value other than `undefined`.
* @returns {function(context)} an interpolation function which is used to compute the
* interpolated string. The function has these parameters:
*
* - `context`: evaluation context for all expressions embedded in the interpolated text
*/
function $interpolate(text, mustHaveExpression, trustedContext) {
function $interpolate(text, mustHaveExpression, trustedContext, allOrNothing) {
allOrNothing = !!allOrNothing;
var startIndex,
endIndex,
index = 0,
Expand Down Expand Up @@ -182,16 +205,21 @@ function $InterpolateProvider() {
return concat.join('');
};

var stringify = function (value) {
var getValue = function (value) {
if (trustedContext) {
value = $sce.getTrusted(trustedContext, value);
} else {
value = $sce.valueOf(value);
}

if (value === null || isUndefined(value)) {
return value;
};

var stringify = function (value) {
if (isUndefined(value) || value === null) {
value = '';
} else if (typeof value != 'string') {
}
if (typeof value != 'string') {
value = toJson(value);
}

Expand Down Expand Up @@ -225,7 +253,11 @@ function $InterpolateProvider() {

try {
for (; i < ii; i++) {
val = stringify(parseFns[i](context));
val = getValue(parseFns[i](context));
if (allOrNothing && isUndefined(val)) {
return;
}
val = stringify(val);
if (val !== lastValues[i]) {
inputsChanged = true;
}
Expand Down
5 changes: 5 additions & 0 deletions test/ng/interpolateSpec.js
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,11 @@ describe('$interpolate', function() {
expect($interpolate('some text', true)).toBeUndefined();
}));

it('should return undefined when there are bindings and strict is set to true',
inject(function($interpolate) {
expect($interpolate('test {{foo}}', false, null, true)({})).toBeUndefined();
}));

it('should suppress falsy objects', inject(function($interpolate) {
expect($interpolate('{{undefined}}')({})).toEqual('');
expect($interpolate('{{null}}')({})).toEqual('');
Expand Down

1 comment on commit c2362e3

@tabanliviu
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldn't "var context = {greeting: 'Hey', name: undefined };" be "var context = {greeting: 'Hello', name: undefined };" in the documentation?

Please sign in to comment.