在没有服务器的情况下从 HTML 头读取 JSON 文件
Read JSON File from HTML Head without Server
我得到了一些翻译的 json 文件。
我想在 JS 文件中使用这个文件来翻译一些字符串。
但是我没有找到一个好的解决方案来加载这个文件和数据。
到目前为止我得到的是在我的 HTML 文件中:
<script type='application/json' src='lang/translations.json'></script>
<script src="Javascript/translator.js" charset="UTF-8"></script>
JSON 文件:
{
"language": {
"en": {
"closure": "Closure",
"documents": "Documents",
"overview": "Overview"
},
"de": {
"closure": "Abschluss",
"documents": "Dokumente",
"overview": "Übersicht"
}
}
}
还有我的 JS 文件:
let docLanguage = document.documentElement.lang;
let browserLanguage = navigator.language.substr(0, 2);
let lang = docLanguage ? docLanguage : browserLanguage;
let texts;
const Http = new XMLHttpRequest();
const url = "lang/" + lang + ".json";
Http.open("GET", url, false);
Http.send();
Http.onreadystatechange = function () {
texts = JSON.parse(Http.responseText);
return texts;
}
let getJson = jQuery.getJSON('lang/' + lang + '.json', {format: "json", async: false})
.done(function (data) {
// texts = data;
return data;
}).fail(function () {
console.log('empty');
});
class translator {
constructor(lang) {
this.lang = lang;
this.translations = texts;
}
_(keyName) {
// return texts.get(keyName);
// todo get by keyName
}
transHtml(attribute = 'data-lang') {
let htmlElements = document.querySelectorAll('[' + attribute + ']');
for (let htmlElement of htmlElements) {
let keyName = htmlElement.getAttribute(attribute);
htmlElement.textContent = this._(keyName);
}
}
}
var translate = new translator(lang);
但问题是,翻译文件读得太晚了,在构造函数中我无法使用这些部分,还是我做错了什么?
那么加载和读取存储在本地的 json 文件的最佳方式是什么。
我不需要服务器或其他任何东西,只需要可以在所有现代浏览器上 运行 的纯 Javascript。因为这是针对用户的导出,他们应该能够只观看此页面而无需安装任何东西或需要互联网连接
如果你想坚持使用同步 XHTTPRequest(不推荐)那么你只需要改变 send()
函数的顺序,
你在附加 onreadystatechange
事件侦听器之前调用它,它必须在:
之后调用
Http.open("GET", url, false);
Http.onreadystatechange = function () {
texts = JSON.parse(Http.responseText);
return texts;
}
Http.send(); // called after onreadystatechange
它会工作,但在控制台中显示警告 [Deprecation] Synchronous XMLHttpRequest on the main thread is deprecated because of its detrimental effects to the end user's experience.
建议在JavaScript中使用异步函数。
异步构造函数将不起作用,因此有一些模式可以帮助解决这个问题:
例如,最好使用这样的 .init()
函数:
let docLanguage = document.documentElement.lang;
let browserLanguage = navigator.language.substr(0, 2);
let lang = docLanguage ? docLanguage : browserLanguage;
class translator {
constructor(lang) {
this.lang = lang;
}
init(cb) {
jQuery.getJSON('lang/' + this.lang + '.json', { format: "json" })
.done(result => {
this.translations = result;
cb.bind(this)();
})
.fail(err => console.log(err))
}
_(keyName) {
// return texts.get(keyName);
// todo get by keyName
}
transHtml(attribute = 'data-lang') {
let htmlElements = document.querySelectorAll('[' + attribute + ']');
for (let htmlElement of htmlElements) {
let keyName = htmlElement.getAttribute(attribute);
htmlElement.textContent = this._(keyName);
}
}
}
var translate = new translator(lang);
translate.init(() => {
// inside you can use methods that rely on translations being loaded e.g:
translate.transHtml();
})
@回复评论:
例如可以添加另一个文件languages.js
const languages = {
"language": {
"en": {
"closure": "Closure",
"documents": "Documents",
"overview": "Overview"
},
"de": {
"closure": "Abschluss",
"documents": "Dokumente",
"overview": "Übersicht"
}
}
}
export default languages;
然后在你的主脚本中添加 type="module"
这样你就可以导入另一个 js 文件(注意:它主要在现代浏览器中工作,通常它是在 webpack[= 的帮助下完成的40=] 等以帮助旧版浏览器,但这完全是另一个话题)
<script type="module">
import lngs from './languages.js'
let docLanguage = document.documentElement.lang;
...
...
...
rest of script
您也可以简单地将顶部的 languages
对象粘贴到您的主脚本中,然后就不需要导入另一个 js 文件了。
我得到了一些翻译的 json 文件。 我想在 JS 文件中使用这个文件来翻译一些字符串。 但是我没有找到一个好的解决方案来加载这个文件和数据。
到目前为止我得到的是在我的 HTML 文件中:
<script type='application/json' src='lang/translations.json'></script>
<script src="Javascript/translator.js" charset="UTF-8"></script>
JSON 文件:
{
"language": {
"en": {
"closure": "Closure",
"documents": "Documents",
"overview": "Overview"
},
"de": {
"closure": "Abschluss",
"documents": "Dokumente",
"overview": "Übersicht"
}
}
}
还有我的 JS 文件:
let docLanguage = document.documentElement.lang;
let browserLanguage = navigator.language.substr(0, 2);
let lang = docLanguage ? docLanguage : browserLanguage;
let texts;
const Http = new XMLHttpRequest();
const url = "lang/" + lang + ".json";
Http.open("GET", url, false);
Http.send();
Http.onreadystatechange = function () {
texts = JSON.parse(Http.responseText);
return texts;
}
let getJson = jQuery.getJSON('lang/' + lang + '.json', {format: "json", async: false})
.done(function (data) {
// texts = data;
return data;
}).fail(function () {
console.log('empty');
});
class translator {
constructor(lang) {
this.lang = lang;
this.translations = texts;
}
_(keyName) {
// return texts.get(keyName);
// todo get by keyName
}
transHtml(attribute = 'data-lang') {
let htmlElements = document.querySelectorAll('[' + attribute + ']');
for (let htmlElement of htmlElements) {
let keyName = htmlElement.getAttribute(attribute);
htmlElement.textContent = this._(keyName);
}
}
}
var translate = new translator(lang);
但问题是,翻译文件读得太晚了,在构造函数中我无法使用这些部分,还是我做错了什么?
那么加载和读取存储在本地的 json 文件的最佳方式是什么。
我不需要服务器或其他任何东西,只需要可以在所有现代浏览器上 运行 的纯 Javascript。因为这是针对用户的导出,他们应该能够只观看此页面而无需安装任何东西或需要互联网连接
如果你想坚持使用同步 XHTTPRequest(不推荐)那么你只需要改变 send()
函数的顺序,
你在附加 onreadystatechange
事件侦听器之前调用它,它必须在:
Http.open("GET", url, false);
Http.onreadystatechange = function () {
texts = JSON.parse(Http.responseText);
return texts;
}
Http.send(); // called after onreadystatechange
它会工作,但在控制台中显示警告 [Deprecation] Synchronous XMLHttpRequest on the main thread is deprecated because of its detrimental effects to the end user's experience.
建议在JavaScript中使用异步函数。
异步构造函数将不起作用,因此有一些模式可以帮助解决这个问题:
例如,最好使用这样的 .init()
函数:
let docLanguage = document.documentElement.lang;
let browserLanguage = navigator.language.substr(0, 2);
let lang = docLanguage ? docLanguage : browserLanguage;
class translator {
constructor(lang) {
this.lang = lang;
}
init(cb) {
jQuery.getJSON('lang/' + this.lang + '.json', { format: "json" })
.done(result => {
this.translations = result;
cb.bind(this)();
})
.fail(err => console.log(err))
}
_(keyName) {
// return texts.get(keyName);
// todo get by keyName
}
transHtml(attribute = 'data-lang') {
let htmlElements = document.querySelectorAll('[' + attribute + ']');
for (let htmlElement of htmlElements) {
let keyName = htmlElement.getAttribute(attribute);
htmlElement.textContent = this._(keyName);
}
}
}
var translate = new translator(lang);
translate.init(() => {
// inside you can use methods that rely on translations being loaded e.g:
translate.transHtml();
})
@回复评论:
例如可以添加另一个文件languages.js
const languages = {
"language": {
"en": {
"closure": "Closure",
"documents": "Documents",
"overview": "Overview"
},
"de": {
"closure": "Abschluss",
"documents": "Dokumente",
"overview": "Übersicht"
}
}
}
export default languages;
然后在你的主脚本中添加 type="module"
这样你就可以导入另一个 js 文件(注意:它主要在现代浏览器中工作,通常它是在 webpack[= 的帮助下完成的40=] 等以帮助旧版浏览器,但这完全是另一个话题)
<script type="module">
import lngs from './languages.js'
let docLanguage = document.documentElement.lang;
...
...
...
rest of script
您也可以简单地将顶部的 languages
对象粘贴到您的主脚本中,然后就不需要导入另一个 js 文件了。