Updated i18n core plugin APIs to be asynchronous

To be done:
 - Better error handling in APIs
 - Fix threading issue with storePluginLanguageTranslations API
This commit is contained in:
Martin Hickey 2016-06-22 18:25:30 +01:00
parent c3ba5785cb
commit 80d8a2ce72
2 changed files with 125 additions and 116 deletions

View file

@ -8,70 +8,52 @@ const TRANSLATION_FILE_EXTENSION = 'json';
const TRANSLATION_STORE_PATH = kibanaPackage.__dirname + '/data/store_translations';
module.exports = {
storePluginLanguageTranslations: function (pluginName, pluginTranslationPath, language) {
storePluginLanguageTranslations: function (pluginName, pluginTranslationPath, language, cb) {
var translationFiles = [];
var languageList = [];
var translationStorePluginPath = module.exports.getPluginTranslationStoragePath(pluginName);
var translationFileName = language + '.' + TRANSLATION_FILE_EXTENSION;
module.exports.getPluginTranslationDetails(pluginTranslationPath, translationFiles, languageList);
var langSupported = false;
for (var langIndx in languageList) {
if (language === languageList[langIndx]) {
langSupported = true;
break;
}
}
if (!langSupported) {
return false;
}
if (!fs.existsSync(translationStorePluginPath)) {
createDirectoriesRecursively(translationStorePluginPath);
}
for (var fileIndx in translationFiles) {
if (!translationFiles.hasOwnProperty(fileIndx)) continue;
var translationFile = translationFiles[fileIndx];
var pluginTranslationFileName = getFileName(translationFile);
if (pluginTranslationFileName !== translationFileName) continue;
var translationJson = require(translationFile);
var fileToWrite = translationStorePluginPath + '/' + translationFileName;
saveTranslationToFile(fileToWrite, translationJson);
}
return translationFiles;
},
getPluginLanguageTranslation: function (pluginName, language) {
var translationStorePluginPath = module.exports.getPluginTranslationStoragePath(pluginName);
var translationFileName = language + '.' + TRANSLATION_FILE_EXTENSION;
var translationFile = translationStorePluginPath + '/' + translationFileName;
var translationStr = fs.readFileSync(translationFile);
return JSON.parse(translationStr);
},
getPluginTranslationDetails: function (pluginTranslationPath, translationFiles, languageList) {
getFilesRecursivelyFromTopDir(pluginTranslationPath, function parseDetails(fullPath) {
var files = getFilesFromDir(fullPath);
var fileLength = files.length;
for (var i = 0; i < fileLength; i++) {
var fullFilePath = files[i];
var fileName = getFileName(fullFilePath);
var fileExt = fileName.split('.').pop();
if (fileName === fileExt) continue;
if (fileExt !== TRANSLATION_FILE_EXTENSION) continue;
translationFiles.push(fullFilePath);
var lang = fileName.substr(0, fileName.lastIndexOf('.'));
if (languageList.indexOf(lang) !== -1) {
continue;
module.exports.getPluginTranslationDetails(pluginTranslationPath, translationFiles, languageList, function (err) {
var langSupported = false;
for (var langIndx in languageList) {
if (language === languageList[langIndx]) {
langSupported = true;
break;
}
}
if (langSupported) {
if (!fs.existsSync(translationStorePluginPath)) {
createDirectoriesRecursively(translationStorePluginPath);
}
for (var fileIndx in translationFiles) {
if (!translationFiles.hasOwnProperty(fileIndx)) continue;
var translationFile = translationFiles[fileIndx];
var pluginTranslationFileName = getFileName(translationFile);
if (pluginTranslationFileName !== translationFileName) continue;
var translationJson = require(translationFile);
var fileToWrite = translationStorePluginPath + '/' + translationFileName;
saveTranslationToFile(fileToWrite, translationJson);
}
languageList.push(lang);
}
});
return cb(null);
},
getPluginLanguageTranslation: function (pluginName, language, callback) {
var translationStorePluginPath = module.exports.getPluginTranslationStoragePath(pluginName);
var translationFileName = language + '.' + TRANSLATION_FILE_EXTENSION;
var translationFile = translationStorePluginPath + '/' + translationFileName;
fs.readFile(translationFile, function (err, translationStr) {
if (err) return callback(err);
return callback(null, JSON.parse(translationStr));
});
},
getPluginTranslationDetails: function (pluginTranslationPath, translationFiles, languageList, callback) {
getFilesRecursivelyFromTopDir(pluginTranslationPath, translationFiles, languageList);
return callback(null);
},
getPluginTranslationStoragePath: function (pluginName) {
@ -91,16 +73,34 @@ function saveTranslationToFile(translationFullFileName, translationJson) {
fs.writeFileSync(translationFullFileName, JSON.stringify(jsonToWrite, null, 4));
}
function getFilesRecursivelyFromTopDir(topDir, fileCallback) {
function getFilesRecursivelyFromTopDir(topDir, translationFiles, languageList) {
fs.readdirSync(topDir).forEach(function (name) {
var fullPath = path.join(topDir, name);
var stat = fs.statSync(fullPath);
if (stat.isDirectory()) {
fileCallback(fullPath);
getTranslationDetailsFromDirectory(fullPath, translationFiles, languageList);
}
});
}
function getTranslationDetailsFromDirectory(fullPath, translationFiles, languageList) {
var files = getFilesFromDir(fullPath);
var fileLength = files.length;
for (var i = 0; i < fileLength; i++) {
var fullFilePath = files[i];
var fileName = getFileName(fullFilePath);
var fileExt = fileName.split('.').pop();
if (fileName === fileExt) continue;
if (fileExt !== TRANSLATION_FILE_EXTENSION) continue;
translationFiles.push(fullFilePath);
var lang = fileName.substr(0, fileName.lastIndexOf('.'));
if (languageList.indexOf(lang) !== -1) {
continue;
}
languageList.push(lang);
}
}
function getFilesFromDir(dir) {
var fileList = [];

View file

@ -7,67 +7,74 @@ describe('Test plugin translations details for test_plugin_1', function () {
var pluginName = 'test_plugin_1';
var pluginTranslationPath = __dirname + '/' + pluginName + '/translations';
it('2 translation languages exist', function () {
it('2 translation languages exist', function (done) {
var result = true;
var expectedLanguages = ['en', 'de'];
var actualLanguages = getPluginTranslationLanguages(pluginName, pluginTranslationPath);
if (actualLanguages.length !== expectedLanguages.length) {
result = false;
} else {
var index = actualLanguages.length;
actualLanguages.sort();
expectedLanguages.sort();
while (index--) {
if (actualLanguages[index] !== expectedLanguages[index]) {
result = false;
break;
getPluginTranslationLanguages(pluginName, pluginTranslationPath, function (err, actualLanguages) {
if (actualLanguages.length !== expectedLanguages.length) {
result = false;
} else {
var index = actualLanguages.length;
actualLanguages.sort();
expectedLanguages.sort();
while (index--) {
if (actualLanguages[index] !== expectedLanguages[index]) {
result = false;
break;
}
}
}
}
expect(result).to.be(true);
expect(result).to.be(true);
done();
});
});
it('2 translation languages exist and wrongly expecting 1', function () {
it('2 translation languages exist and wrongly expecting 1', function (done) {
var result = true;
var expectedLanguages = ['de'];
var actualLanguages = getPluginTranslationLanguages(pluginName, pluginTranslationPath);
if (actualLanguages.length !== expectedLanguages.length) {
result = false;
} else {
var index = actualLanguages.length;
actualLanguages.sort();
expectedLanguages.sort();
while (index--) {
if (actualLanguages[index] !== expectedLanguages[index]) {
result = false;
break;
getPluginTranslationLanguages(pluginName, pluginTranslationPath, function (err, actualLanguages) {
if (actualLanguages.length !== expectedLanguages.length) {
result = false;
} else {
var index = actualLanguages.length;
actualLanguages.sort();
expectedLanguages.sort();
while (index--) {
if (actualLanguages[index] !== expectedLanguages[index]) {
result = false;
break;
}
}
}
}
expect(result).to.be(false);
expect(result).to.be(false);
done();
});
});
it('Translation files exist', function () {
it('Translation files exist', function (done) {
var result = true;
var expectedFiles = [
pluginTranslationPath + '/view1/de.json',
pluginTranslationPath + '/view1/en.json',
pluginTranslationPath + '/view2/en.json'
];
var actualFiles = getPluginTranslationFiles(pluginName, pluginTranslationPath);
if (actualFiles.length !== expectedFiles.length) {
result = false;
} else {
var index = actualFiles.length;
actualFiles.sort();
expectedFiles.sort();
while (index--) {
if (actualFiles[index] !== expectedFiles[index]) {
result = false;
break;
getPluginTranslationFiles(pluginName, pluginTranslationPath, function (err, actualFiles) {
if (actualFiles.length !== expectedFiles.length) {
result = false;
} else {
var index = actualFiles.length;
actualFiles.sort();
expectedFiles.sort();
while (index--) {
if (actualFiles[index] !== expectedFiles[index]) {
result = false;
break;
}
}
}
}
expect(result).to.be(true);
expect(result).to.be(true);
done();
});
});
});
@ -75,23 +82,23 @@ describe('Test storing translations for test_plugin_1', function () {
var pluginName = 'test_plugin_1';
var pluginTranslationPath = __dirname + '/' + pluginName + '/translations';
it('Translation plugin bundle for English' , function () {
it('Translation plugin bundle for English' , function (done) {
var result = true;
var language = 'en';
if (!i18n.storePluginLanguageTranslations(pluginName, pluginTranslationPath, language)) {
result = false;
} else {
i18n.storePluginLanguageTranslations(pluginName, pluginTranslationPath, language, function (err) {
var expectedTranslationJsonFile = __dirname + '/data/reference/' + pluginName + '/' + language + '.json';
var expectedTranslationJson = require(expectedTranslationJsonFile);
expectedTranslationJson = JSON.stringify(expectedTranslationJson);
var actualTranslationJson = i18n.getPluginLanguageTranslation(pluginName, language);
actualTranslationJson = JSON.stringify(actualTranslationJson);
if (actualTranslationJson !== expectedTranslationJson) {
result = false;
}
}
expect(result).to.be(true);
i18n.getPluginLanguageTranslation(pluginName, language, function (err, actualTranslationJson) {
actualTranslationJson = JSON.stringify(actualTranslationJson);
if (actualTranslationJson !== expectedTranslationJson) {
result = false;
}
});
expect(result).to.be(true);
done();
});
});
afterEach(function (done) {
@ -103,16 +110,18 @@ describe('Test storing translations for test_plugin_1', function () {
});
});
function getPluginTranslationLanguages(pluginName, pluginTranslationPath) {
function getPluginTranslationLanguages(pluginName, pluginTranslationPath, cb) {
var translationFiles = [];
var languageList = [];
i18n.getPluginTranslationDetails(pluginTranslationPath, translationFiles, languageList);
return languageList;
i18n.getPluginTranslationDetails(pluginTranslationPath, translationFiles, languageList, function (err) {
return cb(null, languageList);
});
}
function getPluginTranslationFiles(pluginName, pluginTranslationPath) {
function getPluginTranslationFiles(pluginName, pluginTranslationPath, cb) {
var translationFiles = [];
var languageList = [];
i18n.getPluginTranslationDetails(pluginTranslationPath, translationFiles, languageList);
return translationFiles;
i18n.getPluginTranslationDetails(pluginTranslationPath, translationFiles, languageList, function (err) {
return cb(null, translationFiles);
});
}