Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
Download
80681 views
1
/**
2
* Copyright 2013 Facebook, Inc.
3
*
4
* Licensed under the Apache License, Version 2.0 (the "License");
5
* you may not use this file except in compliance with the License.
6
* You may obtain a copy of the License at
7
*
8
* http://www.apache.org/licenses/LICENSE-2.0
9
*
10
* Unless required by applicable law or agreed to in writing, software
11
* distributed under the License is distributed on an "AS IS" BASIS,
12
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
* See the License for the specific language governing permissions and
14
* limitations under the License.
15
*/
16
var esprima = require('esprima-fb');
17
var Syntax = esprima.Syntax;
18
19
function traverse(node, visitor) {
20
var key, child;
21
22
if (visitor(node) === false) {
23
return;
24
}
25
for (key in node) {
26
child = node[key];
27
if (typeof child === 'object' && child !== null) {
28
traverse(child, visitor);
29
}
30
}
31
}
32
33
var javelinInstallsRe = /@javelin-installs\s+(.*)/g;
34
function extractJavelinSymbols(code) {
35
var ast = esprima.parse(code);
36
var defines = {};
37
var requires = {};
38
var id = null;
39
40
var visitor = function (node) {
41
if (node.type === Syntax.MemberExpression && !node.computed &&
42
node.object.name === 'JX') {
43
var symbolName = 'JX.' + node.property.name;
44
if (!defines[symbolName]) {
45
requires[symbolName] = true;
46
}
47
}
48
};
49
50
ast.body.forEach(function(node) {
51
var symbolName;
52
// Look for calls to JX.install() and JX.behavior()
53
if (node.type === Syntax.ExpressionStatement &&
54
node.expression.type === Syntax.CallExpression &&
55
node.expression.callee.type === Syntax.MemberExpression &&
56
!node.expression.callee.object.computed &&
57
node.expression.callee.object.name === 'JX') {
58
59
var expressionArgs = node.expression['arguments'];
60
if (node.expression.callee.property.name === 'install') {
61
symbolName = 'JX.' + expressionArgs[0].value;
62
defines[symbolName] = true;
63
if (!id) {
64
id = symbolName;
65
}
66
} else if (node.expression.callee.property.name === 'behavior') {
67
symbolName = 'javelin-behavior-' + expressionArgs[0].value;
68
defines[symbolName] = true;
69
if (!id) {
70
id = symbolName;
71
}
72
}
73
}
74
});
75
76
ast.body.forEach(function(node) {
77
traverse(node, visitor);
78
});
79
80
var match;
81
// Next we need to look at the docblock for javelin-installs.
82
while (match = javelinInstallsRe.exec(code)) {
83
var name = 'JX.' + match[1].split('.')[1];
84
delete requires[name];
85
defines[name] = true;
86
}
87
88
return {
89
id: id,
90
defines: Object.keys(defines),
91
requires: Object.keys(requires)
92
};
93
}
94
95
module.exports = extractJavelinSymbols;
96
97