Created
September 1, 2011 18:22
-
-
Save DmitrySoshnikov/1186853 to your computer and use it in GitHub Desktop.
Runtime documentation for function declarations
This file contains hidden or 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
/** | |
* Simple doc-property generator. Uses JavaDoc style comments. | |
* Also provides type checking guards. | |
* | |
* Dependencies: SpiderMonkey >= 1.7 | |
* | |
* by Dmitry Soshnikov <[email protected]> | |
* MIT Style License | |
*/ | |
/** | |
* include | |
* @param {String} filename -- file to load and pre-process | |
* | |
* Loads source file and processes it with | |
* forming __doc__ property of function declarations. | |
* Also provides type checking guards. Finally, "eval"s | |
* the source in the global context. | |
* | |
* TODO: | |
* - support FE (including anonymous) | |
* - better regexp to consider more cases | |
*/ | |
function include(filename) { | |
// get the source as a string | |
var source = snarf(filename); | |
var re = /(\/\*[^/]*\*\/)\s*(function\s*(\w*)\s*\([^)]+\)\s*{)?/; | |
var globalRe = RegExp(re.source, "g"); | |
var singleRe = RegExp(re.source); | |
source = source.replace(globalRe, function(data) { | |
// separate doc-string, function name and header | |
var [_, comment, header, name] = data.match(singleRe); | |
// since function declarations are created on | |
// entering the context, we may place __doc__ generation | |
// before the function definiton itself (thus, we don't need to | |
// find the closing } in the regexp, but only function header | |
var transformedCode = name + ".__doc__ = " + '"' + comment.replace(/\n/g, "\\n") + '";'; | |
// validation code | |
var paramsRe = /@param {(\w+)} (\w+)/g; | |
var validationCode = []; | |
var param; | |
while (param = paramsRe.exec(comment)) { | |
var paramType = param[1].toLowerCase(); | |
var paramName = param[2]; | |
// build simple validation if (typeof name != type) throw TypeError(...) | |
validationCode.push( | |
'if (typeof ' + paramName + ' != "' + paramType + '") ' + | |
'throw TypeError(\'"' + paramName + '" must be a ' + paramType + '\');' | |
); | |
} | |
return transformedCode + header + validationCode.join(""); | |
}); | |
("global", eval)(source); | |
} | |
/** | |
* help | |
* @param {Function} fn | |
* Prints help on a function | |
*/ | |
function help(fn) { | |
print('Help on "' + fn.name + '" function:\n'); | |
print(fn.__doc__); | |
} |
This file contains hidden or 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
/** | |
* sum | |
* @param {Number} x | |
* @param {Number} y | |
* The function of summation. | |
*/ | |
function sum(x, y) { | |
return x + y; | |
} | |
/** | |
* multSum | |
* @param {Number} x | |
* @param {Number} y | |
* @param {String} value | |
* The function of calculation. | |
*/ | |
function calculate(x, y, value) { | |
// comment | |
print(value + ": " + sum(x, y)); | |
} |
This file contains hidden or 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
// load our library | |
load("doc.js"); | |
// and the test source | |
include("source.js"); | |
// ---------- Test documentation ---------- | |
help(sum); | |
// Result: | |
// Help on "sum" function: | |
// | |
// /** | |
// * sum | |
// * @param {Number} x | |
// * @param {Number} y | |
// * The function of summation. | |
// */ | |
help(calculate); | |
// Result: | |
// Help on "calculate" function: | |
// | |
// /** | |
// * multSum | |
// * @param {Number} x | |
// * @param {Number} y | |
// * @param {String} value | |
// * The function of calculation. | |
// */ | |
// ---------- Test guards ---------- | |
sum(1, 2); // 3, OK | |
calculate(1, 2, "value"); // value: 3 | |
sum(1, "2"); // TypeError: "y" must be a number | |
calculate(1, 2, 4); // TypeError: "value" must be a string |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment