📅 You're Invited: Meet the Socket team at RSAC (April 28 – May 1).RSVP
Socket
Sign inDemoInstall
Socket

babel-plugin-jsx-to-handlebars

Package Overview
Dependencies
Maintainers
1
Versions
5
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

babel-plugin-jsx-to-handlebars - npm Package Compare versions

Comparing version

to
0.1.2

.travis.yml

1

demo/main.js

@@ -1,2 +0,1 @@

require('./car-tile')();
require('./test')();

@@ -3,0 +2,0 @@ var Handlebars = require('handlebars');

@@ -8,3 +8,3 @@ 'use strict';

var localContextRef = t.identifier('localContext');
var vars = undefined;
var vars = new Map();
return new Plugin('handlebars', {

@@ -32,3 +32,3 @@ visitor: {

enter: function enter() {
vars = findVariablesInJSX(this);
findVariablesInJSX(this);
},

@@ -58,38 +58,2 @@ exit: function exit(node) {

},
VariableDeclaration: {
enter: function enter() {
// Add line 'context.<varname> = <varname>;'
// after each variable declaration in methods but not in jsx-attributes
// This fills the handlebars render-context with all local vars and react.props
if (isInMethodDefinition(this) && !wasInsideJSXExpressionContainer(this)) {
var _iteratorNormalCompletion = true;
var _didIteratorError = false;
var _iteratorError = undefined;
try {
for (var _iterator = this.get('declarations')[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
var decl = _step.value;
var varRef = vars.get(createKeyFromPath(decl.get('id')));
if (varRef) {
this.replaceWith(t.expressionStatement(t.assignmentExpression('=', createMemberExpression(localContextRef, varRef), decl.get('init').node)));
}
}
} catch (err) {
_didIteratorError = true;
_iteratorError = err;
} finally {
try {
if (!_iteratorNormalCompletion && _iterator['return']) {
_iterator['return']();
}
} finally {
if (_didIteratorError) {
throw _iteratorError;
}
}
}
}
}
},
MemberExpression: {

@@ -118,3 +82,2 @@ enter: function enter() {

function findVariablesInJSX(path) {
var vars = new Map();
path.traverse({

@@ -128,8 +91,7 @@ JSXExpressionContainer: {

if (!isThisPropsExpression(expression)) {
var key = createKeyFromPath(expression);
var varRef = vars.get(key);
if (!varRef) {
varRef = scope.generateUidIdentifier('var');
vars.set(key, varRef);
var varRef = newVariableReplacement(expression);
if (!isFunctionInsideJSXExpressionContainer(expression)) {
findClosestStatement(expression).insertBefore(t.expressionStatement(t.assignmentExpression('=', createMemberExpression(localContextRef, varRef.name), expression.node)));
}
this.setData('original', expression.node);
expression.replaceWith(t.identifier(varRef.name));

@@ -142,3 +104,2 @@ }

});
return vars;
}

@@ -148,10 +109,10 @@

switch (path.type) {
case 'Literal':
return path.get('value').node;
case 'Identifier':
case 'JSXIdentifier':
return path.get('name').node;
case 'MemberExpression':
case 'JSXMemberExpression':
return createKeyFromPath(path.get('object')) + '.' + createKeyFromPath(path.get('property'));
case 'LogicalExpression':
return createKeyFromPath(path.get('left')) + path.get('operator').node + createKeyFromPath(path.get('right'));
case 'ThisExpression':
return 'this';
default:

@@ -169,3 +130,5 @@ throw new Error('Unable to create key for path type: ' + path.type);

// TODO: Dynamic Component with Dynamic Partial
tagName = '{{' + stringifyExpression(filterThisExpressions(namePath)) + '}}';
var varRef = newVariableReplacement(namePath);
findClosestStatement(namePath).insertBefore(t.expressionStatement(t.assignmentExpression('=', createMemberExpression(localContextRef, varRef.name), rewriteJsxThisProps(namePath).node)));
tagName = '{{' + varRef.name + '}}';
} else {

@@ -190,3 +153,3 @@ tagName = namePath.get('name').node;

// ... attributes...
var attributes = opening.get('attributes');
var attributes = filterAttriubtes(opening.get('attributes'));
if (hasSpreadAttribute(attributes)) {

@@ -198,23 +161,20 @@ markup += processAttributesWithSpread(attributes, tagName, renderAsPartial);

if (selfClosing) {
markup += ' />';
if (renderAsPartial) {
markup += '}}';
} else {
if (renderAsPartial) {
markup += '}}';
} else {
markup += '>';
}
markup += '>';
}
// ... children...
var childMarkup = '';
path.traverse({
enter: function enter() {
if (this.isJSXElement()) {
markup += processJSXElement(this);
childMarkup += processJSXElement(this);
} else if (this.isJSXExpressionContainer() && !isInsideJSXAttribute(this)) {
markup += processJSXExpressionContainer.bind(this)();
childMarkup += processJSXExpressionContainer.bind(this)();
} else if (this.isJSXOpeningElement() || this.isJSXClosingElement()) {
// Skip
} else if (this.isLiteral()) {
markup += this.get('value').node;
childMarkup += this.get('value').node;
} else {

@@ -226,2 +186,3 @@ throw new Error('Unknown element during JSX processing: ' + this.type);

});
markup += childMarkup.trim().replace(/(>|}})[\n\t]+\s*(<|{{)/g, '$1$2');

@@ -231,3 +192,3 @@ // ... and closing tag

markup += '{{/' + tagName + '}}';
} else if (!selfClosing) {
} else if (!selfClosing || !isHtmlVoidElement(tagName)) {
markup += '</' + tagName + '>';

@@ -240,9 +201,9 @@ }

var objects = [];
var _iteratorNormalCompletion2 = true;
var _didIteratorError2 = false;
var _iteratorError2 = undefined;
var _iteratorNormalCompletion = true;
var _didIteratorError = false;
var _iteratorError = undefined;
try {
for (var _iterator2 = attributes[Symbol.iterator](), _step2; !(_iteratorNormalCompletion2 = (_step2 = _iterator2.next()).done); _iteratorNormalCompletion2 = true) {
var attribute = _step2.value;
for (var _iterator = attributes[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
var attribute = _step.value;

@@ -256,3 +217,3 @@ if (attribute.isJSXSpreadAttribute()) {

if (valuePath.isJSXExpressionContainer()) {
value = valuePath.get('expression').node;
value = valuePath.getData('original') || valuePath.get('expression').node;
} else if (valuePath.isLiteral()) {

@@ -265,12 +226,12 @@ value = valuePath.node;

} catch (err) {
_didIteratorError2 = true;
_iteratorError2 = err;
_didIteratorError = true;
_iteratorError = err;
} finally {
try {
if (!_iteratorNormalCompletion2 && _iterator2['return']) {
_iterator2['return']();
if (!_iteratorNormalCompletion && _iterator['return']) {
_iterator['return']();
}
} finally {
if (_didIteratorError2) {
throw _iteratorError2;
if (_didIteratorError) {
throw _iteratorError;
}

@@ -286,3 +247,4 @@ }

}
return ' {{#each ' + ref.name + '}}{{@key}}="{{this}}"{{/each}}';
findClosestStatement(attributes[0]).insertBefore(t.expressionStatement(t.assignmentExpression('=', createMemberExpression(localContextRef, ref.name), t.callExpression(createMemberExpression(t.callExpression(createMemberExpression(t.callExpression(createMemberExpression('Object', 'keys'), [createMemberExpression(localContextRef, ref.name)]), 'filter'), [t.functionExpression(null, [t.identifier('key')], t.blockStatement([t.returnStatement(t.logicalExpression('&&', t.logicalExpression('!=', t.identifier('key'), t.literal('children')), t.logicalExpression('!=', t.identifier('key'), t.literal('__$spread$__'))))]))]), 'reduce'), [t.functionExpression(null, [t.identifier('props'), t.identifier('key')], t.blockStatement([t.expressionStatement(t.assignmentExpression('=', t.memberExpression(t.identifier('props'), t.identifier('key'), true), t.memberExpression(createMemberExpression(localContextRef, ref.name), t.identifier('key'), true))), t.returnStatement(t.identifier('props'))])), t.objectExpression([])]))));
return '{{#each ' + ref.name + '}} {{@key}}="{{this}}"{{/each}}';
}

@@ -292,9 +254,9 @@

var markup = '';
var _iteratorNormalCompletion3 = true;
var _didIteratorError3 = false;
var _iteratorError3 = undefined;
var _iteratorNormalCompletion2 = true;
var _didIteratorError2 = false;
var _iteratorError2 = undefined;
try {
for (var _iterator3 = attributes[Symbol.iterator](), _step3; !(_iteratorNormalCompletion3 = (_step3 = _iterator3.next()).done); _iteratorNormalCompletion3 = true) {
var attribute = _step3.value;
for (var _iterator2 = attributes[Symbol.iterator](), _step2; !(_iteratorNormalCompletion2 = (_step2 = _iterator2.next()).done); _iteratorNormalCompletion2 = true) {
var attribute = _step2.value;

@@ -305,7 +267,7 @@ markup += ' ' + getAttributeName(attribute) + '=';

if (!renderAsPartial) {
markup += '{{';
markup += '"{{';
}
markup += stringifyExpression(filterThisExpressions(value.get('expression')));
if (!renderAsPartial) {
markup += '}}';
markup += '}}"';
}

@@ -319,12 +281,12 @@ } else if (value.isLiteral()) {

} catch (err) {
_didIteratorError3 = true;
_iteratorError3 = err;
_didIteratorError2 = true;
_iteratorError2 = err;
} finally {
try {
if (!_iteratorNormalCompletion3 && _iterator3['return']) {
_iterator3['return']();
if (!_iteratorNormalCompletion2 && _iterator2['return']) {
_iterator2['return']();
}
} finally {
if (_didIteratorError3) {
throw _iteratorError3;
if (_didIteratorError2) {
throw _iteratorError2;
}

@@ -349,17 +311,38 @@ }

this.replaceWith(t.functionExpression(null, this.node.params, t.blockStatement([t.returnStatement(body.node)]), false, false));
return;
}
if (this.isFunctionExpression()) {
this.setData('was-jsx', true);
var body = this.get('body').get('body');
var firstStatement = body[0];
firstStatement.insertBefore(t.variableDeclaration('var', [t.variableDeclarator(localContextRef, t.callExpression(createMemberExpression('Object', 'assign'), [t.objectExpression([]), localContextRef]))]));
if (this.isFunction()) {
var params = this.get('params');
for (var i = params.length - 1; i >= 0; i--) {
var _name3 = params[i].get('name').node;
var varRef = vars.get(createKeyFromPath(params[i]));
if (varRef) {
firstStatement.insertBefore(t.expressionStatement(t.assignmentExpression('=', createMemberExpression(localContextRef, varRef.name), t.identifier(_name3))));
var objects = [];
var _iteratorNormalCompletion3 = true;
var _didIteratorError3 = false;
var _iteratorError3 = undefined;
try {
for (var _iterator3 = params[Symbol.iterator](), _step3; !(_iteratorNormalCompletion3 = (_step3 = _iterator3.next()).done); _iteratorNormalCompletion3 = true) {
var param = _step3.value;
var _name3 = param.get('name').node;
var varRef = vars.get(createKeyFromPath(param));
if (varRef) {
objects.push(t.property(null, t.literal(varRef.name), t.identifier(_name3)));
}
}
} catch (err) {
_didIteratorError3 = true;
_iteratorError3 = err;
} finally {
try {
if (!_iteratorNormalCompletion3 && _iterator3['return']) {
_iterator3['return']();
}
} finally {
if (_didIteratorError3) {
throw _iteratorError3;
}
}
}
var body = this.get('body').get('body');
var firstStatement = body[0];
firstStatement.insertBefore(t.variableDeclaration('var', [t.variableDeclarator(localContextRef, t.callExpression(createMemberExpression('Object', 'assign'), [t.objectExpression([]), localContextRef, t.objectExpression(objects)]))]));
}

@@ -407,9 +390,4 @@ }

switch (path.get('type').node) {
case 'Literal':
return path;
case 'Identifier':
return path;
case 'BinaryExpression':
path.replaceWith(t.binaryExpression(path.get('operator').node, filterThisExpressions(path.get('left')).node, filterThisExpressions(path.get('right')).node));
return path;
case 'MemberExpression':

@@ -422,17 +400,2 @@ if (path.get('object').isThisExpression()) {

return path;
case 'CallExpression':
if (path.get('callee').isMemberExpression()) {
path.replaceWith(t.callExpression(filterThisExpressions(path.get('callee')).node, path.get('arguments').node));
}
return path;
case 'JSXMemberExpression':
var object = path.get('object');
if (object.isJSXMemberExpression()) {
path.replaceWith(t.jSXMemberExpression(filterThisExpressions(object).node, path.get('property').node));
} else {
if (object.get('name').node == 'this') {
path.replaceWith(path.get('property').node);
}
}
return path;
}

@@ -445,16 +408,6 @@ throw new Error('Unknown expression node type: ' + path.get('type').node);

switch (path.get('type').node) {
case 'Literal':
return path.get('value').node;
case 'Identifier':
return path.get('name').node;
case 'BinaryExpression':
return stringifyExpression(path.get('left')) + path.get('operator').node + stringifyExpression(path.get('right'));
case 'MemberExpression':
return stringifyExpression(path.get('object')) + '.' + stringifyExpression(path.get('property'));
case 'ThisExpression':
return 'this';
case 'JSXMemberExpression':
return stringifyExpression(path.get('object')) + '.' + stringifyExpression(path.get('property'));
case 'JSXIdentifier':
return path.get('name').node;
}

@@ -464,2 +417,14 @@ throw new Error('Unknown expression node type: ' + path.type);

function rewriteJsxThisProps(path) {
if (path.isJSXMemberExpression()) {
var object = path.get('object');
if (object.isJSXIdentifier() && object.get('name').node == 'this') {
path.replaceWith(createMemberExpression(localContextRef, path.get('property').node));
} else {
rewriteJsxThisProps(path.get('object'));
}
}
return path;
}
// -- helper -------------------

@@ -498,18 +463,22 @@

function isInMethodDefinition(path) {
return path.findParent(function (path) {
return path.isMethodDefinition();
});
}
function wasInsideJSXExpressionContainer(path) {
function isInsideJSXAttribute(path) {
return !!path.findParent(function (path) {
return path.getData('was-jsx');
return path.isJSXAttribute();
});
}
function isInsideJSXAttribute(path) {
return !!path.findParent(function (path) {
return path.isJSXAttribute();
function isFunctionInsideJSXExpressionContainer(path) {
var result = false;
path = path.findParent(function (path) {
return path.isFunction();
});
if (path && path.isFunction()) {
path = path.findParent(function (path) {
return path.isJSXExpressionContainer();
});
if (path && path.isJSXExpressionContainer()) {
result = true;
}
}
return result;
}

@@ -568,2 +537,19 @@

function newVariableReplacement(path) {
var key = createKeyFromPath(path);
var varRef = vars.get(key);
if (!varRef) {
varRef = path.scope.generateUidIdentifier('var');
vars.set(key, varRef);
}
return varRef;
}
function filterAttriubtes(attributes) {
var filteredAttributes = ['key', 'children'];
return attributes.filter(function (attribute) {
return !attribute.has('name') || filteredAttributes.indexOf(attribute.get('name').get('name').node) == -1;
});
}
function getAttributeName(attribute) {

@@ -579,3 +565,11 @@ var JSXAttributeAliases = {

}
function isHtmlVoidElement(tagName) {
var voidElements = ['area', 'base', 'br', 'col', 'embed', 'hr', 'img', 'input', 'keygen', 'link',
// Note: menuitem is not void in react
// 'menuitem',
'meta', 'param', 'source', 'track', 'wbr'];
return voidElements.indexOf(tagName) > -1;
}
};

@@ -6,3 +6,3 @@ module.exports = function(opts) {

let localContextRef = t.identifier('localContext');
let vars;
let vars = new Map();
return new Plugin('handlebars', {

@@ -51,3 +51,3 @@ visitor: {

enter() {
vars = findVariablesInJSX(this);
findVariablesInJSX(this);
},

@@ -168,25 +168,2 @@ exit(node) {

},
VariableDeclaration: {
enter() {
// Add line 'context.<varname> = <varname>;'
// after each variable declaration in methods but not in jsx-attributes
// This fills the handlebars render-context with all local vars and react.props
if (isInMethodDefinition(this) && !wasInsideJSXExpressionContainer(this)) {
for (let decl of this.get('declarations')) {
let varRef = vars.get(createKeyFromPath(decl.get('id')));
if (varRef) {
this.replaceWith(
t.expressionStatement(
t.assignmentExpression(
'=',
createMemberExpression(localContextRef, varRef),
decl.get('init').node
)
)
);
}
}
}
}
},
MemberExpression: {

@@ -242,3 +219,2 @@ enter() {

function findVariablesInJSX(path) {
let vars = new Map();
path.traverse({

@@ -252,8 +228,15 @@ JSXExpressionContainer: {

if (!isThisPropsExpression(expression)) {
let key = createKeyFromPath(expression);
let varRef = vars.get(key);
if (!varRef) {
varRef = scope.generateUidIdentifier('var');
vars.set(key, varRef);
let varRef = newVariableReplacement(expression);
if (!isFunctionInsideJSXExpressionContainer(expression)) {
findClosestStatement(expression).insertBefore(
t.expressionStatement(
t.assignmentExpression(
'=',
createMemberExpression(localContextRef, varRef.name),
expression.node
)
)
);
}
this.setData('original', expression.node);
expression.replaceWith(t.identifier(varRef.name));

@@ -266,3 +249,2 @@ }

});
return vars;
}

@@ -272,12 +254,10 @@

switch (path.type) {
case 'Literal':
return path.get('value').node;
case 'Identifier':
case 'JSXIdentifier':
return path.get('name').node;
case 'MemberExpression':
case 'JSXMemberExpression':
return createKeyFromPath(path.get('object')) + '.' + createKeyFromPath(path.get('property'));
case 'LogicalExpression':
return createKeyFromPath(path.get('left'))
+ path.get('operator').node
+ createKeyFromPath(path.get('right'));
case 'ThisExpression':
return 'this';
default:

@@ -295,3 +275,13 @@ throw new Error('Unable to create key for path type: ' + path.type);

// TODO: Dynamic Component with Dynamic Partial
tagName = '{{' + stringifyExpression(filterThisExpressions(namePath)) + '}}';
let varRef = newVariableReplacement(namePath);
findClosestStatement(namePath).insertBefore(
t.expressionStatement(
t.assignmentExpression(
'=',
createMemberExpression(localContextRef, varRef.name),
rewriteJsxThisProps(namePath).node
)
)
);
tagName = '{{' + varRef.name + '}}';
} else {

@@ -324,3 +314,3 @@ tagName = namePath.get('name').node;

// ... attributes...
var attributes = opening.get('attributes');
var attributes = filterAttriubtes(opening.get('attributes'));
if (hasSpreadAttribute(attributes)) {

@@ -332,23 +322,20 @@ markup += processAttributesWithSpread(attributes, tagName, renderAsPartial);

if (selfClosing) {
markup += ' />';
if (renderAsPartial) {
markup += '}}';
} else {
if (renderAsPartial) {
markup += '}}';
} else {
markup += '>';
}
markup += '>';
}
// ... children...
let childMarkup = '';
path.traverse({
enter() {
if (this.isJSXElement()) {
markup += processJSXElement(this);
childMarkup += processJSXElement(this);
} else if (this.isJSXExpressionContainer() && !isInsideJSXAttribute(this)) {
markup += processJSXExpressionContainer.bind(this)();
childMarkup += processJSXExpressionContainer.bind(this)();
} else if (this.isJSXOpeningElement() || this.isJSXClosingElement()) {
// Skip
} else if (this.isLiteral()) {
markup += this.get('value').node;
childMarkup += this.get('value').node;
} else {

@@ -360,2 +347,3 @@ throw new Error('Unknown element during JSX processing: ' + this.type);

});
markup += childMarkup.trim().replace(/(>|}})[\n\t]+\s*(<|{{)/g, '$1$2');

@@ -365,3 +353,3 @@ // ... and closing tag

markup += '{{/' + tagName + '}}';
} else if (!selfClosing) {
} else if (!selfClosing || !isHtmlVoidElement(tagName)) {
markup += '</' + tagName + '>';

@@ -382,3 +370,3 @@ }

if (valuePath.isJSXExpressionContainer()) {
value = valuePath.get('expression').node;
value = valuePath.getData('original') || valuePath.get('expression').node;
} else if (valuePath.isLiteral()) {

@@ -431,3 +419,82 @@ value = valuePath.node;

}
return ' {{#each ' + ref.name + '}}{{@key}}="{{this}}"{{/each}}';
findClosestStatement(attributes[0]).insertBefore(
t.expressionStatement(
t.assignmentExpression(
'=',
createMemberExpression(localContextRef, ref.name),
t.callExpression(
createMemberExpression(
t.callExpression(
createMemberExpression(
t.callExpression(
createMemberExpression('Object', 'keys'),
[
createMemberExpression(localContextRef, ref.name)
]
),
'filter'
),
[
t.functionExpression(
null,
[
t.identifier('key')
],
t.blockStatement([
t.returnStatement(
t.logicalExpression(
'&&',
t.logicalExpression(
'!=',
t.identifier('key'),
t.literal('children')
),
t.logicalExpression(
'!=',
t.identifier('key'),
t.literal('__$spread$__')
)
)
)
])
)
]
),
'reduce'
),
[
t.functionExpression(
null,
[
t.identifier('props'),
t.identifier('key')
],
t.blockStatement([
t.expressionStatement(
t.assignmentExpression(
'=',
t.memberExpression(
t.identifier('props'),
t.identifier('key'),
true
),
t.memberExpression(
createMemberExpression(localContextRef, ref.name),
t.identifier('key'),
true
)
)
),
t.returnStatement(
t.identifier('props')
)
])
),
t.objectExpression([])
]
)
)
)
);
return '{{#each ' + ref.name + '}} {{@key}}="{{this}}"{{/each}}';
}

@@ -442,7 +509,7 @@

if (!renderAsPartial) {
markup += '{{'
markup += '"{{'
}
markup += stringifyExpression(filterThisExpressions(value.get('expression')));
if (!renderAsPartial) {
markup += '}}'
markup += '}}"'
}

@@ -482,6 +549,19 @@ } else if (value.isLiteral()) {

);
return;
}
if (this.isFunctionExpression()) {
this.setData('was-jsx', true);
if (this.isFunction()) {
let params = this.get('params');
let objects = [];
for (let param of params) {
let name = param.get('name').node;
let varRef = vars.get(createKeyFromPath(param));
if (varRef) {
objects.push(
t.property(
null,
t.literal(varRef.name),
t.identifier(name)
)
);
}
}
let body = this.get('body').get('body');

@@ -497,3 +577,4 @@ let firstStatement = body[0];

t.objectExpression([]),
localContextRef
localContextRef,
t.objectExpression(objects)
]

@@ -504,18 +585,2 @@ )

);
let params = this.get('params');
for (let i = params.length - 1; i >= 0; i--) {
let name = params[i].get('name').node;
var varRef = vars.get(createKeyFromPath(params[i]));
if (varRef) {
firstStatement.insertBefore(
t.expressionStatement(
t.assignmentExpression(
'=',
createMemberExpression(localContextRef, varRef.name),
t.identifier(name)
)
)
);
}
}
}

@@ -606,15 +671,4 @@ }

switch (path.get('type').node) {
case 'Literal':
return path;
case 'Identifier':
return path;
case 'BinaryExpression':
path.replaceWith(
t.binaryExpression(
path.get('operator').node,
filterThisExpressions(path.get('left')).node,
filterThisExpressions(path.get('right')).node
)
);
return path;
case 'MemberExpression':

@@ -629,26 +683,2 @@ if (path.get('object').isThisExpression()) {

return path;
case 'CallExpression':
if (path.get('callee').isMemberExpression()) {
path.replaceWith(
t.callExpression(filterThisExpressions(path.get('callee')).node, path.get('arguments').node)
);
}
return path;
case 'JSXMemberExpression':
let object = path.get('object');
if (object.isJSXMemberExpression()) {
path.replaceWith(
t.jSXMemberExpression(
filterThisExpressions(object).node,
path.get('property').node
)
);
} else {
if (object.get('name').node == 'this') {
path.replaceWith(
path.get('property').node
)
}
}
return path;
}

@@ -661,18 +691,6 @@ throw new Error('Unknown expression node type: ' + path.get('type').node);

switch (path.get('type').node) {
case 'Literal':
return path.get('value').node;
case 'Identifier':
return path.get('name').node;
case 'BinaryExpression':
return stringifyExpression(path.get('left'))
+ path.get('operator').node
+ stringifyExpression(path.get('right'));
case 'MemberExpression':
return stringifyExpression(path.get('object')) + '.' + stringifyExpression(path.get('property'));
case 'ThisExpression':
return 'this';
case 'JSXMemberExpression':
return stringifyExpression(path.get('object')) + '.' + stringifyExpression(path.get('property'));
case 'JSXIdentifier':
return path.get('name').node;
}

@@ -682,2 +700,16 @@ throw new Error('Unknown expression node type: ' + path.type);

function rewriteJsxThisProps(path) {
if (path.isJSXMemberExpression()) {
let object = path.get('object');
if (object.isJSXIdentifier() && object.get('name').node == 'this') {
path.replaceWith(
createMemberExpression(localContextRef, path.get('property').node)
);
} else {
rewriteJsxThisProps(path.get('object'));
}
}
return path;
}
// -- helper -------------------

@@ -708,14 +740,18 @@

function isInMethodDefinition(path) {
return path.findParent(path => path.isMethodDefinition());
function isInsideJSXAttribute(path) {
return !!path.findParent(path => path.isJSXAttribute());
}
function wasInsideJSXExpressionContainer(path) {
return !!path.findParent(path => path.getData('was-jsx'));
function isFunctionInsideJSXExpressionContainer(path) {
let result = false;
path = path.findParent(path => path.isFunction());
if (path && (path.isFunction())) {
path = path.findParent(path => path.isJSXExpressionContainer());
if (path && path.isJSXExpressionContainer()) {
result = true;
}
}
return result;
}
function isInsideJSXAttribute(path) {
return !!path.findParent(path => path.isJSXAttribute());
}
function isThisPropsExpression(path) {

@@ -785,2 +821,20 @@ if (path.isMemberExpression()) {

function newVariableReplacement(path) {
let key = createKeyFromPath(path);
let varRef = vars.get(key);
if (!varRef) {
varRef = path.scope.generateUidIdentifier('var');
vars.set(key, varRef);
}
return varRef;
}
function filterAttriubtes(attributes) {
const filteredAttributes = [
'key',
'children'
];
return attributes.filter(attribute => !attribute.has('name') || filteredAttributes.indexOf(attribute.get('name').get('name').node) == -1);
}
function getAttributeName(attribute) {

@@ -797,2 +851,25 @@ const JSXAttributeAliases = {

function isHtmlVoidElement(tagName) {
const voidElements = [
'area',
'base',
'br',
'col',
'embed',
'hr',
'img',
'input',
'keygen',
'link',
// Note: menuitem is not void in react
// 'menuitem',
'meta',
'param',
'source',
'track',
'wbr'
];
return voidElements.indexOf(tagName) > -1;
}
}
{
"name": "babel-plugin-jsx-to-handlebars",
"version": "0.1.1",
"version": "0.1.2",
"description": "babel-plugin to convert simple stateless react compontents to handlebars templates",

@@ -11,6 +11,23 @@ "main": "dist/plugin.dist.js",

"browserify": "browserify demo/main.js > demo/index.js",
"test": "tape ./tests/**/*-test.js | faucet"
"test": "babel-istanbul cover tests/run.js | faucet"
},
"author": "markus.wolf@sinnerschrader.com",
"author": {
"name": "SinnerSchrader - Freie Radikale",
"email": "team-freie-radikale@sinnerschrader.com"
},
"contributors": [
{
"name": "Markus Wolf",
"email": "markus.wolf@sinnerschrader.com"
}
],
"license": "MIT",
"repository": {
"type": "git",
"url": "sinnerschrader/babel-plugin-jsx-to-handlebars"
},
"engines": {
"node": ">= 4.0.0",
"npm": ">= 2.5.1"
},
"dependencies": {

@@ -21,8 +38,11 @@ "babel": "^5.8.23",

"devDependencies": {
"babel-istanbul": "^0.3.20",
"browserify": "^11.1.0",
"classnames": "^2.1.3",
"faucet": "0.0.1",
"glob": "^5.0.14",
"nodemon": "^1.5.0",
"react": "^0.13.3",
"tape": "^4.2.0"
}
}
# babel-plugin-jsx-to-handlebars
[![GitHub license](https://img.shields.io/github/license/sinnerschrader/babel-plugin-jsx-to-handlebars.svg)](https://github.com/sinnerschrader/babel-plugin-jsx-to-handlebars)
[![Build Status](https://travis-ci.org/sinnerschrader/babel-plugin-jsx-to-handlebars.svg)](https://travis-ci.org/sinnerschrader/babel-plugin-jsx-to-handlebars)
[![npm version](https://img.shields.io/npm/v/babel-plugin-jsx-to-handlebars.svg)](https://www.npmjs.com/package/babel-plugin-jsx-to-handlebars)
Convertes simple stateless react compontents to handlebars templates

@@ -3,0 +8,0 @@

@@ -1,33 +0,50 @@

var fs = require('fs');
var babel = require('babel');
var Handlebars = require('handlebars');
import * as path from 'path';
import * as fs from 'fs';
import * as babel from 'babel';
import Handlebars from 'handlebars';
import React from 'react';
var helpers = function(path) {
return helpers.compile(helpers.load(helpers.transform(path)));
export function handlebars(file, data = {}) {
var dir = path.dirname(file);
return compileTemplate(customRequire(dir, babelTransform(file)), undefined, data)();
}
helpers.transform = function(path) {
var source = fs.readFileSync(path);
export function react(file, data = {}) {
let Component = require(path.resolve(__dirname, '..', file));
return React.renderToStaticMarkup(React.createElement(Component, data));
}
export function babelTransform(file, enablePlugin = true) {
let source = fs.readFileSync(file);
return babel.transform(source, {
stage: 0,
plugins: ['../dist/plugin.dist.js']
plugins: enablePlugin ? ['../dist/plugin.dist.js'] : []
}).code;
}
helpers.load = function(code) {
var mod = {
exports: {}
};
var fn = new Function('module', 'exports', 'require', code);
fn.call(null, mod, mod.exports, require);
return mod.exports;
export function customRequire(dir, code) {
let commonjs = function(code) {
let mod = {
exports: {}
};
let req = function(id) {
if (id[0] == '.') {
id = './' + path.join(dir, id);
return commonjs(babelTransform(id));
} else {
return require(id);
}
}
let fn = new Function('module', 'exports', 'require', code);
fn.call(null, mod, mod.exports, req);
return mod.exports;
}
return commonjs(code);
}
helpers.compile = function(templateModule, children) {
children = children || '';
export function compileTemplate(templateModule, children = '', data = {}) {
templateModule.call(null);
var name = templateModule.name;
return Handlebars.compile('{{#>' + name + '}}' + children + '{{/' + name + '}}');
let name = templateModule.name;
let props = Object.keys(data).map(key => `${key}="${data[key]}"`).join(' ');
return Handlebars.compile(`{{#>${name} ${props}}}${children}{{/${name}}}`);
}
module.exports = helpers;

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet