Skip to content

Commit

Permalink
Reimplement inline link-to as an AST transform (emberjs#12229)
Browse files Browse the repository at this point in the history
  • Loading branch information
mmun authored and toddjordan committed Sep 9, 2016
1 parent 3fbc1a2 commit d31a14d
Show file tree
Hide file tree
Showing 5 changed files with 54 additions and 41 deletions.
8 changes: 4 additions & 4 deletions packages/ember-routing-htmlbars/tests/helpers/link-to_test.js
Original file line number Diff line number Diff line change
Expand Up @@ -99,7 +99,7 @@ QUnit.test('escaped inline form (double curlies) escapes link title', function()
view = EmberView.create({
[OWNER]: owner,
title: '<b>blah</b>',
template: compile('{{link-to view.title}}')
template: compile('{{link-to view.title "index"}}')
});

runAppend(view);
Expand All @@ -111,7 +111,7 @@ QUnit.test('escaped inline form with (-html-safe) does not escape link title', f
view = EmberView.create({
[OWNER]: owner,
title: '<b>blah</b>',
template: compile('{{link-to (-html-safe view.title)}}')
template: compile('{{link-to (-html-safe view.title) "index"}}'),
});

runAppend(view);
Expand All @@ -123,7 +123,7 @@ QUnit.test('unescaped inline form (triple curlies) does not escape link title',
view = EmberView.create({
[OWNER]: owner,
title: '<b>blah</b>',
template: compile('{{{link-to view.title}}}')
template: compile('{{{link-to view.title "index"}}}')
});

runAppend(view);
Expand Down Expand Up @@ -153,7 +153,7 @@ QUnit.test('able to safely extend the built-in component and use the normal path
view = EmberView.create({
[OWNER]: owner,
title: 'my custom link-to component',
template: compile('{{custom-link-to view.title}}')
template: compile('{{#custom-link-to \'index\'}}{{view.title}}{{/custom-link-to}}')
});

runAppend(view);
Expand Down
8 changes: 2 additions & 6 deletions packages/ember-routing-views/lib/components/link-to.js
Original file line number Diff line number Diff line change
Expand Up @@ -322,7 +322,6 @@ import EmberComponent from 'ember-views/components/component';
import inject from 'ember-runtime/inject';
import 'ember-runtime/system/service'; // creates inject.service
import ControllerMixin from 'ember-runtime/mixins/controller';
import { HAS_BLOCK } from 'ember-htmlbars/node-managers/component-node-manager';
import htmlbarsTemplate from 'ember-htmlbars/templates/link-to';
import require from 'require';

Expand Down Expand Up @@ -666,7 +665,7 @@ let LinkComponent = EmberComponent.extend({
if (lastParam && lastParam.isQueryParams) {
params.pop();
}
let onlyQueryParamsSupplied = (this[HAS_BLOCK] ? params.length === 0 : params.length === 1);
let onlyQueryParamsSupplied = (params.length === 0);
if (onlyQueryParamsSupplied) {
return get(this, '_routing.currentRouteName');
}
Expand Down Expand Up @@ -777,10 +776,7 @@ let LinkComponent = EmberComponent.extend({
}

// Process the positional arguments, in order.
// 1. Inline link title comes first, if present.
if (!this[HAS_BLOCK]) {
this.set('linkTitle', params.shift());
}
// 1. Inline link title was shifted off by AST.

// 2. `targetRouteName` is now always at index 0.
this.set('targetRouteName', params[0]);
Expand Down
4 changes: 2 additions & 2 deletions packages/ember-template-compiler/lib/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,8 @@ import TransformComponentCurlyToReadonly from 'ember-template-compiler/plugins/t
import TransformAngleBracketComponents from 'ember-template-compiler/plugins/transform-angle-bracket-components';
import TransformInputOnToOnEvent from 'ember-template-compiler/plugins/transform-input-on-to-onEvent';
import TransformTopLevelComponents from 'ember-template-compiler/plugins/transform-top-level-components';
import TransformUnescapedInlineLinkTo from 'ember-template-compiler/plugins/transform-unescaped-inline-link-to';
import DeprecateRenderModel from 'ember-template-compiler/plugins/deprecate-render-model';
import TransformInlineLinkTo from 'ember-template-compiler/plugins/transform-inline-link-to';
import AssertNoViewAndControllerPaths from 'ember-template-compiler/plugins/assert-no-view-and-controller-paths';
import AssertNoViewHelper from 'ember-template-compiler/plugins/assert-no-view-helper';
import AssertNoEachIn from 'ember-template-compiler/plugins/assert-no-each-in';
Expand All @@ -31,9 +31,9 @@ registerPlugin('ast', TransformComponentCurlyToReadonly);
registerPlugin('ast', TransformAngleBracketComponents);
registerPlugin('ast', TransformInputOnToOnEvent);
registerPlugin('ast', TransformTopLevelComponents);
registerPlugin('ast', TransformUnescapedInlineLinkTo);
registerPlugin('ast', DeprecateRenderModel);
registerPlugin('ast', AssertNoEachIn);
registerPlugin('ast', TransformInlineLinkTo);

if (!_Ember.ENV._ENABLE_LEGACY_VIEW_SUPPORT) {
registerPlugin('ast', AssertNoViewAndControllerPaths);
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
export default function TransformInlineLinkTo(options) {
this.options = options;
this.syntax = null;
}

TransformInlineLinkTo.prototype.transform = function TransformInlineLinkTo_transform(ast) {
let { traverse, builders: b } = this.syntax;

function buildProgram(content) {
return b.program([buildStatement(content)]);
}

function buildStatement(content) {
switch (content.type) {
case 'PathExpression':
return b.mustache(content);

case 'SubExpression':
return b.mustache(content.path, content.params, content.hash);

// The default case handles literals.
default:
return b.text('' + content.value);
}
}

function unsafeHtml(expr) {
return b.sexpr('-html-safe', [expr]);
}

traverse(ast, {
MustacheStatement(node) {
if (node.path.original === 'link-to') {
let content = node.escaped ? node.params[0] : unsafeHtml(node.params[0]);
return b.block(
'link-to',
node.params.slice(1),
node.hash,
buildProgram(content)
);
}
}
});

return ast;
};

This file was deleted.

0 comments on commit d31a14d

Please sign in to comment.