2011-08-22 22:34:20 -05:00
|
|
|
|
#!/usr/bin/env node
|
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
/**
|
|
|
|
|
* marked tests
|
|
|
|
|
* Copyright (c) 2011-2013, Christopher Jeffrey. (MIT Licensed)
|
|
|
|
|
* https://github.com/chjj/marked
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Modules
|
|
|
|
|
*/
|
|
|
|
|
|
2011-08-22 22:34:20 -05:00
|
|
|
|
var fs = require('fs')
|
|
|
|
|
, path = require('path')
|
2013-01-20 17:44:25 -06:00
|
|
|
|
, marked = require('../');
|
2013-01-03 08:29:40 -06:00
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
/**
|
|
|
|
|
* Load Tests
|
|
|
|
|
*/
|
|
|
|
|
|
2013-01-03 08:29:40 -06:00
|
|
|
|
function load() {
|
2013-01-06 21:54:44 -06:00
|
|
|
|
var dir = __dirname + '/tests'
|
|
|
|
|
, files = {}
|
|
|
|
|
, list
|
|
|
|
|
, file
|
|
|
|
|
, i
|
|
|
|
|
, l;
|
2011-08-22 22:34:20 -05:00
|
|
|
|
|
2013-01-06 21:54:44 -06:00
|
|
|
|
list = fs
|
2011-08-22 23:16:25 -05:00
|
|
|
|
.readdirSync(dir)
|
|
|
|
|
.filter(function(file) {
|
|
|
|
|
return path.extname(file) !== '.html';
|
|
|
|
|
})
|
|
|
|
|
.sort(function(a, b) {
|
|
|
|
|
a = path.basename(a).toLowerCase().charCodeAt(0);
|
|
|
|
|
b = path.basename(b).toLowerCase().charCodeAt(0);
|
|
|
|
|
return a > b ? 1 : (a < b ? -1 : 0);
|
|
|
|
|
});
|
2011-08-22 22:34:20 -05:00
|
|
|
|
|
2013-01-06 21:54:44 -06:00
|
|
|
|
i = 0;
|
|
|
|
|
l = list.length;
|
2011-08-22 23:16:25 -05:00
|
|
|
|
|
|
|
|
|
for (; i < l; i++) {
|
|
|
|
|
file = path.join(dir, list[i]);
|
|
|
|
|
files[path.basename(file)] = {
|
|
|
|
|
text: fs.readFileSync(file, 'utf8'),
|
|
|
|
|
html: fs.readFileSync(file.replace(/[^.]+$/, 'html'), 'utf8')
|
|
|
|
|
};
|
|
|
|
|
}
|
2012-03-10 17:27:44 -06:00
|
|
|
|
|
|
|
|
|
return files;
|
2013-01-03 08:29:40 -06:00
|
|
|
|
}
|
2011-08-22 23:16:25 -05:00
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
/**
|
|
|
|
|
* Test Runner
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
function runTests(engine, options) {
|
|
|
|
|
if (typeof engine !== 'function') {
|
|
|
|
|
options = engine;
|
|
|
|
|
engine = null;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
var engine = engine || marked
|
|
|
|
|
, options = options || {}
|
2013-01-06 21:54:44 -06:00
|
|
|
|
, files = options.files || load()
|
2013-01-06 21:43:11 -06:00
|
|
|
|
, complete = 0
|
2013-02-07 03:51:43 -06:00
|
|
|
|
, failed = 0
|
2013-12-04 00:24:17 -06:00
|
|
|
|
, failures = []
|
2011-08-22 23:16:25 -05:00
|
|
|
|
, keys = Object.keys(files)
|
2013-01-06 21:43:11 -06:00
|
|
|
|
, i = 0
|
|
|
|
|
, len = keys.length
|
2011-08-22 23:16:25 -05:00
|
|
|
|
, filename
|
|
|
|
|
, file
|
2013-08-07 06:10:50 -05:00
|
|
|
|
, flags
|
2011-08-22 23:16:25 -05:00
|
|
|
|
, text
|
2013-01-06 21:43:11 -06:00
|
|
|
|
, html
|
|
|
|
|
, j
|
|
|
|
|
, l;
|
2011-08-22 22:34:20 -05:00
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
if (options.marked) {
|
|
|
|
|
marked.setOptions(options.marked);
|
|
|
|
|
}
|
|
|
|
|
|
2011-10-22 08:36:34 -05:00
|
|
|
|
main:
|
2013-01-06 21:43:11 -06:00
|
|
|
|
for (; i < len; i++) {
|
|
|
|
|
filename = keys[i];
|
2011-08-22 23:16:25 -05:00
|
|
|
|
file = files[filename];
|
|
|
|
|
|
2013-08-07 06:10:50 -05:00
|
|
|
|
if (marked._original) {
|
|
|
|
|
marked.defaults = marked._original;
|
|
|
|
|
delete marked._original;
|
2013-02-07 03:51:43 -06:00
|
|
|
|
}
|
|
|
|
|
|
2013-08-07 06:10:50 -05:00
|
|
|
|
flags = filename.split('.').slice(1, -1);
|
|
|
|
|
if (flags.length) {
|
|
|
|
|
marked._original = marked.defaults;
|
|
|
|
|
marked.defaults = {};
|
|
|
|
|
Object.keys(marked._original).forEach(function(key) {
|
|
|
|
|
marked.defaults[key] = marked._original[key];
|
|
|
|
|
});
|
|
|
|
|
flags.forEach(function(key) {
|
|
|
|
|
var val = true;
|
2017-12-22 11:05:30 -06:00
|
|
|
|
if(key.indexOf('=') !== -1) {
|
|
|
|
|
val = decodeURIComponent(key.substring(key.indexOf('=') + 1));
|
|
|
|
|
key = key.substring(0, key.indexOf('='));
|
|
|
|
|
} else if (key.indexOf('no') === 0) {
|
2013-08-07 06:10:50 -05:00
|
|
|
|
key = key.substring(2);
|
|
|
|
|
val = false;
|
|
|
|
|
}
|
|
|
|
|
if (marked.defaults.hasOwnProperty(key)) {
|
|
|
|
|
marked.defaults[key] = val;
|
|
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
}
|
2013-08-07 06:40:08 -05:00
|
|
|
|
|
2011-10-22 08:36:34 -05:00
|
|
|
|
try {
|
2013-08-07 06:10:50 -05:00
|
|
|
|
text = engine(file.text).replace(/\s/g, '');
|
|
|
|
|
html = file.html.replace(/\s/g, '');
|
2011-10-22 08:36:34 -05:00
|
|
|
|
} catch(e) {
|
|
|
|
|
console.log('%s failed.', filename);
|
|
|
|
|
throw e;
|
2011-08-22 22:34:20 -05:00
|
|
|
|
}
|
|
|
|
|
|
2013-01-06 21:43:11 -06:00
|
|
|
|
j = 0;
|
|
|
|
|
l = html.length;
|
2011-08-22 23:16:25 -05:00
|
|
|
|
|
2013-01-06 21:43:11 -06:00
|
|
|
|
for (; j < l; j++) {
|
|
|
|
|
if (text[j] !== html[j]) {
|
2013-02-12 01:17:28 -06:00
|
|
|
|
failed++;
|
2013-12-04 00:24:17 -06:00
|
|
|
|
failures.push(filename);
|
2013-02-12 01:17:28 -06:00
|
|
|
|
|
2011-08-22 22:34:20 -05:00
|
|
|
|
text = text.substring(
|
2013-01-06 21:43:11 -06:00
|
|
|
|
Math.max(j - 30, 0),
|
|
|
|
|
Math.min(j + 30, text.length));
|
2012-03-11 00:45:28 -06:00
|
|
|
|
|
2011-08-22 22:34:20 -05:00
|
|
|
|
html = html.substring(
|
2013-01-06 21:43:11 -06:00
|
|
|
|
Math.max(j - 30, 0),
|
|
|
|
|
Math.min(j + 30, html.length));
|
2012-03-11 00:45:28 -06:00
|
|
|
|
|
2011-08-22 22:34:20 -05:00
|
|
|
|
console.log(
|
2011-10-22 08:36:34 -05:00
|
|
|
|
'\n#%d. %s failed at offset %d. Near: "%s".\n',
|
2013-01-06 21:43:11 -06:00
|
|
|
|
i + 1, filename, j, text);
|
2012-03-11 00:45:28 -06:00
|
|
|
|
|
|
|
|
|
console.log('\nGot:\n%s\n', text.trim() || text);
|
|
|
|
|
console.log('\nExpected:\n%s\n', html.trim() || html);
|
|
|
|
|
|
2013-01-06 21:43:11 -06:00
|
|
|
|
if (options.stop) {
|
2011-08-22 22:34:20 -05:00
|
|
|
|
break main;
|
|
|
|
|
}
|
2013-01-06 21:43:11 -06:00
|
|
|
|
|
|
|
|
|
continue main;
|
2011-08-22 22:34:20 -05:00
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2013-01-06 21:43:11 -06:00
|
|
|
|
complete++;
|
|
|
|
|
console.log('#%d. %s completed.', i + 1, filename);
|
2011-08-22 22:34:20 -05:00
|
|
|
|
}
|
|
|
|
|
|
2013-01-06 21:43:11 -06:00
|
|
|
|
console.log('%d/%d tests completed successfully.', complete, len);
|
2013-02-07 03:51:43 -06:00
|
|
|
|
if (failed) console.log('%d/%d tests failed.', failed, len);
|
2013-08-03 21:46:48 -07:00
|
|
|
|
|
2013-12-04 00:24:17 -06:00
|
|
|
|
// Tests currently failing.
|
2014-05-01 17:49:58 -05:00
|
|
|
|
if (~failures.indexOf('def_blocks.text')) {
|
|
|
|
|
failed -= 1;
|
2013-12-04 00:24:17 -06:00
|
|
|
|
}
|
2013-08-03 21:46:48 -07:00
|
|
|
|
|
|
|
|
|
return !failed;
|
2013-01-03 08:29:40 -06:00
|
|
|
|
}
|
2011-08-22 22:34:20 -05:00
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
/**
|
|
|
|
|
* Benchmark a function
|
|
|
|
|
*/
|
|
|
|
|
|
2013-01-03 08:29:40 -06:00
|
|
|
|
function bench(name, func) {
|
2013-01-06 21:54:44 -06:00
|
|
|
|
var files = bench.files || load();
|
|
|
|
|
|
|
|
|
|
if (!bench.files) {
|
|
|
|
|
bench.files = files;
|
|
|
|
|
|
2013-01-06 21:43:11 -06:00
|
|
|
|
// Change certain tests to allow
|
2012-01-06 01:07:45 -06:00
|
|
|
|
// comparison to older benchmark times.
|
2012-01-09 08:18:24 -06:00
|
|
|
|
fs.readdirSync(__dirname + '/new').forEach(function(name) {
|
2013-01-06 21:54:44 -06:00
|
|
|
|
if (path.extname(name) === '.html') return;
|
2012-01-09 08:18:24 -06:00
|
|
|
|
if (name === 'main.text') return;
|
|
|
|
|
delete files[name];
|
2012-01-02 23:59:13 -06:00
|
|
|
|
});
|
2013-01-06 21:54:44 -06:00
|
|
|
|
|
2012-01-14 04:45:06 -06:00
|
|
|
|
files['backslash_escapes.text'] = {
|
|
|
|
|
text: 'hello world \\[how](are you) today'
|
|
|
|
|
};
|
2013-01-06 21:54:44 -06:00
|
|
|
|
|
2012-01-28 16:53:34 -06:00
|
|
|
|
files['main.text'].text = files['main.text'].text.replace('* * *\n\n', '');
|
2012-01-02 23:59:13 -06:00
|
|
|
|
}
|
2011-08-22 23:16:25 -05:00
|
|
|
|
|
|
|
|
|
var start = Date.now()
|
|
|
|
|
, times = 1000
|
|
|
|
|
, keys = Object.keys(files)
|
2013-01-06 21:43:11 -06:00
|
|
|
|
, i
|
2011-08-22 23:16:25 -05:00
|
|
|
|
, l = keys.length
|
|
|
|
|
, filename
|
|
|
|
|
, file;
|
|
|
|
|
|
|
|
|
|
while (times--) {
|
|
|
|
|
for (i = 0; i < l; i++) {
|
|
|
|
|
filename = keys[i];
|
|
|
|
|
file = files[filename];
|
|
|
|
|
func(file.text);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
console.log('%s completed in %dms.', name, Date.now() - start);
|
2013-01-03 08:29:40 -06:00
|
|
|
|
}
|
2011-08-22 23:16:25 -05:00
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
/**
|
|
|
|
|
* Benchmark all engines
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
function runBench(options) {
|
|
|
|
|
var options = options || {};
|
|
|
|
|
|
|
|
|
|
// Non-GFM, Non-pedantic
|
2013-01-09 13:43:36 -06:00
|
|
|
|
marked.setOptions({
|
|
|
|
|
gfm: false,
|
|
|
|
|
tables: false,
|
|
|
|
|
breaks: false,
|
|
|
|
|
pedantic: false,
|
2013-02-07 03:51:43 -06:00
|
|
|
|
sanitize: false,
|
|
|
|
|
smartLists: false
|
2013-01-09 13:43:36 -06:00
|
|
|
|
});
|
2013-02-07 03:51:43 -06:00
|
|
|
|
if (options.marked) {
|
|
|
|
|
marked.setOptions(options.marked);
|
|
|
|
|
}
|
2013-01-03 08:29:40 -06:00
|
|
|
|
bench('marked', marked);
|
2011-08-22 23:16:25 -05:00
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
// GFM
|
2013-01-09 13:43:36 -06:00
|
|
|
|
marked.setOptions({
|
|
|
|
|
gfm: true,
|
|
|
|
|
tables: false,
|
|
|
|
|
breaks: false,
|
|
|
|
|
pedantic: false,
|
2013-02-07 03:51:43 -06:00
|
|
|
|
sanitize: false,
|
|
|
|
|
smartLists: false
|
2013-01-09 13:43:36 -06:00
|
|
|
|
});
|
2013-02-07 03:51:43 -06:00
|
|
|
|
if (options.marked) {
|
|
|
|
|
marked.setOptions(options.marked);
|
|
|
|
|
}
|
2013-01-03 08:29:40 -06:00
|
|
|
|
bench('marked (gfm)', marked);
|
2012-02-19 21:51:52 -06:00
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
// Pedantic
|
2013-01-09 13:43:36 -06:00
|
|
|
|
marked.setOptions({
|
|
|
|
|
gfm: false,
|
|
|
|
|
tables: false,
|
|
|
|
|
breaks: false,
|
|
|
|
|
pedantic: true,
|
2013-02-07 03:51:43 -06:00
|
|
|
|
sanitize: false,
|
|
|
|
|
smartLists: false
|
2013-01-09 13:43:36 -06:00
|
|
|
|
});
|
2013-02-07 03:51:43 -06:00
|
|
|
|
if (options.marked) {
|
|
|
|
|
marked.setOptions(options.marked);
|
|
|
|
|
}
|
2013-01-03 08:29:40 -06:00
|
|
|
|
bench('marked (pedantic)', marked);
|
2012-02-19 20:29:35 -06:00
|
|
|
|
|
2013-03-01 17:25:28 +08:00
|
|
|
|
// robotskirt
|
2013-05-28 20:32:11 -05:00
|
|
|
|
try {
|
|
|
|
|
bench('robotskirt', (function() {
|
|
|
|
|
var rs = require('robotskirt');
|
|
|
|
|
return function(text) {
|
|
|
|
|
var parser = rs.Markdown.std();
|
|
|
|
|
return parser.render(text);
|
|
|
|
|
};
|
|
|
|
|
})());
|
|
|
|
|
} catch (e) {
|
|
|
|
|
console.log('Could not bench robotskirt.');
|
|
|
|
|
}
|
2011-10-22 08:36:34 -05:00
|
|
|
|
|
2013-05-28 20:32:11 -05:00
|
|
|
|
// showdown
|
|
|
|
|
try {
|
|
|
|
|
bench('showdown (reuse converter)', (function() {
|
|
|
|
|
var Showdown = require('showdown');
|
2011-10-22 08:36:34 -05:00
|
|
|
|
var convert = new Showdown.converter();
|
2013-05-28 20:32:11 -05:00
|
|
|
|
return function(text) {
|
|
|
|
|
return convert.makeHtml(text);
|
|
|
|
|
};
|
|
|
|
|
})());
|
|
|
|
|
bench('showdown (new converter)', (function() {
|
|
|
|
|
var Showdown = require('showdown');
|
|
|
|
|
return function(text) {
|
|
|
|
|
var convert = new Showdown.converter();
|
|
|
|
|
return convert.makeHtml(text);
|
|
|
|
|
};
|
|
|
|
|
})());
|
|
|
|
|
} catch (e) {
|
|
|
|
|
console.log('Could not bench showdown.');
|
|
|
|
|
}
|
2011-08-22 23:16:25 -05:00
|
|
|
|
|
2013-05-28 20:32:11 -05:00
|
|
|
|
// markdown.js
|
|
|
|
|
try {
|
|
|
|
|
bench('markdown.js', require('markdown').parse);
|
|
|
|
|
} catch (e) {
|
|
|
|
|
console.log('Could not bench markdown.js.');
|
|
|
|
|
}
|
2013-01-03 08:29:40 -06:00
|
|
|
|
}
|
2011-08-22 22:34:20 -05:00
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
/**
|
|
|
|
|
* A simple one-time benchmark
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
function time(options) {
|
|
|
|
|
var options = options || {};
|
|
|
|
|
if (options.marked) {
|
|
|
|
|
marked.setOptions(options.marked);
|
|
|
|
|
}
|
2013-01-03 08:29:40 -06:00
|
|
|
|
bench('marked', marked);
|
|
|
|
|
}
|
2011-10-22 08:36:34 -05:00
|
|
|
|
|
2013-02-12 01:17:28 -06:00
|
|
|
|
/**
|
|
|
|
|
* Markdown Test Suite Fixer
|
|
|
|
|
* This function is responsible for "fixing"
|
|
|
|
|
* the markdown test suite. There are
|
|
|
|
|
* certain aspects of the suite that
|
|
|
|
|
* are strange or might make tests
|
|
|
|
|
* fail for reasons unrelated to
|
|
|
|
|
* conformance.
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
function fix(options) {
|
|
|
|
|
['tests', 'original', 'new'].forEach(function(dir) {
|
|
|
|
|
try {
|
|
|
|
|
fs.mkdirSync(path.resolve(__dirname, dir), 0755);
|
|
|
|
|
} catch (e) {
|
|
|
|
|
;
|
|
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
// rm -rf tests
|
|
|
|
|
fs.readdirSync(path.resolve(__dirname, 'tests')).forEach(function(file) {
|
|
|
|
|
fs.unlinkSync(path.resolve(__dirname, 'tests', file));
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
// cp -r original tests
|
|
|
|
|
fs.readdirSync(path.resolve(__dirname, 'original')).forEach(function(file) {
|
2013-08-07 06:10:50 -05:00
|
|
|
|
var nfile = file;
|
|
|
|
|
if (file.indexOf('hard_wrapped_paragraphs_with_list_like_lines.') === 0) {
|
|
|
|
|
nfile = file.replace(/\.(text|html)$/, '.nogfm.$1');
|
|
|
|
|
}
|
|
|
|
|
fs.writeFileSync(path.resolve(__dirname, 'tests', nfile),
|
2013-02-12 01:17:28 -06:00
|
|
|
|
fs.readFileSync(path.resolve(__dirname, 'original', file)));
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
// node fix.js
|
|
|
|
|
var dir = __dirname + '/tests';
|
|
|
|
|
|
|
|
|
|
fs.readdirSync(dir).filter(function(file) {
|
|
|
|
|
return path.extname(file) === '.html';
|
|
|
|
|
}).forEach(function(file) {
|
|
|
|
|
var file = path.join(dir, file)
|
|
|
|
|
, html = fs.readFileSync(file, 'utf8');
|
|
|
|
|
|
2013-08-04 06:52:02 -05:00
|
|
|
|
// fix unencoded quotes
|
2013-02-12 01:17:28 -06:00
|
|
|
|
html = html
|
|
|
|
|
.replace(/='([^\n']*)'(?=[^<>\n]*>)/g, '=&__APOS__;$1&__APOS__;')
|
|
|
|
|
.replace(/="([^\n"]*)"(?=[^<>\n]*>)/g, '=&__QUOT__;$1&__QUOT__;')
|
|
|
|
|
.replace(/"/g, '"')
|
|
|
|
|
.replace(/'/g, ''')
|
|
|
|
|
.replace(/&__QUOT__;/g, '"')
|
|
|
|
|
.replace(/&__APOS__;/g, '\'');
|
|
|
|
|
|
2013-12-23 07:46:31 -06:00
|
|
|
|
// add heading id's
|
|
|
|
|
html = html.replace(/<(h[1-6])>([^<]+)<\/\1>/g, function(s, h, text) {
|
|
|
|
|
var id = text
|
|
|
|
|
.replace(/'/g, '\'')
|
|
|
|
|
.replace(/"/g, '"')
|
|
|
|
|
.replace(/>/g, '>')
|
|
|
|
|
.replace(/</g, '<')
|
|
|
|
|
.replace(/&/g, '&');
|
|
|
|
|
|
|
|
|
|
id = id.toLowerCase().replace(/[^\w]+/g, '-');
|
|
|
|
|
|
|
|
|
|
return '<' + h + ' id="' + id + '">' + text + '</' + h + '>';
|
|
|
|
|
});
|
|
|
|
|
|
2013-02-12 01:17:28 -06:00
|
|
|
|
fs.writeFileSync(file, html);
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
// turn <hr /> into <hr>
|
|
|
|
|
fs.readdirSync(dir).forEach(function(file) {
|
|
|
|
|
var file = path.join(dir, file)
|
|
|
|
|
, text = fs.readFileSync(file, 'utf8');
|
|
|
|
|
|
|
|
|
|
text = text.replace(/(<|<)hr\s*\/(>|>)/g, '$1hr$2');
|
|
|
|
|
|
|
|
|
|
fs.writeFileSync(file, text);
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
// markdown does some strange things.
|
|
|
|
|
// it does not encode naked `>`, marked does.
|
|
|
|
|
(function() {
|
|
|
|
|
var file = dir + '/amps_and_angles_encoding.html';
|
|
|
|
|
var html = fs.readFileSync(file, 'utf8')
|
|
|
|
|
.replace('6 > 5.', '6 > 5.');
|
|
|
|
|
|
|
|
|
|
fs.writeFileSync(file, html);
|
|
|
|
|
})();
|
|
|
|
|
|
|
|
|
|
// cp new/* tests/
|
|
|
|
|
fs.readdirSync(path.resolve(__dirname, 'new')).forEach(function(file) {
|
|
|
|
|
fs.writeFileSync(path.resolve(__dirname, 'tests', file),
|
|
|
|
|
fs.readFileSync(path.resolve(__dirname, 'new', file)));
|
|
|
|
|
});
|
|
|
|
|
}
|
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
/**
|
|
|
|
|
* Argument Parsing
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
function parseArg(argv) {
|
|
|
|
|
var argv = process.argv.slice(2)
|
|
|
|
|
, options = {}
|
|
|
|
|
, orphans = []
|
|
|
|
|
, arg;
|
|
|
|
|
|
|
|
|
|
function getarg() {
|
|
|
|
|
var arg = argv.shift();
|
|
|
|
|
|
|
|
|
|
if (arg.indexOf('--') === 0) {
|
|
|
|
|
// e.g. --opt
|
|
|
|
|
arg = arg.split('=');
|
|
|
|
|
if (arg.length > 1) {
|
|
|
|
|
// e.g. --opt=val
|
|
|
|
|
argv.unshift(arg.slice(1).join('='));
|
|
|
|
|
}
|
|
|
|
|
arg = arg[0];
|
|
|
|
|
} else if (arg[0] === '-') {
|
|
|
|
|
if (arg.length > 2) {
|
|
|
|
|
// e.g. -abc
|
|
|
|
|
argv = arg.substring(1).split('').map(function(ch) {
|
|
|
|
|
return '-' + ch;
|
|
|
|
|
}).concat(argv);
|
|
|
|
|
arg = argv.shift();
|
|
|
|
|
} else {
|
|
|
|
|
// e.g. -a
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
// e.g. foo
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return arg;
|
2013-01-03 08:29:40 -06:00
|
|
|
|
}
|
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
while (argv.length) {
|
|
|
|
|
arg = getarg();
|
|
|
|
|
switch (arg) {
|
2013-02-12 01:17:28 -06:00
|
|
|
|
case '-f':
|
|
|
|
|
case '--fix':
|
|
|
|
|
case 'fix':
|
|
|
|
|
options.fix = true;
|
|
|
|
|
break;
|
2013-02-07 03:51:43 -06:00
|
|
|
|
case '-b':
|
|
|
|
|
case '--bench':
|
|
|
|
|
options.bench = true;
|
|
|
|
|
break;
|
|
|
|
|
case '-s':
|
|
|
|
|
case '--stop':
|
|
|
|
|
options.stop = true;
|
|
|
|
|
break;
|
|
|
|
|
case '-t':
|
|
|
|
|
case '--time':
|
|
|
|
|
options.time = true;
|
|
|
|
|
break;
|
|
|
|
|
default:
|
|
|
|
|
if (arg.indexOf('--') === 0) {
|
|
|
|
|
opt = camelize(arg.replace(/^--(no-)?/, ''));
|
|
|
|
|
if (!marked.defaults.hasOwnProperty(opt)) {
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
options.marked = options.marked || {};
|
|
|
|
|
if (arg.indexOf('--no-') === 0) {
|
|
|
|
|
options.marked[opt] = typeof marked.defaults[opt] !== 'boolean'
|
|
|
|
|
? null
|
|
|
|
|
: false;
|
|
|
|
|
} else {
|
|
|
|
|
options.marked[opt] = typeof marked.defaults[opt] !== 'boolean'
|
|
|
|
|
? argv.shift()
|
|
|
|
|
: true;
|
|
|
|
|
}
|
|
|
|
|
} else {
|
|
|
|
|
orphans.push(arg);
|
|
|
|
|
}
|
|
|
|
|
break;
|
|
|
|
|
}
|
2011-08-22 23:16:25 -05:00
|
|
|
|
}
|
2013-01-03 08:29:40 -06:00
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
return options;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Helpers
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
function camelize(text) {
|
|
|
|
|
return text.replace(/(\w)-(\w)/g, function(_, a, b) {
|
|
|
|
|
return a + b.toUpperCase();
|
2013-01-06 21:43:11 -06:00
|
|
|
|
});
|
2013-01-03 08:29:40 -06:00
|
|
|
|
}
|
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
/**
|
|
|
|
|
* Main
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
function main(argv) {
|
|
|
|
|
var opt = parseArg();
|
|
|
|
|
|
2013-02-12 01:17:28 -06:00
|
|
|
|
if (opt.fix) {
|
|
|
|
|
return fix(opt);
|
|
|
|
|
}
|
|
|
|
|
|
2013-02-07 03:51:43 -06:00
|
|
|
|
if (opt.bench) {
|
|
|
|
|
return runBench(opt);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (opt.time) {
|
|
|
|
|
return time(opt);
|
|
|
|
|
}
|
|
|
|
|
|
2013-08-04 07:12:52 -05:00
|
|
|
|
return runTests(opt);
|
2013-02-07 03:51:43 -06:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Execute
|
|
|
|
|
*/
|
|
|
|
|
|
2013-01-03 08:29:40 -06:00
|
|
|
|
if (!module.parent) {
|
2013-02-07 03:51:43 -06:00
|
|
|
|
process.title = 'marked';
|
2013-08-04 07:12:52 -05:00
|
|
|
|
process.exit(main(process.argv.slice()) ? 0 : 1);
|
2011-08-22 23:16:25 -05:00
|
|
|
|
} else {
|
2013-02-07 03:51:43 -06:00
|
|
|
|
exports = main;
|
|
|
|
|
exports.main = main;
|
|
|
|
|
exports.runTests = runTests;
|
|
|
|
|
exports.runBench = runBench;
|
|
|
|
|
exports.load = load;
|
|
|
|
|
exports.bench = bench;
|
|
|
|
|
module.exports = exports;
|
2011-08-22 23:16:25 -05:00
|
|
|
|
}
|