mirror of
https://github.com/pgadmin-org/pgadmin4.git
synced 2025-02-25 18:55:31 -06:00
Add a mechanism for centralising JS translations, to avoid having to render many JS files with Jinja.
This commit is contained in:
parent
2f84156dc6
commit
4445f9dd63
3
test/javascript/fake_translations.js
Normal file
3
test/javascript/fake_translations.js
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
define(function () {
|
||||||
|
return {}
|
||||||
|
});
|
43
test/javascript/translate_spec.js
Normal file
43
test/javascript/translate_spec.js
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
define(["sources/translate", "translations"], function (translate, translations) {
|
||||||
|
describe("translate", function () {
|
||||||
|
describe("when there is no translation", function () {
|
||||||
|
it("returns the original string", function () {
|
||||||
|
expect(translate("something to be translated")).toEqual("something to be translated");
|
||||||
|
});
|
||||||
|
|
||||||
|
describe("when there are substitutions", function () {
|
||||||
|
it("interpolates a substitution", function () {
|
||||||
|
expect(translate("translate text for %(person)s", {"person": "Sarah"})).toEqual("translate text for Sarah")
|
||||||
|
});
|
||||||
|
|
||||||
|
it("interpolates multiple substitutions", function () {
|
||||||
|
expect(translate("translate '%(text)s' for %(person)s",
|
||||||
|
{
|
||||||
|
"text": "constitution",
|
||||||
|
"person": "Sarah"
|
||||||
|
}
|
||||||
|
)).toEqual("translate 'constitution' for Sarah")
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
});
|
||||||
|
|
||||||
|
describe("when there is a translation", function () {
|
||||||
|
beforeEach(function () {
|
||||||
|
translations['something to be translated'] = 'etwas zum uebersetzen';
|
||||||
|
translations['another translation for %(person)s'] = 'eine weitere Uebersetzung fuer %(person)s';
|
||||||
|
});
|
||||||
|
|
||||||
|
it("returns the translation", function () {
|
||||||
|
expect(translate("something to be translated")).toEqual("etwas zum uebersetzen");
|
||||||
|
});
|
||||||
|
|
||||||
|
describe("when there is a substitution", function () {
|
||||||
|
it("interpolates the substitution", function () {
|
||||||
|
expect(translate("another translation for %(person)s", {"person": "Sarah"}))
|
||||||
|
.toEqual("eine weitere Uebersetzung fuer Sarah");
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
32
web/pgadmin/static/js/translate.js
Normal file
32
web/pgadmin/static/js/translate.js
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
define(["translations"], function (translations) {
|
||||||
|
|
||||||
|
/***
|
||||||
|
* This method behaves as a drop-in replacement for flask translation rendering.
|
||||||
|
* It uses the same translation file under the hood and uses flask to determine the language.
|
||||||
|
*
|
||||||
|
* ex. translate("some %(adjective)s text", {adjective: "cool"})
|
||||||
|
*
|
||||||
|
* @param {String} text
|
||||||
|
* @param {Object} substitutions
|
||||||
|
*/
|
||||||
|
return function translate(text, substitutions) {
|
||||||
|
|
||||||
|
var rawTranslation = translations[text] ? translations[text] : text;
|
||||||
|
|
||||||
|
// captures things of the form %(substitutionName)s
|
||||||
|
var substitutionGroupsRegExp = /([^%]*)%\(([^\)]+)\)s(.*)/;
|
||||||
|
var matchFound;
|
||||||
|
|
||||||
|
var interpolated = rawTranslation;
|
||||||
|
do {
|
||||||
|
matchFound = false;
|
||||||
|
interpolated = interpolated.replace(substitutionGroupsRegExp, function (_, textBeginning, substitutionName, textEnd) {
|
||||||
|
matchFound = true;
|
||||||
|
return textBeginning + substitutions[substitutionName] + textEnd;
|
||||||
|
});
|
||||||
|
} while (matchFound);
|
||||||
|
|
||||||
|
return interpolated;
|
||||||
|
};
|
||||||
|
|
||||||
|
});
|
@ -9,7 +9,11 @@
|
|||||||
|
|
||||||
"""A blueprint module container for keeping all submodule of type tool."""
|
"""A blueprint module container for keeping all submodule of type tool."""
|
||||||
|
|
||||||
|
from flask import render_template, Response
|
||||||
|
from flask import url_for
|
||||||
|
from flask.ext.babel import get_translations
|
||||||
from flask_babel import gettext
|
from flask_babel import gettext
|
||||||
|
|
||||||
from pgadmin.utils import PgAdminModule
|
from pgadmin.utils import PgAdminModule
|
||||||
from pgadmin.utils.ajax import bad_request
|
from pgadmin.utils.ajax import bad_request
|
||||||
|
|
||||||
@ -17,8 +21,11 @@ MODULE_NAME = 'tools'
|
|||||||
|
|
||||||
class ToolsModule(PgAdminModule):
|
class ToolsModule(PgAdminModule):
|
||||||
def get_own_javascripts(self):
|
def get_own_javascripts(self):
|
||||||
from flask import url_for
|
|
||||||
return [{
|
return [{
|
||||||
|
'name': 'translations',
|
||||||
|
'path': url_for('tools.index') + "translations",
|
||||||
|
'when': None
|
||||||
|
},{
|
||||||
'name': 'pgadmin-sqlfoldcode',
|
'name': 'pgadmin-sqlfoldcode',
|
||||||
'path': url_for(
|
'path': url_for(
|
||||||
'static',
|
'static',
|
||||||
@ -49,3 +56,13 @@ blueprint = ToolsModule(MODULE_NAME, __name__)
|
|||||||
def index():
|
def index():
|
||||||
"""Calling tools index URL directly is not allowed."""
|
"""Calling tools index URL directly is not allowed."""
|
||||||
return bad_request(gettext('This URL cannot be requested directly.'))
|
return bad_request(gettext('This URL cannot be requested directly.'))
|
||||||
|
|
||||||
|
@blueprint.route("/translations.js")
|
||||||
|
def translations():
|
||||||
|
"""Return a js file that will handle translations so Flask interpolation can be isolated"""
|
||||||
|
template = render_template("js/translations.js", translations=get_translations()._catalog)
|
||||||
|
return Response(
|
||||||
|
response=template,
|
||||||
|
status=200,
|
||||||
|
mimetype="application/javascript"
|
||||||
|
)
|
4
web/pgadmin/tools/templates/js/translations.js
Normal file
4
web/pgadmin/tools/templates/js/translations.js
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
define(function () {
|
||||||
|
var translations = {{ translations|tojson }};
|
||||||
|
return translations;
|
||||||
|
});
|
Loading…
Reference in New Issue
Block a user