-
-
Save germanviscuso/fd5a9f132e4f4faf5e12360634a5af9e to your computer and use it in GitHub Desktop.
Optimized i18n request interceptor for Alexa custom skills in Node. Loads only required language assets from external files and provides some convenient functions to read them. Will also let you store localized settings represented as JSON objects in your language files.
This file contains 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
module.exports = Object.freeze({ | |
translation: { | |
welcome: 'Howdy', | |
images: [ | |
{ | |
background: 'https://image/en-US.png' | |
}, | |
{ | |
background: 'https://image/en-US2.png' | |
}, | |
{ | |
background: 'https://image/en-US3.png' | |
} | |
] | |
} | |
}); |
This file contains 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
module.exports = Object.freeze({ | |
translation: { | |
welcome: 'Hello', | |
greet: 'Hello %s', | |
random: { | |
welcome: [ 'Hello', 'Hi' ], | |
greet: [ 'Hello %s', 'Hi %s' ], | |
} | |
} | |
}); |
This file contains 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
const Alexa = require('ask-sdk-core'); | |
const LaunchRequestHandler = { | |
canHandle(handlerInput) { | |
return handlerInput.requestEnvelope.request.type === 'LaunchRequest'; | |
}, | |
handle(handlerInput) { | |
console.log(handlerInput.t('welcome')); | |
console.log(handlerInput.t2('welcome')); | |
console.log(handlerInput.t('random.welcome')); | |
console.log(handlerInput.t2('random.welcome')[1]); | |
console.log(handlerInput.t('greet', 'Michael')); | |
console.log(handlerInput.t2('greet', 'Michael')); | |
console.log(handlerInput.t('random.greet', 'Michael')); | |
console.log(handlerInput.t2('random.greet', 'Michael')[1]); | |
console.log(handlerInput.o('images').background); | |
console.log(handlerInput.o2('images')[1].background); | |
return handlerInput.responseBuilder.speak('Test').getResponse(); | |
}, | |
}; | |
const skillBuilder = Alexa.SkillBuilders.custom(); | |
exports.handler = skillBuilder | |
.addRequestHandlers(LaunchRequestHandler) | |
.addRequestInterceptors(require("./intercept_i18n")) | |
.lambda(); |
This file contains 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
const i18n = require('i18next'); | |
const sprintf = require('i18next-sprintf-postprocessor'); | |
const merge_json = require("merge-json"); | |
/* | |
1) SETUP: | |
required are language file (e.g. en.js or de.js) and locale file (e.g. en-US.js) both in format of: | |
/* | |
module.exports = Object.freeze({ | |
translation: { | |
sayhello: [ 'hello', 'hi' ], | |
greet: 'Welcome %s', | |
saybye: 'Good bye', | |
images: { | |
logo: 'https://localized/images/us.png' | |
}, | |
nice_places: [ | |
{ | |
name: 'Golden Gate Bridge', | |
city: 'San Francisco' | |
}, ... | |
], | |
... | |
} | |
}); | |
2) INTEGRATE: | |
Alexa.SkillBuilders.custom().addRequestInterceptors(require("./path/to/this/file.js")); | |
3) USE: | |
handlerInput.t('welcome'); | |
handlerInput.t('greet', 'Scott'); | |
handlerInput.o('images').logo; | |
handlerInput.o2('nice_places')[0].name; | |
*/ | |
module.exports = Object.freeze({ | |
process(handlerInput) { | |
const locale = handlerInput.requestEnvelope.request.locale; | |
const localizationClient = i18n.use(sprintf).init({ | |
resources: { | |
/* merge language and locale file where locale file is dominant and overwrites generic language assets. | |
e.g. you can set generic English welcome string 'hello' and specifc en-US welcome 'Howdy'. 'Howdy' will be taken */ | |
[locale]: merge_json.merge( | |
require(`./strings/${locale.split("-")[0]}.js`), // e.g. en.js | |
require(`./strings/${locale}.js`) // e.g. en-US.js | |
)}, lng: locale }); | |
localizationClient.localize = function(format, randomize, ...args) { | |
const settings = Object.assign({ returnObjects: true }, format ? { postProcess: 'sprintf', sprintf: args.slice(1) } : {}); | |
const value = i18n.t(args[0], settings); | |
return randomize && Array.isArray(value) ? value[Math.floor(Math.random() * value.length)] : value; | |
}; | |
handlerInput.t = handlerInput.attributesManager.getRequestAttributes().t = function(...args) { | |
return localizationClient.localize(true, true, ...args); | |
}; | |
// t2 skips returning randomized string from an array of strings for a given asset. instead returns array as is | |
handlerInput.t2 = handlerInput.attributesManager.getRequestAttributes().t2 = function(...args) { | |
return localizationClient.localize(true, false, ...args); | |
}; | |
// o skips string post processing and returns plain JSON object (useful if you store localized settings in your language files) | |
// will still pick random item if requested asset is an array | |
handlerInput.o = handlerInput.attributesManager.getRequestAttributes().o = function(...args) { | |
return localizationClient.localize(false, true, ...args); | |
}; | |
// o2 skips string post processing and returns JSON object (useful if you store localized settings in your language files) | |
// also skips picking random item if requested asset is an array | |
handlerInput.o2 = handlerInput.attributesManager.getRequestAttributes().o2 = function(...args) { | |
return localizationClient.localize(false, false, ...args); | |
}; | |
} | |
}); |
This file contains 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
{ | |
"name": "i18n-interceptor-sample", | |
"version": "1.0.0", | |
"description": "", | |
"main": "index.js", | |
"scripts": { | |
"test": "echo \"Error: no test specified\" && exit 1" | |
}, | |
"author": "Kay Lerch", | |
"license": "ISC", | |
"dependencies": { | |
"ask-sdk-core": "^2.0.0", | |
"ask-sdk-model": "^1.0.0", | |
"i18next": "^11.8.0", | |
"i18next-sprintf-postprocessor": "^0.2.2", | |
"merge-json": "0.1.0-b.3" | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment