diff --git a/lib/assets/it-i18n.jst b/lib/assets/it-i18n.jst deleted file mode 100644 index b44aad1..0000000 --- a/lib/assets/it-i18n.jst +++ /dev/null @@ -1,13 +0,0 @@ -it('should be equal `${ it }` by ${ engine.name } in `${ lang }` lang', function (<% if (saveHtml) { %>done<% } %>) { - var bemjson = references['${ it }']['${ lang }'].bemjson, - expected = references['${ it }']['${ lang }'].html, - actual = engines['${ engine.name }']['${ lang }'].apply(bemjson); - - assertHtml(actual, expected);<% - if (saveHtml) { - var filename = [it, engine.name.toLowerCase().replace(' ', '-'), lang, 'html'].join('.'), - sep = '\n '; - - print(sep + 'fs.writeFile(path.join(__dirname, \'' + filename + '\'), beautifyHtml(actual), done);'); - } %> -}); diff --git a/lib/assets/it.jst b/lib/assets/it.jst index 3fa3b00..c3235c3 100644 --- a/lib/assets/it.jst +++ b/lib/assets/it.jst @@ -1,13 +1,50 @@ -it('should be equal `${ it }` by ${ engine.name }', function (<% if (saveHtml) { %>done<% } %>) { - var bemjson = references['${ it }'].bemjson, - expected = references['${ it }'].html, - actual = engines['${ engine.name }'].apply(bemjson); +<% +// prepares +var titleSuffix = lang ? ' in `' + lang + '` lang' : ''; +var subreference = lang ? '[\'' + lang + '\']' : ''; +var prettifyEngineName = function (ngn) { + return lang ? String(ngn).toLowerCase().replace(' ', '-') + '.' + lang : ngn; +}; +if (saveHtml) { + var filename = [it, prettifyEngineName(engine.name), 'html'].join('.'); +} +%> +it('should be equal `${ it }` by ${ engine.name }${ titleSuffix }', function (<% if (saveHtml || engine.async) { %>done<% } %>) { + var bemjson = references['${ it }']${ subreference }.bemjson, + expected = references['${ it }']${ subreference }.html;<% + +if (lang) { %> + lazies['${ engine.name }${ lang }'](); +<% } + +if (!engine.async) { %> + // sync mode + var actual = engines['${ engine.name }']${ subreference }.apply(bemjson); assertHtml(actual, expected);<% - if (saveHtml) { - var filename = [it, engine.name, 'html'].join('.'), - sep = '\n '; - print(sep + 'fs.writeFile(path.join(__dirname, \'' + filename + '\'), beautifyHtml(actual), done);'); - } %> +if (saveHtml) { %> + saveHtmlFile('${ filename }', actual, done); +<% } + +} else { // engine.async %> + // async mode + engines['${ engine.name }']${ subreference }.apply(bemjson, function(errs, actual) { + if (errs !== null) { + done(errs); + return; + } + + assertHtml(actual, expected, function(err) { +<% if (saveHtml) {%> + saveHtmlFile('${ filename }', actual, function() { + done(err || null); + }); +<% } else { %> + done(err || null); +<% } %> + }); + });<% +} %> + }); diff --git a/lib/assets/tmpl-spec.jst b/lib/assets/tmpl-spec.jst index 2826fec..a8869f0 100644 --- a/lib/assets/tmpl-spec.jst +++ b/lib/assets/tmpl-spec.jst @@ -1,9 +1,21 @@ +<% +function reRequire(where, what, lazy) { + var name = what.name, + target = what.target, + exportName = what.exportName; + lazy && print('lazies[\'' + lazy + '\'] = function () {\n'); + print('dropRequireCache(require, require.resolve(\'' + target + '\'));\n'); + print((lazy ? 'return ' : '') + where + '[\'' + name + '\'] = require(\'' + target + '\')' + exportName + ';\n'); + lazy && print('};\n'); +} +%> var assert = require('assert'), path = require('path'), <% if (saveHtml) { %> fs = require('fs'), - beautifyHtml = require('${ paths['js-beautify'] }').html, -<% } %> + beautifyHtml = function(html) { + return require('${ paths['js-beautify'] }').html(html, beautifyHtmlConfig); + }, beautifyHtmlConfig = { unformatted: [ 'a', 'span', 'img', 'address', 'script', 'h1', 'h2', 'h3', 'h4', 'h5','h6', @@ -13,11 +25,16 @@ var assert = require('assert'), 'font', 'ins', 'del', 'pre', 'address', 'dt', 'q', 'i', 'b', 'u', 's', 'bdo', 'em' ]}, + saveHtmlFile = function(filename, actual, done) { + fs.writeFile(path.join(__dirname, filename), beautifyHtml(actual), done); + }, +<% } %> dropRequireCache = require('enb/lib/fs/drop-require-cache'), HtmlDiffer = require('${ paths['html-differ'] }').HtmlDiffer, htmlDiffer = new HtmlDiffer('bem'), referencesFilename = require.resolve('${ paths.references }'), engines, + lazies = {}, references; describe('${ describe }', function() { @@ -27,19 +44,11 @@ describe('${ describe }', function() { engines = {}; <% _.forEach(engines, function(engine) { - function reRequire(where, what) { - var name = what.name, - target = what.target, - exportName = what.exportName; - print('dropRequireCache(require, require.resolve(\'' + target + '\'));\n'); - print(where + '[\'' + name + '\'] = require(\'' + target + '\')' + exportName + ';\n'); - } - - if (langs.length) { + if (langs && langs.length) { var engineObject = 'engines[\'' + engine.name + '\']'; print(engineObject + ' = {};\n'); _.forEach(engine.langs, function(lang) { - reRequire(engineObject, lang); + reRequire(engineObject, lang, engine.name + lang.name); }); } else { reRequire('engines', engine); @@ -51,9 +60,9 @@ describe('${ describe }', function() { describe('${ it }', function() { <% _.forEach(engines, function(engine) { - if (langs.length) { + if (langs && langs.length) { _.forEach(langs, function(lang) { - print(template('it-i18n', { + print(template('it', { it: it, engine: engine, lang: lang, @@ -64,6 +73,7 @@ describe('${ it }', function() { print(template('it', { it: it, engine: engine, + lang: null, saveHtml: saveHtml })); } @@ -72,9 +82,10 @@ describe('${ it }', function() { });<% }); %> }); -function assertHtml(actual, expected) { +function assertHtml(actual, expected, done) { if (htmlDiffer.isEqual(actual, expected)) { assert.ok(actual); + done && done(null); } else { assert.fail(actual, expected, null, '\n'); } diff --git a/lib/plugin.js b/lib/plugin.js index 5abafa8..c59ab5e 100644 --- a/lib/plugin.js +++ b/lib/plugin.js @@ -42,10 +42,11 @@ module.exports = function (helper) { return level; }), - langs: options.langs || [], + langs: options.langs, engines: _.map(engines, function (engine, name) { var techPath = engine.tech, tech = require(techPath), + async = !!engine.async, options = _.cloneDeep(engine.options || {}), target = '?.' + name.toLowerCase().replace(' ', '-') + '.js', exportName = options && options.exportName; @@ -62,6 +63,7 @@ module.exports = function (helper) { target: target, exportName: exportName, tech: tech, + async: async, options: options }; }), diff --git a/lib/techs/mock-lang-js.js b/lib/techs/mock-lang-js.js index 47c9e8a..a9b30f4 100644 --- a/lib/techs/mock-lang-js.js +++ b/lib/techs/mock-lang-js.js @@ -8,7 +8,7 @@ module.exports = require('enb/lib/build-flow').create() return vfs.read(source, 'utf8') .then(function (content) { var mock = [ - '(function(global, bem_) {', + ';(function(global, bem_) {', ' global.BEM = bem_;', ' var i18n = bem_.I18N = function(keyset, key, param) {', ' var result = key;', @@ -20,7 +20,7 @@ module.exports = require('enb/lib/build-flow').create() ' i18n.keyset = function() { return i18n }', ' i18n.key = function(key) { return key }', ' i18n.lang = function() { return }', - '})(this, typeof BEM === \'undefined\' ? {} : BEM);' + '}(this, typeof BEM === \'undefined\' ? {} : BEM));' ].join('\n'), mapIndex = content.lastIndexOf('//# sourceMappingURL='), map; diff --git a/lib/techs/references.js b/lib/techs/references.js index 61ef1fa..c3ca145 100644 --- a/lib/techs/references.js +++ b/lib/techs/references.js @@ -10,26 +10,34 @@ module.exports = require('enb/lib/build-flow').create() .useDirList('tmpl-specs') .builder(function (dirs) { var references = {}, - bemjsons = {}, - htmls = {}; + bemjsons = [], + htmls = []; dirs.forEach(function (dir) { dir.files.forEach(function (file) { var filename = file.name, - name = filename.split('.')[0]; + fullname = file.fullname, + name = filename.split('.')[0], + lang = getLang(fullname), + item = { + name: name, + fullname: fullname, + lang: lang + }; if (hasExt(filename, '.bemjson.js')) { - bemjsons[name] = file.fullname; + bemjsons.push(item); } else if (hasExt(filename, '.html')) { - htmls[name] = file.fullname; + htmls.push(item); } }); }); return vow.all([ - vow.all(Object.keys(bemjsons).map(function (name) { - var filename = bemjsons[name], - lang = getLang(filename); + vow.all(bemjsons.map(function (file) { + var name = file.name, + lang = file.lang, + filename = file.fullname; dropRequireCache(require, filename); @@ -45,11 +53,11 @@ module.exports = require('enb/lib/build-flow').create() } }); })), - vow.all(Object.keys(htmls).map(function (name) { - var filename = htmls[name], - lang = getLang(filename); + vow.all(htmls.map(function (file) { + var name = file.name, + lang = file.lang; - return vfs.read(filename, 'utf-8') + return vfs.read(file.fullname, 'utf-8') .then(function (source) { var reference = references[name] || (references[name] = {}); diff --git a/lib/techs/tmpl-spec.js b/lib/techs/tmpl-spec.js index d239c11..71bb27c 100644 --- a/lib/techs/tmpl-spec.js +++ b/lib/techs/tmpl-spec.js @@ -4,8 +4,7 @@ var path = require('path'), assetsDirname = path.join(__dirname, '..', 'assets'), readAssets = vow.all([ vfs.read(path.join(assetsDirname, 'tmpl-spec.jst'), 'utf-8'), - vfs.read(path.join(assetsDirname, 'it.jst'), 'utf-8'), - vfs.read(path.join(assetsDirname, 'it-i18n.jst'), 'utf-8') + vfs.read(path.join(assetsDirname, 'it.jst'), 'utf-8') ]), lodash = require('lodash'), template = lodash.template, @@ -40,13 +39,15 @@ module.exports = require('enb/lib/build-flow').create() references = require(referencesFilename), engines = this._engines, langs = this._langs, + oneLang = langs === true, + manyLangs = Array.isArray(langs) && langs.length > 0, saveHtml = this._saveHtml, coverageEngines = this._coverageEngines, coverageBundle = this._coverageBundle, its = {}; if (!this._coverageBundle) { - if (langs.length > 0) { + if (manyLangs) { Object.keys(references).forEach(function (name) { langs.forEach(function (lang) { var reference = references[name], @@ -69,10 +70,9 @@ module.exports = require('enb/lib/build-flow').create() } its = Object.keys(its); - return readAssets.spread(function (asset, it, iti18n) { + return readAssets.spread(function (asset, it) { var templates = { - it: it, - 'it-i18n': iti18n + it: it }, data = { describe: path.basename(nodePath) + ' (' + path.dirname(nodePath) + ')', @@ -83,7 +83,7 @@ module.exports = require('enb/lib/build-flow').create() exportName = engine.exportName ? '.' + engine.exportName : ''; - if (langs && !langs.length) { + if (oneLang) { target = coverageBundle ? target.replace('.js.instr.js', '.lang.js.instr.js') : target.replace('.js', '.lang.js'); @@ -91,13 +91,14 @@ module.exports = require('enb/lib/build-flow').create() target = './' + node.unmaskTargetName(target); - if (langs.length) { + if (manyLangs) { return { name: engine.name, langs: langs.map(function (lang) { var langTarget = target.replace('.js', '.' + lang + '.js'); return { name: lang, + async: engine.async, target: langTarget, exportName: exportName }; @@ -107,6 +108,7 @@ module.exports = require('enb/lib/build-flow').create() return { name: engine.name, + async: engine.async, target: target, exportName: exportName };