Bump i18n-js to v4

This commit is contained in:
Oliver Günther
2023-07-18 21:39:33 +02:00
parent 470f92eb8c
commit bf6e9e037e
19 changed files with 109 additions and 1157 deletions
+1 -1
View File
@@ -64,7 +64,7 @@ npm-debug.log*
# Generated files
/app/assets/javascripts/editor/*
/app/assets/javascripts/locales/*.*
/frontend/src/locales/*.js
/frontend/src/locales/*
/modules/*/frontend/module/module
/config/additional_environment.rb
/config/configuration.yml
+1 -1
View File
@@ -170,7 +170,7 @@ group :production do
gem 'dalli', '~> 3.2.0'
end
gem 'i18n-js', '~> 3.9.0'
gem 'i18n-js', '~> 4.2.3'
gem 'rails-i18n', '~> 7.0.0'
gem 'sprockets', '~> 3.7.2' # lock sprockets below 4.0
+5 -3
View File
@@ -480,6 +480,7 @@ GEM
fuubar (2.5.1)
rspec-core (~> 3.0)
ruby-progressbar (~> 1.4)
glob (0.4.0)
globalid (1.1.0)
activesupport (>= 5.0)
gon (6.4.0)
@@ -530,8 +531,9 @@ GEM
httpclient (2.8.3)
i18n (1.14.1)
concurrent-ruby (~> 1.0)
i18n-js (3.9.2)
i18n (>= 0.6.6)
i18n-js (4.2.3)
glob (>= 0.4.0)
i18n
icalendar (2.8.0)
ice_cube (~> 0.16)
ice_cube (0.16.4)
@@ -1034,7 +1036,7 @@ DEPENDENCIES
grids!
html-pipeline (~> 2.14.0)
htmldiff
i18n-js (~> 3.9.0)
i18n-js (~> 4.2.3)
json_schemer (~> 1.0.1)
json_spec (~> 1.1.4)
ladle
-3
View File
@@ -34,9 +34,6 @@ OpenProject::Application.configure do
# since you don't have to restart the web server when you make code changes.
config.cache_classes = false
# Automatically refresh translations with I18n middleware
config.middleware.use ::I18n::JS::Middleware
# Do not eager load code on boot by default.
config.eager_load = ENV['EAGER_LOAD'].present?
-4
View File
@@ -1,4 +0,0 @@
fallbacks: :en
translations:
- file: "frontend/src/locales/%{locale}.js"
only: ['*.js', '*.number.*', '*.time.*', '*.date.*']
+11
View File
@@ -0,0 +1,11 @@
# This file controls ONLY the translation
# for the frontend (i18n-js)
embed_fallback_translations:
enabled: true
translations:
- file: "frontend/src/locales/:locale.json"
patterns:
- '*.js'
- '*.number.*'
- '*.time.*'
- '*.date.*'
+7
View File
@@ -0,0 +1,7 @@
# Auto-build js translations in dev mode
Rails.application.config.after_initialize do
if Rails.env.development?
require "i18n-js/listen"
I18nJS.listen
end
end
+42
View File
@@ -65,6 +65,7 @@
"fuse.js": "^3.4.5",
"glob": "^7.1.4",
"hammerjs": "^2.0.8",
"i18n-js": "^4.3.0",
"jquery": "^3.5.1",
"jquery-ui": "1.13.2",
"jquery-ujs": "^1.2.2",
@@ -19969,6 +19970,14 @@
"node": "*"
}
},
"node_modules/bignumber.js": {
"version": "9.1.1",
"resolved": "https://registry.npmjs.org/bignumber.js/-/bignumber.js-9.1.1.tgz",
"integrity": "sha512-pHm4LsMJ6lzgNGVfZHjMoO8sdoRhOzOH4MLmY65Jg70bpxCKu5iOHNJyfF6OyvYw7t8Fpf35RuzUyqnQsj8Vig==",
"engines": {
"node": "*"
}
},
"node_modules/binary-extensions": {
"version": "2.2.0",
"license": "MIT",
@@ -26876,6 +26885,15 @@
"ms": "^2.0.0"
}
},
"node_modules/i18n-js": {
"version": "4.3.0",
"resolved": "https://registry.npmjs.org/i18n-js/-/i18n-js-4.3.0.tgz",
"integrity": "sha512-PX93eT6WPV6Ym6mHtFKGDRZB0zwDX7HUPkgprjsZ28J6/Ohw1nvRYuM93or3pWv2VLxs6XfBf7X9Fc/YAZNEtQ==",
"dependencies": {
"bignumber.js": "*",
"make-plural": "*"
}
},
"node_modules/i18next": {
"version": "22.5.1",
"resolved": "https://registry.npmjs.org/i18next/-/i18next-22.5.1.tgz",
@@ -29496,6 +29514,11 @@
"node": ">=8"
}
},
"node_modules/make-plural": {
"version": "7.3.0",
"resolved": "https://registry.npmjs.org/make-plural/-/make-plural-7.3.0.tgz",
"integrity": "sha512-/K3BC0KIsO+WK2i94LkMPv3wslMrazrQhfi5We9fMbLlLjzoOSJWr7TAdupLlDWaJcWxwoNosBkhFDejiu5VDw=="
},
"node_modules/makeerror": {
"version": "1.0.12",
"dev": true,
@@ -52691,6 +52714,11 @@
"version": "5.2.2",
"dev": true
},
"bignumber.js": {
"version": "9.1.1",
"resolved": "https://registry.npmjs.org/bignumber.js/-/bignumber.js-9.1.1.tgz",
"integrity": "sha512-pHm4LsMJ6lzgNGVfZHjMoO8sdoRhOzOH4MLmY65Jg70bpxCKu5iOHNJyfF6OyvYw7t8Fpf35RuzUyqnQsj8Vig=="
},
"binary-extensions": {
"version": "2.2.0"
},
@@ -57417,6 +57445,15 @@
"ms": "^2.0.0"
}
},
"i18n-js": {
"version": "4.3.0",
"resolved": "https://registry.npmjs.org/i18n-js/-/i18n-js-4.3.0.tgz",
"integrity": "sha512-PX93eT6WPV6Ym6mHtFKGDRZB0zwDX7HUPkgprjsZ28J6/Ohw1nvRYuM93or3pWv2VLxs6XfBf7X9Fc/YAZNEtQ==",
"requires": {
"bignumber.js": "*",
"make-plural": "*"
}
},
"i18next": {
"version": "22.5.1",
"resolved": "https://registry.npmjs.org/i18next/-/i18next-22.5.1.tgz",
@@ -59130,6 +59167,11 @@
}
}
},
"make-plural": {
"version": "7.3.0",
"resolved": "https://registry.npmjs.org/make-plural/-/make-plural-7.3.0.tgz",
"integrity": "sha512-/K3BC0KIsO+WK2i94LkMPv3wslMrazrQhfi5We9fMbLlLjzoOSJWr7TAdupLlDWaJcWxwoNosBkhFDejiu5VDw=="
},
"makeerror": {
"version": "1.0.12",
"dev": true,
+1
View File
@@ -137,6 +137,7 @@
"fuse.js": "^3.4.5",
"glob": "^7.1.4",
"hammerjs": "^2.0.8",
"i18n-js": "^4.3.0",
"jquery": "^3.5.1",
"jquery-ui": "1.13.2",
"jquery-ujs": "^1.2.2",
+10 -58
View File
@@ -1,70 +1,22 @@
import { Injectable } from '@angular/core';
/**
* General components
*/
export interface GlobalI18n {
t<T=string>(translateId:string, parameters?:unknown):T;
lookup(translateId:string):boolean|undefined;
toNumber(num:number, options?:ToNumberOptions):string;
toPercentage(num:number, options?:ToPercentageOptions):string;
toCurrency(num:number, options?:ToCurrencyOptions):string;
strftime(date:Date, format:string):string;
toHumanSize(num:number, options?:ToHumanSizeOptions):string;
toTime(format:string, date:Date):string;
locale:string;
firstDayOfWeek:number;
pluralization:any;
}
interface ToNumberOptions {
precision?:number;
separator?:string;
delimiter?:string;
strip_insignificant_zeros?:boolean;
}
type ToPercentageOptions = ToNumberOptions;
interface ToCurrencyOptions extends ToNumberOptions {
format?:string;
unit?:string;
sign_first?:boolean;
}
interface ToHumanSizeOptions extends ToNumberOptions {
format?:string;
}
import { I18n } from 'i18n-js';
import { FormatNumberOptions, TranslateOptions } from 'i18n-js/src/typing';
@Injectable({ providedIn: 'root' })
export class I18nService {
private i18n:GlobalI18n = window.I18n;
private i18n:I18n = window.I18n;
public get locale():string {
return this.i18n.locale;
}
public t = this.i18n.t.bind(this.i18n) as GlobalI18n['t'];
public t<T = string>(input:string, options:Partial<TranslateOptions> = {}) {
return this.i18n.t<T>(input, options);
}
public lookup = this.i18n.lookup.bind(this.i18n) as GlobalI18n['lookup'];
public toTime = this.i18n.toTime.bind(this.i18n);
public toTime = this.i18n.toTime.bind(this.i18n) as GlobalI18n['toTime'];
public toNumber = this.i18n.toNumber.bind(this.i18n) as GlobalI18n['toNumber'];
public toPercentage = this.i18n.toPercentage.bind(this.i18n) as GlobalI18n['toPercentage'];
public toCurrency = this.i18n.toCurrency.bind(this.i18n) as GlobalI18n['toCurrency'];
public strftime = this.i18n.strftime.bind(this.i18n) as GlobalI18n['strftime'];
public toHumanSize = this.i18n.toHumanSize.bind(this.i18n) as GlobalI18n['toHumanSize'];
public toNumber(val:string|number, options:Partial<FormatNumberOptions>):string {
return this.i18n.localize('number', val, options);
}
}
+19 -12
View File
@@ -27,6 +27,7 @@
//++
import * as moment from 'moment';
import * as i18njs from 'i18n-js';
export function initializeLocale() {
const meta = document.querySelector('meta[name=openproject_initializer]') as HTMLMetaElement;
@@ -34,10 +35,10 @@ export function initializeLocale() {
const firstDayOfWeek = parseInt(meta.dataset.firstdayofweek || '', 10); // properties of meta.dataset are exposed in lowercase
const firstWeekOfYear = parseInt(meta.dataset.firstweekofyear || '', 10); // properties of meta.dataset are exposed in lowercase
window.I18n = new i18njs.I18n();
I18n.locale = locale;
if (!Number.isNaN(firstDayOfWeek) && !Number.isNaN(firstWeekOfYear)) {
I18n.firstDayOfWeek = firstDayOfWeek;
moment.updateLocale(locale, {
week: {
dow: firstDayOfWeek,
@@ -49,16 +50,22 @@ export function initializeLocale() {
// Override the default pluralization function to allow
// "other" to be used as a fallback for "one" in languages where one is not set
// (japanese, for example)
I18n.pluralization.default = function (count:number) {
switch (count) {
case 0:
return ['zero', 'other'];
case 1:
return ['one', 'other'];
default:
return ['other'];
}
};
I18n.pluralization.register(
'default',
(_i18n:i18njs.I18n, count:number) => {
switch (count) {
case 0:
return ['zero', 'other'];
case 1:
return ['one', 'other'];
default:
return ['other'];
}
},
);
return import(/* webpackChunkName: "locale" */ `../../../locales/${I18n.locale}.js`);
return import(/* webpackChunkName: "locale" */ `../../../locales/${I18n.locale}.json`)
.then((imported:{ default:object }) => {
I18n.store(imported.default);
});
}
@@ -66,7 +66,5 @@ require('moment-timezone/builds/moment-timezone-with-data.min.js');
require('expose-loader?URI!urijs');
require('urijs/src/URITemplate');
require('expose-loader?I18n!core-vendor/i18n');
// Localization for fullcalendar
require('@fullcalendar/core/locales-all');
@@ -369,7 +369,7 @@ export class TimeEntryCalendarComponent {
rendering: 'background' as const,
startEditable: false,
// eslint-disable-next-line @typescript-eslint/no-unsafe-assignment
sum: this.i18n.t('js.units.hour', { count: this.formatNumber(duration) }),
sum: this.i18n.t('js.units.hour', { count: duration }),
};
}
@@ -186,7 +186,7 @@ export class HalResourceNotificationService {
const attributeType = schema.type.toLowerCase();
const i18nString = `js.hal.error.format.${attributeType}`;
if (this.I18n.lookup(i18nString) === undefined) {
if (this.I18n.t(i18nString, { default: '[not found]' }) === '[not found]') {
return false;
}
@@ -74,7 +74,7 @@ export class OpAttachmentListItemComponent extends UntilDestroyedMixin implement
dragHint: this.I18n.t('js.attachments.draggable_hint'),
deleteTitle: this.I18n.t('js.attachments.delete'),
deleteConfirmation: this.I18n.t('js.attachments.delete_confirmation'),
removeFile: (arg:unknown):string => this.I18n.t('js.label_remove_file', arg),
removeFile: (arg:object):string => this.I18n.t('js.label_remove_file', arg),
};
public get deleteIconTitle():string {
+3 -2
View File
@@ -22,6 +22,7 @@ import { GlobalI18n } from 'core-app/core/i18n/i18n.service';
import { Dragula } from 'dragula';
import { Screenfull } from 'screenfull';
import { ErrorReporterBase } from 'core-app/core/errors/error-reporter-base';
import { I18n } from 'i18n-js';
declare module 'observable-array';
declare module 'dom-autoscroller';
@@ -29,13 +30,13 @@ declare module 'core-vendor/enjoyhint';
declare global {
const _:typeof TLodash;
const I18n:GlobalI18n;
const I18n:I18n;
const dragula:Dragula;
}
declare global {
interface Window {
I18n:GlobalI18n;
I18n:I18n;
appBasePath:string;
ng2Injector:Injector;
OpenProject:OpenProject;
-1067
View File
File diff suppressed because it is too large Load Diff
+1
View File
@@ -17,6 +17,7 @@
"noFallthroughCasesInSwitch": true,
"strictNullChecks": true,
"strictBindCallApply": true,
"allowSyntheticDefaultImports": true,
"skipLibCheck": true,
"baseUrl": "./src/",
"typeRoots": [
+5 -1
View File
@@ -78,5 +78,9 @@ namespace :assets do
end
desc 'Export frontend locale files'
task export_locales: ['i18n:js:export']
task :export_locales do
sh('bundle exec i18n export') do |ok, res|
raise "Failed to export i18n-js translations: #{res.exitstatus}" if !ok
end
end
end