i18nucleus-onesky
Version:
OneSky translation provider middleware for i18nucleus
254 lines (232 loc) • 7.69 kB
JavaScript
var pjson = require('./package.json')
, path = require('path')
, os = require('os')
, async = require('breeze-async')
, request = require('request')
, crypto = require('crypto')
, _ = require('underscore')
, flat = require('flat')
, fs = require('node-fs')
, rmdir = require('rimraf')
, colors = require('colors')
, OneSky = require('onesky')
, defineOptions = require('./options')
, oneSky = null
, baseUrl = 'https://platform.api.onesky.io/1';
function i18nucleus_onesky () {
var version = pjson.version
, type = 'translationProvider'
, name = pjson.name
, options = {}
, utils = null
, parentOptions = null
, MwareError = null;
function setOptions (_options, _utils) {
utils = _utils;
var optionObj = defineOptions(_options, utils);
if (!optionObj.err) {
options = optionObj.options;
}
return optionObj;
}
function init (_parentOptions, _MwareError, cb) {
parentOptions = _parentOptions;
MwareError = _MwareError;
oneSky = OneSky(options.publicKey, options.secretKey);
cb();
}
function buildAuthObj () {
var now = Math.round((new Date()).getTime() / 1000)
, concatStr = now + options.secretKey
, devHash = crypto.createHash('md5').update(concatStr).digest('hex');
return {
api_key: options.publicKey
, timestamp: now
, dev_hash: devHash
};
}
function buildGetRequestParams (partUrl, paramObj) {
var qsObj = paramObj || {};
qsObj = _.extend(buildAuthObj(), qsObj);
return {
url: baseUrl + partUrl
, qs: qsObj
, method: 'GET'
, headers: {
'content-type': 'application/json'
}
};
}
function getLocalesSummary (cb) {
var partialUrl = '/projects/' + options.platformId + '/languages'
, authObj = null
, requestOpts = null;
authObj = buildAuthObj();
requestOpts = buildGetRequestParams(partialUrl, authObj);
request(requestOpts, function (err, incomingMsg, response) {
if (err) {
return cb(new MwareError(err, name));
} else {
function buildLocaleData (rawData) {
return {
locale: rawData.locale
, region: rawData.region
, is_base_language: rawData.is_base_language
, completeness: parseFloat(rawData.translation_progress) / 100.0 * 100
, name: {
local: rawData.local_name
, english: rawData.english_name
}
};
}
response = JSON.parse(response);
if (!response.data) {
return cb(new MwareError(response.meta.message, name));
} else {
response = response.data;
var locs = []
, defaultLng = parentOptions.defaultLng
, supportedLngs = parentOptions.supportedLngs
, defaultLocale = _.find(response, function (obj) { return obj.code == defaultLng; });
defaultLocale = buildLocaleData(defaultLocale);
locs.push(defaultLocale);
supportedLngs.forEach(function (lng) {
if (lng != defaultLng) {
var localeObj = _.find(response, function (obj) { return obj.code == lng; });
if (localeObj) {
localeObj = buildLocaleData(localeObj);
locs.push(localeObj);
}
}
});
return cb(null, locs);
}
}
});
};
function getTranslations (locale, cb) {
var authObj = null
, namespaces = parentOptions.namespaces
, partialUrl = '/projects/' + options.platformId + '/translations'
, paramObj = null
, allParamObj = null
, requestOpts = null
, totalTerms = 0
, retObj = { translations: {} };
function nsIterrator (ns, next) {
var file = ns + '.json';
authObj = buildAuthObj();
paramObj = {
locale: locale
, source_file_name: file
, export_file_name: 'gimme.json'
};
allParamObj = _.extend(authObj, paramObj);
requestOpts = buildGetRequestParams(partialUrl, allParamObj);
request(requestOpts, function (err, incomingMsg, response) {
if (err) {
next(err);
} else {
response = JSON.parse(response);
totalTerms += _.size(response);
retObj.translations[ns] = flat.unflatten(response);
next();
}
});
}
function finish (err) {
if (err) {
return cb(new MwareError(err, name));
} else {
retObj.totalTerms = totalTerms;
return cb(null, retObj);
}
}
async.forEach(
namespaces
, nsIterrator
, finish
);
}
function updateResources (resources, cb) {
var authObj = null
, totalTerms = 0
, partialUrl = '/projects/' + options.platformId + '/files';
function resIterrator (resource, next) {
if (options.ignoredNamespaces.indexOf(resource.namespace) == -1) {
var locale = resource.lng
, ns = resource.namespace
, flatNsResources = flat.flatten(resource.resources)
, rand = Math.floor(Math.random() * 1000000000)
, environment = process.env.NODE_ENV
, tmpFilePath = ((environment == 'development') ? path.dirname(require.main.filename) + '/tmp' : os.tmpdir()) + '/' + rand
, filePath = tmpFilePath + '/' + ns + '.json';
fs.mkdir(tmpFilePath, 0777, true, function (err) {
if (err) {
return next(err);
} else {
fs.writeFile(filePath, JSON.stringify(flatNsResources, null, 2), { mode: 777 }, function (err) {
if (err) {
return next(err);
} else {
authObj = buildAuthObj();
var r = request.post(baseUrl + partialUrl, function (err, incomingMsg, response) {
if (err) {
return next(err);
} else {
rmdir(tmpFilePath, function (err) {
if (err) {
console.log(('WARNING: Resources temp file ' + filePath + ' could not be deleted.').magenta);
}
});
response = JSON.parse(response);
if (!response.data) {
return next(response.meta.message);
} else {
totalTerms += _.size(flatNsResources);
next();
}
}
});
var form = r.form();
form.append('api_key', authObj.api_key);
form.append('timestamp', authObj.timestamp + '');
form.append('dev_hash', authObj.dev_hash);
form.append('file_format', 'HIERARCHICAL_JSON');
form.append('locale', locale);
form.append('file', fs.createReadStream(filePath));
form.append('is_keeping_all_strings', 'false');
}
});
}
});
} else {
next();
}
}
function finish (err) {
if (err) {
return cb(new MwareError(err, name));
} else {
cb(null, { totalTerms: totalTerms });
}
}
async.forEach(
resources
, resIterrator
, finish
);
}
return {
version: version
, type: type
, name: name
, setOptions: setOptions
, init: init
, options: options
, getLocalesSummary: getLocalesSummary
, getTranslations: getTranslations
, updateResources: updateResources
}
}
module.exports = i18nucleus_onesky;