Created
September 14, 2013 04:50
-
-
Save iamnoah/6558898 to your computer and use it in GitHub Desktop.
Convert stealJS modules to AMD modules
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/** | |
* Shaper for cleaning up steal 3.2 declarations. Multiple calls are collapsed into a single | |
* wrapped call and non-dependant arguments are sorted. | |
*/ | |
if (typeof define !== 'function') { var define = require('amdefine')(module); } | |
define(['../shaper', '../fmt', '../ref', '../tkn'], function(Shaper, Fmt, Ref, tkn) { | |
"use strict"; "use restrict"; | |
var args = process.argv, | |
dir = args[2].replace(process.env.SRC_ROOT, "").replace(/(^\/|\/$)/, "").split("/").slice(0, -1).join("/") + "/"; | |
var EXT = /\.[^\/]+$/i, | |
DOT_JS = /\.js$/i; | |
function fixPath(path, i) { | |
// a steal module is "name" (directory), but an AMD module is "name/name" (file - .js) | |
var p = path.value; | |
if (p.indexOf("//") === 0) { | |
p = path.value = p.substring(2); | |
} | |
if (path.type === tkn.FUNCTION) { | |
throw new Error("argument " + i + " is a function! "+ path.getSrc()); | |
} | |
if (p.indexOf("./") === 0) { | |
p = path.value = dir + path.value.substring(2); | |
// relative paths are always to a file, not a module, so must have an extension | |
if (!p.match(EXT)) { | |
// if there wasn't one, it was js | |
p = path.value = path.value + ".js"; | |
} | |
} | |
if (p.match(/\.mustache$/i)) { | |
path.value = "r/mustache!" + path.value; | |
} else { | |
if (p.match(DOT_JS)) { | |
// the .js is no longer necessary and seems to make require think | |
// it's an absolute path | |
path.value = p.replace(DOT_JS, ""); | |
} else { | |
// if it's a steal "module", we need to append the name again to | |
// match require's concept of a module | |
var parts = p.split("/"); | |
path.value += "/" + parts[parts.length - 1]; | |
} | |
} | |
return Shaper.parse(JSON.stringify(path.value)); | |
} | |
new Shaper("amdify", function(root) { | |
return Shaper.traverse(root, { | |
pre: function(node, ref) { | |
var replacement; | |
// TODO 6 thens is silly, but this could be more generic | |
if (Shaper.match("steal($$).then($$).then($$).then($$).then($$)", node) || | |
Shaper.match("steal($$).then($$).then($$).then($$)", node) || | |
Shaper.match("steal($$).then($$).then($$)", node) || | |
Shaper.match("steal($$).then($$)", node)) { | |
var kids = [], | |
srcs = []; | |
var n = node; | |
var func; | |
while(n) { | |
// XXX since this is pre-order, the first set of steals we get to is the last | |
// but we don't want to mess up the function arguments, so they need to go first | |
if (kids.length) { | |
srcs.push(",\n\t"); | |
} else { | |
// the first steals we encounter may include the function | |
var firstKids = n.children[1].children; | |
if (firstKids[firstKids.length - 1].type === tkn.FUNCTION) { | |
func = firstKids.pop(); | |
} | |
} | |
kids.push.apply(kids, n.children[1].children); | |
srcs.push.apply(srcs, n.children[1].srcs.slice(1, -1)); | |
if (n.children[0].type === tkn.DOT) { | |
n = n.children[0].children[0]; | |
} else { | |
n = null; | |
} | |
} | |
srcs.unshift("skip"); | |
replacement = { | |
fn: func, | |
list: { | |
children: kids, | |
srcs: srcs | |
} | |
}; | |
} else if (Shaper.match("steal($$);", node)) { | |
replacement = { | |
semi: true, | |
list: node.expression.children[1] | |
}; | |
} else if (Shaper.match("steal.then($$)", node)) { | |
replacement = { | |
list: node.children[1] | |
}; | |
} else if (Shaper.match("steal($$)", node)) { | |
// XXX for some reason, the above doesn't always match... | |
replacement = { | |
list: node.children[1] | |
}; | |
} | |
if (Shaper.match("steal.plugins", node)) { | |
ref.set(Shaper.parse("false")); | |
} | |
if (replacement) { | |
var list = replacement.list; | |
var args = list.children; | |
var fn = replacement.fn || args.pop(); | |
if (fn.type !== tkn.FUNCTION) { | |
args.push(fn); | |
fn = null; | |
} | |
// recreate the list as an array, using the same commas and spacing | |
var deps = Shaper.replace.apply(Shaper, | |
["["+ args.map(function(arg, i) { | |
return "$" + (i < args.length - 1 ? list.srcs[i + 1] : ""); | |
}).join("") + "]"].concat(args.map(fixPath))); | |
if (fn) { | |
ref.set(Shaper.replace("define($,\n$)" + (replacement.semi ? ";" : ""), deps, fn)); | |
} else { | |
ref.set(Shaper.replace("require($)" + (replacement.semi ? ";" : ""), deps)); | |
} | |
return "break"; | |
} | |
} | |
}); | |
}); | |
return Shaper.get("amdify"); | |
}); | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment