Reputation: 33
I use a JSON file for common phrases so I don't have to type them and maybe in the future they can be translated. So for example in my main code I want to say You don't have the permission to use ${command_name}
. This works perfectly fine hardcoded into my .js file but ultimately I want this to be in a JSON file, which does not allow any variables to be inserted.
Does anyone know a solution to my problem?
EDIT: Thanks for the suggestions. I guess string.replace would be my best option here. Wish there was some built in feature that'd convert variables in a JSON string to variables declared in that JS file.
Upvotes: 3
Views: 8136
Reputation: 64943
Basically you can implement a function parse
which, given a text and a dictionary, it could replace any ocurrence of each dictionary key:
const parse = (template, textMap) => {
let output = template
for (let [id, text] of Object.entries(textMap)) {
output = output.replace(new RegExp(`\\$\{${id}}`, 'mg'), text)
}
return output
}
const textMap = {
commandName: 'grep',
foo: 'hello',
bar: 'world'
}
const parsed = parse('command "${commandName}" said "${foo} ${bar}"', textMap)
console.log(parsed)
BTW, I would suggest you that you should use some existing string templating engine like string-template to avoid reinventing the wheel.
Upvotes: 0
Reputation: 23763
So the main challenge is getting separated file with string constants when some of them being parametrizable, right?
JSON format itself operates on strings(numbers, booleans, lists and hashmap) and knows nothing about substitution and parameters.
You are also unable to use template strings like you don't have permission to do ${actionName}
since template strings are interpolated immediately.
So what can you do?
Writing your own parser that takes config data from JSON file, parse a string, find a reference to variable and substitute it with value. Simple example:
const varPattern = /\${([^{}]+)}/g; function replaceVarWithValue(templateStr, params) { return templateStr.replace(varPattern, (fullMatch, varName) => params[varName] || fullMatch); }
or you can use any npm package aimed on localization like i18n so it would handle templates for you
Upvotes: 0
Reputation: 144729
You can simply use placeholders. The following function replaces the placeholders with user-defined values:
const messages = {
msgName: 'Foo is :foo: and bar is :bar:!'
}
function _(key, placeholders) {
return messages[key].replace(/:(\w+):/g, function(__, item) {
return placeholders[item] || item;
});
}
Usage:
_('msgName', { foo: 'one', bar: 'two' })
// "Foo is one and bar is two!"
It's just an example. You can change the placeholders style and the function behavior the way you want!
Upvotes: 1
Reputation: 8520
You cannot treat template string literals in JSON files like in Javascript "code". You said it yourself. But: You could use a template engine for this - or just simple String.replace()
.
Example for a template engine: https://github.com/janl/mustache.js
With Mustache (as an example) your code will look like this
var trans = {
command_name: "dump"
};
var output = Mustache.render("You don't have the permission to use {{command_name}}", trans);
With simple String.replace()
:
var str = "You don't have the permission to use %command_name%";
console.log(str.replace('%command_name%', 'dump'));
Upvotes: 3
Reputation: 949
./name.json
{
command: "this is the output of 'command'"
}
./Node.js
cost names = require('./name.json');
console.log('name === ', name.command);
// name === this is the output of 'command'
Upvotes: 0