Unfortunately, so far Opera does not support the localization of widgets by the method proposed in
the W3C standard , but even if it does support, then this only applies to the server side, and, apparently, only the server language. Therefore, we will do everything ourselves, given that the languages of the browser server and the browser client are generally different.
Receiving from the server the language of the information sent to the client
How to determine the client language on the server? -
HTTP Accept-Language header . How to get to him? - via the getRequestHeader method or the headers property of the
WebServerRequest object type. And then process it according to the algorithm described in the RFC? - Yes. To do this, I wrote a function that accepts WebServerRequest and a list of supported localizations, and gives the client a preferred localization:
function getLanguageNameForRequest (Request, SelectedArray) {
var HeaderCollection = Request.getRequestHeader ("Accept-Language");
var AcceptString = "";
if (HeaderCollection! = null) if (HeaderCollection.length> = 1) {
// HeaderCollection is a DOMStringList and does not have a join method, so pornography
for (var i = 0, AcceptString = HeaderCollection.item (0); i <HeaderCollection.length-1;) {
i ++;
AcceptString + = "," + HeaderCollection.item (i);
}
}
var AcceptArray = AcceptString.replace ("", ""). split (",");
// See RFC2616, # 14.4 Accept-Language
//http://tools.ietf.org/html/rfc2616#section-14.4
var Lang = SelectedArray [0], Qu = -Infinity;
for (var i in AcceptArray) {
var l, q, lq;
lq = AcceptArray [i] .split (";");
l = lq [0]; q = 1;
try {
if (lq [1] .substring (0,2) === "q =") {
q = parseFloat (lq [1] .substring (2));
}
} catch (err) {
q = 1;
}
if (SelectedArray.indexOf (l)> = 0) {
if (q> Qu) {
Lang = l;
Qu = q;
}
}
}
return lang;
}
Call example
For example, if the client sent the string “ru, ru-RU; q = 0.9, en; q = 0.8, de; q = 0.7” in the Accept-Language header, and the languages ru and en are supported on the server, then getLanguageNameForRequest will return “ru”:
window.onload = function () {opera.io.webserver.addEventListener ('_ index', function (RequestEvent) {
RequestEvent.connection.response.writeLine ("Client language:" + getLanguageNameForRequest (RequestEvent.connection.request, ["ru", "en"]));
RequestEvent.connection.response.close ();
}, false);}
Why not use UserAgent instead? Because it conveys the language of the browser interface, not the pages.
Receiving from the server side the language of information output to the server
The feature of Opera Unite technology is that the server-side script interacts not only with people who receive HTML clients through browsers, but also with the person who sits behind the server browser directly through various APIs, such as sending messages through
widget.showNotification . Fortunately, the same DOM is available for the server code as for the normal page, that is, window.navigator.language works and gives the interface language of the browser-server. Wrap in a function similar to the previous case that selects a language from the available:
function getLanguageNameForServer (SelectedArray) {
var l = window.navigator.language
return (SelectedArray.indexOf (l)> = 0)? l: SelectedArray [0];
}
widget.showNotification ("Server language:" + getLanguageNameForServer (["en", "ru", "de"]));
Creating infrastructure for localization of the application as a whole
Since one of the most important advantages of Opera Unite is the ability to use the same JavaScript code simultaneously in the server and client parts of the application, I would like to not lose this property when creating an API for localization, that is, the language of the returned strings should be implicitly determined by the place executing the code that asks for them. This will be the second part of the post, if I write it.