Fix #64, Non-English month parsing doesn't work in Standalone
Month values from the Firefox language packs are included in a JSON file used by `Zotero.Date.getMonths()`. `getMonths(true)` includes English months as well. The JSON file should be bundled with the connectors as well, and Zotero.Date.init() should be updated to populate the month data from that.
This commit is contained in:
parent
7bdcc17ed0
commit
ef1ff8bc42
4 changed files with 1477 additions and 31 deletions
|
@ -39,39 +39,75 @@ Zotero.Date = new function(){
|
|||
this.getLocaleDateOrder = getLocaleDateOrder;
|
||||
|
||||
var _localeDateOrder = null;
|
||||
var _months = null;
|
||||
var _months;
|
||||
var _monthsWithEnglish;
|
||||
|
||||
/**
|
||||
* Load dateFormat bundle into _dateFormatsBundle
|
||||
*/
|
||||
this.getMonths = function() {
|
||||
if(_months) return _months;
|
||||
|
||||
if(Zotero.isFx && !Zotero.isBookmarklet) {
|
||||
var src = 'chrome://global/locale/dateFormat.properties';
|
||||
var localeService = Components.classes['@mozilla.org/intl/nslocaleservice;1'].
|
||||
getService(Components.interfaces.nsILocaleService);
|
||||
var appLocale = localeService.getApplicationLocale();
|
||||
|
||||
var bundle =
|
||||
Components.classes["@mozilla.org/intl/stringbundle;1"]
|
||||
.getService(Components.interfaces.nsIStringBundleService).createBundle(src, appLocale);
|
||||
|
||||
_months = {"short":[], "long":[]};
|
||||
for(var i=1; i<=12; i++) {
|
||||
_months.short.push(bundle.GetStringFromName("month."+i+".Mmm"));
|
||||
_months.long.push(bundle.GetStringFromName("month."+i+".name"));
|
||||
}
|
||||
} else {
|
||||
// TODO localize for Chrome/Safari
|
||||
_months = {
|
||||
"short":["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep",
|
||||
"Oct", "Nov", "Dec"],
|
||||
"long":["January", "February", "March", "April", "May", "June", "July",
|
||||
"August", "September", "October", "November", "December"]};
|
||||
this.init = Zotero.Promise.coroutine(function* () {
|
||||
if (!Zotero.isFx || Zotero.isBookmarklet) {
|
||||
throw new Error("Unimplemented");
|
||||
}
|
||||
|
||||
return _months;
|
||||
var json = (yield Zotero.HTTP.request(
|
||||
'GET', 'resource://zotero/schema/dateFormats.json', { responseType: 'json' }
|
||||
)).response;
|
||||
var locale = Zotero.locale;
|
||||
var english = locale.startsWith('en');
|
||||
// If no exact match, try first two characters ('de')
|
||||
if (!json[locale]) {
|
||||
locale = locale.substr(0, 2);
|
||||
}
|
||||
// Try first two characters repeated ('de-DE')
|
||||
if (!json[locale]) {
|
||||
locale = locale + "-" + locale.toUpperCase();
|
||||
}
|
||||
// Look for another locale with same first two characters
|
||||
if (!json[locale]) {
|
||||
let sameLang = Object.keys(json).filter(l => l.startsWith(locale.substr(0, 2)));
|
||||
if (sameLang.length) {
|
||||
locale = sameLang[0];
|
||||
}
|
||||
}
|
||||
// If all else fails, use English
|
||||
if (!json[locale]) {
|
||||
locale = 'en-US';
|
||||
english = true;
|
||||
}
|
||||
_months = json[locale];
|
||||
|
||||
// Add English versions if not already added
|
||||
if (english) {
|
||||
_monthsWithEnglish = _months;
|
||||
}
|
||||
else {
|
||||
_monthsWithEnglish = {};
|
||||
for (let key in _months) {
|
||||
_monthsWithEnglish[key] = _months[key].concat(json['en-US'][key]);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
/**
|
||||
* @param {Boolean} [withEnglish = false] - Include English months
|
||||
* @return {Object} - Object with 'short' and 'long' arrays
|
||||
*/
|
||||
this.getMonths = function (withEnglish) {
|
||||
if (withEnglish) {
|
||||
if (_monthsWithEnglish) return _monthsWithEnglish;
|
||||
}
|
||||
else {
|
||||
if (_months) return _months;
|
||||
}
|
||||
|
||||
if (Zotero.isFx && !Zotero.isBookmarklet) {
|
||||
throw new Error("Months not cached");
|
||||
}
|
||||
|
||||
// TODO: Use JSON file for connectors
|
||||
return _months = _monthsWithEnglish = {
|
||||
short: ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"],
|
||||
long: ["January", "February", "March", "April", "May", "June", "July", "August",
|
||||
"September", "October", "November", "December"]};
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -717,7 +717,7 @@ Services.scriptloader.loadSubScript("resource://zotero/polyfill.js");
|
|||
// Initialize keyboard shortcuts
|
||||
Zotero.Keys.init();
|
||||
|
||||
// Initialize Locate Manager
|
||||
yield Zotero.Date.init();
|
||||
Zotero.LocateManager.init();
|
||||
yield Zotero.ID.init();
|
||||
yield Zotero.Collections.init();
|
||||
|
|
1292
resource/schema/dateFormats.json
Normal file
1292
resource/schema/dateFormats.json
Normal file
File diff suppressed because it is too large
Load diff
|
@ -1,4 +1,122 @@
|
|||
describe("Zotero.Date", function() {
|
||||
describe("#getMonths()", function () {
|
||||
var origLocale;
|
||||
var englishShort = [
|
||||
"Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"
|
||||
];
|
||||
var englishLong = [
|
||||
"January", "February", "March", "April", "May", "June", "July", "August", "September",
|
||||
"October", "November", "December"
|
||||
];
|
||||
var frenchShort = [
|
||||
"jan", "fév", "mar", "avr", "mai", "jun", "jul", "aoû", "sep", "oct", "nov", "dec"
|
||||
];
|
||||
var frenchLong = [
|
||||
"janvier", "février", "mars", "avril", "mai", "juin", "juillet", "août", "septembre",
|
||||
"octobre", "novembre", "décembre"
|
||||
];
|
||||
|
||||
before(function () {
|
||||
origLocale = Zotero.locale;
|
||||
});
|
||||
|
||||
after(function () {
|
||||
Zotero.locale = origLocale;
|
||||
});
|
||||
|
||||
describe("English", function () {
|
||||
beforeEach(function* () {
|
||||
if (Zotero.locale != 'en-US') {
|
||||
Zotero.locale = 'en-US';
|
||||
yield Zotero.Date.init();
|
||||
}
|
||||
});
|
||||
|
||||
it("should get English short months", function () {
|
||||
let months = Zotero.Date.getMonths().short;
|
||||
assert.lengthOf(months, 12);
|
||||
assert.sameMembers(months, englishShort);
|
||||
});
|
||||
|
||||
it("should get English long months", function () {
|
||||
let months = Zotero.Date.getMonths().long;
|
||||
assert.lengthOf(months, 12);
|
||||
assert.sameMembers(months, englishLong);
|
||||
});
|
||||
|
||||
it("shouldn't repeat months in 'withEnglish' mode", function () {
|
||||
let months = Zotero.Date.getMonths(true).short;
|
||||
assert.lengthOf(months, 12);
|
||||
assert.sameMembers(months, englishShort);
|
||||
});
|
||||
|
||||
it("should resolve to English from unknown locale", function* () {
|
||||
Zotero.locale = 'zz';
|
||||
yield Zotero.Date.init();
|
||||
let months = Zotero.Date.getMonths().short;
|
||||
assert.lengthOf(months, 12);
|
||||
assert.sameMembers(months, englishShort);
|
||||
});
|
||||
|
||||
it("shouldn't repeat English with unknown locale", function* () {
|
||||
Zotero.locale = 'zz';
|
||||
yield Zotero.Date.init();
|
||||
let months = Zotero.Date.getMonths(true).short;
|
||||
assert.lengthOf(months, 12);
|
||||
assert.sameMembers(months, englishShort);
|
||||
});
|
||||
});
|
||||
|
||||
describe("French", function () {
|
||||
beforeEach(function* () {
|
||||
if (Zotero.locale != 'fr-FR') {
|
||||
Zotero.locale = 'fr-FR';
|
||||
yield Zotero.Date.init();
|
||||
}
|
||||
});
|
||||
|
||||
it("should get French short months", function () {
|
||||
let months = Zotero.Date.getMonths().short;
|
||||
assert.lengthOf(months, 12);
|
||||
assert.sameMembers(months, frenchShort);
|
||||
});
|
||||
|
||||
it("should get French long months", function () {
|
||||
let months = Zotero.Date.getMonths().long;
|
||||
assert.lengthOf(months, 12);
|
||||
assert.sameMembers(months, frenchLong);
|
||||
});
|
||||
|
||||
it("should get French short months with English", function () {
|
||||
let months = Zotero.Date.getMonths(true).short;
|
||||
assert.lengthOf(months, 24);
|
||||
assert.sameMembers(months, frenchShort.concat(englishShort));
|
||||
});
|
||||
|
||||
it("should get French long months with English", function () {
|
||||
let months = Zotero.Date.getMonths(true).long;
|
||||
assert.lengthOf(months, 24);
|
||||
assert.sameMembers(months, frenchLong.concat(englishLong));
|
||||
});
|
||||
|
||||
it("should resolve from two-letter locale", function* () {
|
||||
Zotero.locale = 'fr';
|
||||
yield Zotero.Date.init();
|
||||
let months = Zotero.Date.getMonths().short;
|
||||
assert.lengthOf(months, 12);
|
||||
assert.sameMembers(months, frenchShort);
|
||||
});
|
||||
|
||||
it("should resolve from unknown four-letter locale with common prefix", function* () {
|
||||
Zotero.locale = 'fr-ZZ';
|
||||
yield Zotero.Date.init();
|
||||
let months = Zotero.Date.getMonths().short;
|
||||
assert.lengthOf(months, 12);
|
||||
assert.sameMembers(months, frenchShort);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
describe("#sqlToDate()", function () {
|
||||
it("should convert an SQL local date into a JS Date object", function* () {
|
||||
var d1 = new Date();
|
||||
|
|
Loading…
Add table
Reference in a new issue