@flusys/nestjs-localization 7.1.0 → 8.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/config/index.d.ts +3 -3
- package/controllers/index.d.ts +3 -3
- package/controllers/language.controller.d.ts +4 -4
- package/controllers/translation-key.controller.d.ts +3 -3
- package/controllers/translation.controller.d.ts +4 -4
- package/docs/index.d.ts +1 -1
- package/docs/localization-swagger.config.d.ts +1 -1
- package/dtos/index.d.ts +3 -3
- package/dtos/translation.dto.d.ts +2 -2
- package/entities/index.d.ts +6 -6
- package/entities/language.entity.d.ts +1 -1
- package/entities/translation-key.entity.d.ts +1 -1
- package/entities/translation.entity.d.ts +2 -2
- package/fesm/349.js +1179 -0
- package/fesm/692.js +1205 -0
- package/fesm/config/index.js +101 -3
- package/fesm/controllers/index.js +15 -3
- package/fesm/docs/index.js +126 -1
- package/fesm/dtos/index.js +680 -3
- package/fesm/entities/index.js +405 -8
- package/fesm/index.js +257 -7
- package/fesm/interfaces/index.js +18 -4
- package/fesm/modules/index.js +152 -1
- package/fesm/runtime.js +85 -0
- package/fesm/services/index.js +15 -5
- package/index.d.ts +7 -7
- package/interfaces/index.d.ts +4 -4
- package/interfaces/language.interface.d.ts +1 -1
- package/interfaces/localization-module-options.interface.d.ts +3 -3
- package/interfaces/translation-key.interface.d.ts +1 -1
- package/interfaces/translation.interface.d.ts +3 -3
- package/modules/index.d.ts +1 -1
- package/modules/localization.module.d.ts +2 -2
- package/package.json +25 -34
- package/services/index.d.ts +5 -5
- package/services/language.service.d.ts +6 -6
- package/services/localization-config.service.d.ts +3 -3
- package/services/localization-datasource.provider.d.ts +3 -3
- package/services/translation-key.service.d.ts +6 -6
- package/services/translation.service.d.ts +5 -5
- package/cjs/config/event-actions.js +0 -33
- package/cjs/config/index.js +0 -20
- package/cjs/config/localization.constants.js +0 -11
- package/cjs/config/message-keys.js +0 -41
- package/cjs/controllers/index.js +0 -20
- package/cjs/controllers/language.controller.js +0 -188
- package/cjs/controllers/language.controller.spec.js +0 -154
- package/cjs/controllers/translation-key.controller.js +0 -135
- package/cjs/controllers/translation-key.controller.spec.js +0 -70
- package/cjs/controllers/translation.controller.js +0 -195
- package/cjs/controllers/translation.controller.spec.js +0 -169
- package/cjs/docs/index.js +0 -11
- package/cjs/docs/localization-swagger.config.js +0 -111
- package/cjs/docs/localization-swagger.config.spec.js +0 -30
- package/cjs/dtos/index.js +0 -20
- package/cjs/dtos/language.dto.js +0 -213
- package/cjs/dtos/translation-key.dto.js +0 -215
- package/cjs/dtos/translation.dto.js +0 -269
- package/cjs/entities/index.js +0 -42
- package/cjs/entities/index.spec.js +0 -18
- package/cjs/entities/language.entity.js +0 -126
- package/cjs/entities/translation-key.entity.js +0 -126
- package/cjs/entities/translation.entity.js +0 -120
- package/cjs/index.js +0 -24
- package/cjs/interfaces/index.js +0 -21
- package/cjs/interfaces/language.interface.js +0 -4
- package/cjs/interfaces/localization-module-options.interface.js +0 -4
- package/cjs/interfaces/translation-key.interface.js +0 -4
- package/cjs/interfaces/translation.interface.js +0 -4
- package/cjs/modules/index.js +0 -18
- package/cjs/modules/localization.module.js +0 -116
- package/cjs/modules/localization.module.spec.js +0 -132
- package/cjs/services/index.js +0 -22
- package/cjs/services/language.service.js +0 -181
- package/cjs/services/language.service.spec.js +0 -256
- package/cjs/services/localization-config.service.js +0 -66
- package/cjs/services/localization-config.service.spec.js +0 -80
- package/cjs/services/localization-datasource.provider.js +0 -79
- package/cjs/services/localization-datasource.provider.spec.js +0 -85
- package/cjs/services/translation-key.service.js +0 -179
- package/cjs/services/translation-key.service.spec.js +0 -303
- package/cjs/services/translation.service.js +0 -228
- package/cjs/services/translation.service.spec.js +0 -530
- package/fesm/config/event-actions.js +0 -12
- package/fesm/config/localization.constants.js +0 -1
- package/fesm/config/message-keys.js +0 -20
- package/fesm/controllers/language.controller.js +0 -178
- package/fesm/controllers/language.controller.spec.js +0 -150
- package/fesm/controllers/translation-key.controller.js +0 -125
- package/fesm/controllers/translation-key.controller.spec.js +0 -66
- package/fesm/controllers/translation.controller.js +0 -185
- package/fesm/controllers/translation.controller.spec.js +0 -165
- package/fesm/docs/localization-swagger.config.js +0 -101
- package/fesm/docs/localization-swagger.config.spec.js +0 -26
- package/fesm/dtos/language.dto.js +0 -192
- package/fesm/dtos/translation-key.dto.js +0 -194
- package/fesm/dtos/translation.dto.js +0 -239
- package/fesm/entities/index.spec.js +0 -14
- package/fesm/entities/language.entity.js +0 -116
- package/fesm/entities/translation-key.entity.js +0 -116
- package/fesm/entities/translation.entity.js +0 -110
- package/fesm/interfaces/language.interface.js +0 -1
- package/fesm/interfaces/localization-module-options.interface.js +0 -1
- package/fesm/interfaces/translation-key.interface.js +0 -1
- package/fesm/interfaces/translation.interface.js +0 -1
- package/fesm/modules/localization.module.js +0 -106
- package/fesm/modules/localization.module.spec.js +0 -128
- package/fesm/services/language.service.js +0 -171
- package/fesm/services/language.service.spec.js +0 -252
- package/fesm/services/localization-config.service.js +0 -56
- package/fesm/services/localization-config.service.spec.js +0 -76
- package/fesm/services/localization-datasource.provider.js +0 -69
- package/fesm/services/localization-datasource.provider.spec.js +0 -81
- package/fesm/services/translation-key.service.js +0 -169
- package/fesm/services/translation-key.service.spec.js +0 -299
- package/fesm/services/translation.service.js +0 -218
- package/fesm/services/translation.service.spec.js +0 -526
|
@@ -1,132 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", {
|
|
3
|
-
value: true
|
|
4
|
-
});
|
|
5
|
-
const _localizationmodule = require("./localization.module");
|
|
6
|
-
const _localizationconstants = require("../config/localization.constants");
|
|
7
|
-
const _controllers = require("../controllers");
|
|
8
|
-
function _define_property(obj, key, value) {
|
|
9
|
-
if (key in obj) {
|
|
10
|
-
Object.defineProperty(obj, key, {
|
|
11
|
-
value: value,
|
|
12
|
-
enumerable: true,
|
|
13
|
-
configurable: true,
|
|
14
|
-
writable: true
|
|
15
|
-
});
|
|
16
|
-
} else {
|
|
17
|
-
obj[key] = value;
|
|
18
|
-
}
|
|
19
|
-
return obj;
|
|
20
|
-
}
|
|
21
|
-
function providerTokens(providers) {
|
|
22
|
-
return providers.map((p)=>typeof p === 'function' ? p : p.provide);
|
|
23
|
-
}
|
|
24
|
-
describe('LocalizationModule', ()=>{
|
|
25
|
-
describe('forRoot', ()=>{
|
|
26
|
-
it('should default to a non-global module with all controllers registered', ()=>{
|
|
27
|
-
const dynamicModule = _localizationmodule.LocalizationModule.forRoot({});
|
|
28
|
-
expect(dynamicModule.module).toBe(_localizationmodule.LocalizationModule);
|
|
29
|
-
expect(dynamicModule.global).toBe(false);
|
|
30
|
-
expect(dynamicModule.controllers).toEqual([
|
|
31
|
-
_controllers.LanguageController,
|
|
32
|
-
_controllers.TranslationKeyController,
|
|
33
|
-
_controllers.TranslationController
|
|
34
|
-
]);
|
|
35
|
-
});
|
|
36
|
-
it('should respect global: true', ()=>{
|
|
37
|
-
expect(_localizationmodule.LocalizationModule.forRoot({
|
|
38
|
-
global: true
|
|
39
|
-
}).global).toBe(true);
|
|
40
|
-
});
|
|
41
|
-
it('should register no controllers when includeController is false', ()=>{
|
|
42
|
-
expect(_localizationmodule.LocalizationModule.forRoot({
|
|
43
|
-
includeController: false
|
|
44
|
-
}).controllers).toEqual([]);
|
|
45
|
-
});
|
|
46
|
-
it('should register a LOCALIZATION_MODULE_OPTIONS provider carrying the given options', ()=>{
|
|
47
|
-
const options = {
|
|
48
|
-
bootstrapAppConfig: {}
|
|
49
|
-
};
|
|
50
|
-
const dynamicModule = _localizationmodule.LocalizationModule.forRoot(options);
|
|
51
|
-
const provider = dynamicModule.providers.find((p)=>p.provide === _localizationconstants.LOCALIZATION_MODULE_OPTIONS);
|
|
52
|
-
expect(provider.useValue).toBe(options);
|
|
53
|
-
});
|
|
54
|
-
it('should always export the same fixed set of services', ()=>{
|
|
55
|
-
expect(_localizationmodule.LocalizationModule.forRoot({}).exports).toHaveLength(5);
|
|
56
|
-
});
|
|
57
|
-
});
|
|
58
|
-
describe('forRootAsync', ()=>{
|
|
59
|
-
it('should forward external imports alongside CacheModule/UtilsModule', ()=>{
|
|
60
|
-
let FakeImportedModule = class FakeImportedModule {
|
|
61
|
-
};
|
|
62
|
-
const dynamicModule = _localizationmodule.LocalizationModule.forRootAsync({
|
|
63
|
-
imports: [
|
|
64
|
-
FakeImportedModule
|
|
65
|
-
]
|
|
66
|
-
});
|
|
67
|
-
expect(dynamicModule.imports).toEqual(expect.arrayContaining([
|
|
68
|
-
FakeImportedModule
|
|
69
|
-
]));
|
|
70
|
-
});
|
|
71
|
-
it('useFactory: builds a LOCALIZATION_MODULE_OPTIONS provider merging resolved config', async ()=>{
|
|
72
|
-
const useFactory = jest.fn().mockResolvedValue({
|
|
73
|
-
foo: 'bar'
|
|
74
|
-
});
|
|
75
|
-
const dynamicModule = _localizationmodule.LocalizationModule.forRootAsync({
|
|
76
|
-
useFactory,
|
|
77
|
-
inject: [
|
|
78
|
-
'SOME_TOKEN'
|
|
79
|
-
]
|
|
80
|
-
});
|
|
81
|
-
const provider = dynamicModule.providers.find((p)=>p.provide === _localizationconstants.LOCALIZATION_MODULE_OPTIONS);
|
|
82
|
-
expect(provider.inject).toEqual([
|
|
83
|
-
'SOME_TOKEN'
|
|
84
|
-
]);
|
|
85
|
-
const resolved = await provider.useFactory('injected');
|
|
86
|
-
expect(useFactory).toHaveBeenCalledWith('injected');
|
|
87
|
-
expect(resolved.config).toEqual({
|
|
88
|
-
foo: 'bar'
|
|
89
|
-
});
|
|
90
|
-
});
|
|
91
|
-
it('useClass: registers both the class provider and an options provider calling createLocalizationOptions()', async ()=>{
|
|
92
|
-
let MyOptionsFactory = class MyOptionsFactory {
|
|
93
|
-
constructor(){
|
|
94
|
-
_define_property(this, "createLocalizationOptions", jest.fn().mockResolvedValue({
|
|
95
|
-
foo: 'from-class'
|
|
96
|
-
}));
|
|
97
|
-
}
|
|
98
|
-
};
|
|
99
|
-
const dynamicModule = _localizationmodule.LocalizationModule.forRootAsync({
|
|
100
|
-
useClass: MyOptionsFactory
|
|
101
|
-
});
|
|
102
|
-
const classProvider = dynamicModule.providers.find((p)=>p.provide === MyOptionsFactory);
|
|
103
|
-
expect(classProvider.useClass).toBe(MyOptionsFactory);
|
|
104
|
-
const optionsProvider = dynamicModule.providers.find((p)=>p.provide === _localizationconstants.LOCALIZATION_MODULE_OPTIONS);
|
|
105
|
-
const instance = new MyOptionsFactory();
|
|
106
|
-
const resolved = await optionsProvider.useFactory(instance);
|
|
107
|
-
expect(instance.createLocalizationOptions).toHaveBeenCalled();
|
|
108
|
-
expect(resolved.config).toEqual({
|
|
109
|
-
foo: 'from-class'
|
|
110
|
-
});
|
|
111
|
-
});
|
|
112
|
-
it('useExisting: registers a single options provider without a duplicate class registration', ()=>{
|
|
113
|
-
let MyOptionsFactory = class MyOptionsFactory {
|
|
114
|
-
constructor(){
|
|
115
|
-
_define_property(this, "createLocalizationOptions", jest.fn());
|
|
116
|
-
}
|
|
117
|
-
};
|
|
118
|
-
const dynamicModule = _localizationmodule.LocalizationModule.forRootAsync({
|
|
119
|
-
useExisting: MyOptionsFactory
|
|
120
|
-
});
|
|
121
|
-
expect(dynamicModule.providers.filter((p)=>p.provide === MyOptionsFactory)).toHaveLength(0);
|
|
122
|
-
const optionsProvider = dynamicModule.providers.find((p)=>p.provide === _localizationconstants.LOCALIZATION_MODULE_OPTIONS);
|
|
123
|
-
expect(optionsProvider.inject).toEqual([
|
|
124
|
-
MyOptionsFactory
|
|
125
|
-
]);
|
|
126
|
-
});
|
|
127
|
-
it('should register no LOCALIZATION_MODULE_OPTIONS provider when neither useFactory, useClass, nor useExisting is given', ()=>{
|
|
128
|
-
const dynamicModule = _localizationmodule.LocalizationModule.forRootAsync({});
|
|
129
|
-
expect(providerTokens(dynamicModule.providers)).not.toContain(_localizationconstants.LOCALIZATION_MODULE_OPTIONS);
|
|
130
|
-
});
|
|
131
|
-
});
|
|
132
|
-
});
|
package/cjs/services/index.js
DELETED
|
@@ -1,22 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", {
|
|
3
|
-
value: true
|
|
4
|
-
});
|
|
5
|
-
_export_star(require("./localization-config.service"), exports);
|
|
6
|
-
_export_star(require("./localization-datasource.provider"), exports);
|
|
7
|
-
_export_star(require("./language.service"), exports);
|
|
8
|
-
_export_star(require("./translation-key.service"), exports);
|
|
9
|
-
_export_star(require("./translation.service"), exports);
|
|
10
|
-
function _export_star(from, to) {
|
|
11
|
-
Object.keys(from).forEach(function(k) {
|
|
12
|
-
if (k !== "default" && !Object.prototype.hasOwnProperty.call(to, k)) {
|
|
13
|
-
Object.defineProperty(to, k, {
|
|
14
|
-
enumerable: true,
|
|
15
|
-
get: function() {
|
|
16
|
-
return from[k];
|
|
17
|
-
}
|
|
18
|
-
});
|
|
19
|
-
}
|
|
20
|
-
});
|
|
21
|
-
return from;
|
|
22
|
-
}
|
|
@@ -1,181 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", {
|
|
3
|
-
value: true
|
|
4
|
-
});
|
|
5
|
-
Object.defineProperty(exports, "LanguageService", {
|
|
6
|
-
enumerable: true,
|
|
7
|
-
get: function() {
|
|
8
|
-
return LanguageService;
|
|
9
|
-
}
|
|
10
|
-
});
|
|
11
|
-
const _classes = require("@flusys/nestjs-shared/classes");
|
|
12
|
-
const _modules = require("@flusys/nestjs-shared/modules");
|
|
13
|
-
const _common = require("@nestjs/common");
|
|
14
|
-
const _typeorm = require("typeorm");
|
|
15
|
-
const _config = require("../config");
|
|
16
|
-
const _entities = require("../entities");
|
|
17
|
-
const _localizationdatasourceprovider = require("./localization-datasource.provider");
|
|
18
|
-
function _define_property(obj, key, value) {
|
|
19
|
-
if (key in obj) {
|
|
20
|
-
Object.defineProperty(obj, key, {
|
|
21
|
-
value: value,
|
|
22
|
-
enumerable: true,
|
|
23
|
-
configurable: true,
|
|
24
|
-
writable: true
|
|
25
|
-
});
|
|
26
|
-
} else {
|
|
27
|
-
obj[key] = value;
|
|
28
|
-
}
|
|
29
|
-
return obj;
|
|
30
|
-
}
|
|
31
|
-
function _ts_decorate(decorators, target, key, desc) {
|
|
32
|
-
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
33
|
-
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
34
|
-
else for(var i = decorators.length - 1; i >= 0; i--)if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
35
|
-
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
36
|
-
}
|
|
37
|
-
function _ts_metadata(k, v) {
|
|
38
|
-
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
39
|
-
}
|
|
40
|
-
function _ts_param(paramIndex, decorator) {
|
|
41
|
-
return function(target, key) {
|
|
42
|
-
decorator(target, key, paramIndex);
|
|
43
|
-
};
|
|
44
|
-
}
|
|
45
|
-
let LanguageService = class LanguageService extends _classes.ApiService {
|
|
46
|
-
async beforeUpdateOperation(dto, _user, _queryRunner) {
|
|
47
|
-
const dtos = Array.isArray(dto) ? dto : [
|
|
48
|
-
dto
|
|
49
|
-
];
|
|
50
|
-
const ids = dtos.map((d)=>d.id);
|
|
51
|
-
await this.ensureDataSourceRepository();
|
|
52
|
-
const existingLanguages = await this.repository.find({
|
|
53
|
-
where: {
|
|
54
|
-
id: (0, _typeorm.In)(ids),
|
|
55
|
-
deletedAt: (0, _typeorm.IsNull)()
|
|
56
|
-
}
|
|
57
|
-
});
|
|
58
|
-
for (const d of dtos){
|
|
59
|
-
const existing = existingLanguages.find((e)=>e.id === d.id);
|
|
60
|
-
if (!existing) {
|
|
61
|
-
continue;
|
|
62
|
-
}
|
|
63
|
-
const changesIdentity = d.code !== undefined && d.code !== existing.code || d.name !== undefined && d.name !== existing.name || d.nativeName !== undefined && d.nativeName !== (existing.nativeName ?? undefined) || d.direction !== undefined && d.direction !== existing.direction;
|
|
64
|
-
if (existing.isReadonly && changesIdentity) {
|
|
65
|
-
throw new _common.ForbiddenException({
|
|
66
|
-
message: `Cannot modify code/name of readonly language "${existing.name}"`,
|
|
67
|
-
messageKey: _config.LANGUAGE_MESSAGES.READONLY_UPDATE_FORBIDDEN,
|
|
68
|
-
messageVariables: {
|
|
69
|
-
name: existing.name
|
|
70
|
-
}
|
|
71
|
-
});
|
|
72
|
-
}
|
|
73
|
-
}
|
|
74
|
-
}
|
|
75
|
-
async beforeDeleteOperation(dto, _user, _queryRunner) {
|
|
76
|
-
const ids = Array.isArray(dto.id) ? dto.id : [
|
|
77
|
-
dto.id
|
|
78
|
-
];
|
|
79
|
-
await this.ensureDataSourceRepository();
|
|
80
|
-
const languages = await this.repository.find({
|
|
81
|
-
where: {
|
|
82
|
-
id: (0, _typeorm.In)(ids),
|
|
83
|
-
deletedAt: (0, _typeorm.IsNull)()
|
|
84
|
-
}
|
|
85
|
-
});
|
|
86
|
-
const readonlyLanguages = languages.filter((l)=>l.isReadonly);
|
|
87
|
-
if (readonlyLanguages.length > 0) {
|
|
88
|
-
const names = readonlyLanguages.map((l)=>l.name).join(', ');
|
|
89
|
-
throw new _common.ForbiddenException({
|
|
90
|
-
message: `Cannot delete readonly language(s): ${names}`,
|
|
91
|
-
messageKey: _config.LANGUAGE_MESSAGES.READONLY_DELETE_FORBIDDEN,
|
|
92
|
-
messageVariables: {
|
|
93
|
-
names
|
|
94
|
-
}
|
|
95
|
-
});
|
|
96
|
-
}
|
|
97
|
-
const defaultLanguages = languages.filter((l)=>l.isDefault);
|
|
98
|
-
if (defaultLanguages.length > 0) {
|
|
99
|
-
const names = defaultLanguages.map((l)=>l.name).join(', ');
|
|
100
|
-
throw new _common.ForbiddenException({
|
|
101
|
-
message: `Cannot delete the default language(s): ${names}. Set another language as default first.`,
|
|
102
|
-
messageKey: _config.LANGUAGE_MESSAGES.DEFAULT_DELETE_FORBIDDEN,
|
|
103
|
-
messageVariables: {
|
|
104
|
-
names
|
|
105
|
-
}
|
|
106
|
-
});
|
|
107
|
-
}
|
|
108
|
-
}
|
|
109
|
-
async getDefaultLanguage() {
|
|
110
|
-
await this.ensureDataSourceRepository();
|
|
111
|
-
return this.repository.findOne({
|
|
112
|
-
where: {
|
|
113
|
-
isDefault: true,
|
|
114
|
-
deletedAt: (0, _typeorm.IsNull)()
|
|
115
|
-
}
|
|
116
|
-
});
|
|
117
|
-
}
|
|
118
|
-
async getActiveLanguages() {
|
|
119
|
-
await this.ensureDataSourceRepository();
|
|
120
|
-
return this.repository.find({
|
|
121
|
-
where: {
|
|
122
|
-
isActive: true,
|
|
123
|
-
deletedAt: (0, _typeorm.IsNull)()
|
|
124
|
-
},
|
|
125
|
-
order: {
|
|
126
|
-
serial: 'ASC',
|
|
127
|
-
name: 'ASC'
|
|
128
|
-
}
|
|
129
|
-
});
|
|
130
|
-
}
|
|
131
|
-
async setAsDefault(id) {
|
|
132
|
-
await this.ensureDataSourceRepository();
|
|
133
|
-
const previousDefaults = await this.repository.find({
|
|
134
|
-
where: {
|
|
135
|
-
isDefault: true
|
|
136
|
-
}
|
|
137
|
-
});
|
|
138
|
-
await this.repository.update({
|
|
139
|
-
isDefault: true
|
|
140
|
-
}, {
|
|
141
|
-
isDefault: false
|
|
142
|
-
});
|
|
143
|
-
await this.repository.update({
|
|
144
|
-
id
|
|
145
|
-
}, {
|
|
146
|
-
isDefault: true
|
|
147
|
-
});
|
|
148
|
-
const language = await this.repository.findOne({
|
|
149
|
-
where: {
|
|
150
|
-
id
|
|
151
|
-
}
|
|
152
|
-
});
|
|
153
|
-
await Promise.all([
|
|
154
|
-
this.clearCacheForAll(),
|
|
155
|
-
this.clearCacheForId([
|
|
156
|
-
...previousDefaults,
|
|
157
|
-
{
|
|
158
|
-
id
|
|
159
|
-
}
|
|
160
|
-
])
|
|
161
|
-
]);
|
|
162
|
-
return language;
|
|
163
|
-
}
|
|
164
|
-
constructor(cacheManager, utilsService, dataSourceProvider){
|
|
165
|
-
super(_config.LOCALIZATION_EVENT_ENTITIES.LANGUAGE, cacheManager, utilsService, LanguageService.name, true, _config.LOCALIZATION_EVENT_MODULE, dataSourceProvider, _entities.Language), _define_property(this, "cacheManager", void 0), _define_property(this, "utilsService", void 0), this.cacheManager = cacheManager, this.utilsService = utilsService;
|
|
166
|
-
}
|
|
167
|
-
};
|
|
168
|
-
LanguageService = _ts_decorate([
|
|
169
|
-
(0, _common.Injectable)({
|
|
170
|
-
scope: _common.Scope.REQUEST
|
|
171
|
-
}),
|
|
172
|
-
_ts_param(0, (0, _common.Inject)('CACHE_INSTANCE')),
|
|
173
|
-
_ts_param(1, (0, _common.Inject)(_modules.UtilsService)),
|
|
174
|
-
_ts_param(2, (0, _common.Inject)(_localizationdatasourceprovider.LocalizationDataSourceProvider)),
|
|
175
|
-
_ts_metadata("design:type", Function),
|
|
176
|
-
_ts_metadata("design:paramtypes", [
|
|
177
|
-
typeof _classes.HybridCache === "undefined" ? Object : _classes.HybridCache,
|
|
178
|
-
typeof _modules.UtilsService === "undefined" ? Object : _modules.UtilsService,
|
|
179
|
-
typeof _localizationdatasourceprovider.LocalizationDataSourceProvider === "undefined" ? Object : _localizationdatasourceprovider.LocalizationDataSourceProvider
|
|
180
|
-
])
|
|
181
|
-
], LanguageService);
|
|
@@ -1,256 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", {
|
|
3
|
-
value: true
|
|
4
|
-
});
|
|
5
|
-
const _testing = require("@nestjs/testing");
|
|
6
|
-
const _modules = require("@flusys/nestjs-shared/modules");
|
|
7
|
-
const _repositorymock = require("@test-utils/mocks/repository.mock");
|
|
8
|
-
const _languageservice = require("./language.service");
|
|
9
|
-
const _localizationdatasourceprovider = require("./localization-datasource.provider");
|
|
10
|
-
function buildLanguage(overrides = {}) {
|
|
11
|
-
return {
|
|
12
|
-
id: 'language-uuid-1',
|
|
13
|
-
code: 'en',
|
|
14
|
-
name: 'English',
|
|
15
|
-
nativeName: 'English',
|
|
16
|
-
direction: 'ltr',
|
|
17
|
-
isActive: true,
|
|
18
|
-
isDefault: false,
|
|
19
|
-
serial: 1,
|
|
20
|
-
isReadonly: false,
|
|
21
|
-
createdAt: new Date(),
|
|
22
|
-
updatedAt: new Date(),
|
|
23
|
-
deletedAt: null,
|
|
24
|
-
createdById: null,
|
|
25
|
-
updatedById: null,
|
|
26
|
-
deletedById: null,
|
|
27
|
-
...overrides
|
|
28
|
-
};
|
|
29
|
-
}
|
|
30
|
-
describe('LanguageService', ()=>{
|
|
31
|
-
let service;
|
|
32
|
-
let mockRepo;
|
|
33
|
-
const mockUtilsService = {
|
|
34
|
-
clearCache: jest.fn(),
|
|
35
|
-
getCacheKey: jest.fn().mockReturnValue('cache-key'),
|
|
36
|
-
trackCacheKey: jest.fn()
|
|
37
|
-
};
|
|
38
|
-
// Call history is shared across tests in this file; reset it so each cache assertion is exact.
|
|
39
|
-
beforeEach(()=>{
|
|
40
|
-
mockUtilsService.clearCache.mockClear();
|
|
41
|
-
});
|
|
42
|
-
beforeEach(async ()=>{
|
|
43
|
-
mockRepo = (0, _repositorymock.createMockRepository)();
|
|
44
|
-
const mockDataSourceProvider = (0, _repositorymock.createMockDataSourceProvider)(mockRepo);
|
|
45
|
-
const module = await _testing.Test.createTestingModule({
|
|
46
|
-
providers: [
|
|
47
|
-
_languageservice.LanguageService,
|
|
48
|
-
{
|
|
49
|
-
provide: 'CACHE_INSTANCE',
|
|
50
|
-
useValue: {}
|
|
51
|
-
},
|
|
52
|
-
{
|
|
53
|
-
provide: _modules.UtilsService,
|
|
54
|
-
useValue: mockUtilsService
|
|
55
|
-
},
|
|
56
|
-
{
|
|
57
|
-
provide: _localizationdatasourceprovider.LocalizationDataSourceProvider,
|
|
58
|
-
useValue: mockDataSourceProvider
|
|
59
|
-
}
|
|
60
|
-
]
|
|
61
|
-
}).compile();
|
|
62
|
-
service = await module.resolve(_languageservice.LanguageService);
|
|
63
|
-
});
|
|
64
|
-
describe('getDefaultLanguage', ()=>{
|
|
65
|
-
it('returns the language flagged as default', async ()=>{
|
|
66
|
-
const defaultLanguage = buildLanguage({
|
|
67
|
-
id: 'default-lang',
|
|
68
|
-
isDefault: true,
|
|
69
|
-
code: 'en'
|
|
70
|
-
});
|
|
71
|
-
mockRepo.findOne.mockResolvedValue(defaultLanguage);
|
|
72
|
-
const result = await service.getDefaultLanguage();
|
|
73
|
-
expect(mockRepo.findOne).toHaveBeenCalledWith({
|
|
74
|
-
where: {
|
|
75
|
-
isDefault: true,
|
|
76
|
-
deletedAt: expect.anything()
|
|
77
|
-
}
|
|
78
|
-
});
|
|
79
|
-
expect(result).toEqual(defaultLanguage);
|
|
80
|
-
});
|
|
81
|
-
it('returns null when no language is marked default', async ()=>{
|
|
82
|
-
mockRepo.findOne.mockResolvedValue(null);
|
|
83
|
-
const result = await service.getDefaultLanguage();
|
|
84
|
-
expect(result).toBeNull();
|
|
85
|
-
});
|
|
86
|
-
});
|
|
87
|
-
describe('getActiveLanguages', ()=>{
|
|
88
|
-
it('returns active, non-deleted languages ordered by serial then name', async ()=>{
|
|
89
|
-
const languages = [
|
|
90
|
-
buildLanguage({
|
|
91
|
-
code: 'en',
|
|
92
|
-
serial: 1
|
|
93
|
-
}),
|
|
94
|
-
buildLanguage({
|
|
95
|
-
code: 'bn',
|
|
96
|
-
serial: 2
|
|
97
|
-
})
|
|
98
|
-
];
|
|
99
|
-
mockRepo.find.mockResolvedValue(languages);
|
|
100
|
-
const result = await service.getActiveLanguages();
|
|
101
|
-
expect(mockRepo.find).toHaveBeenCalledWith({
|
|
102
|
-
where: {
|
|
103
|
-
isActive: true,
|
|
104
|
-
deletedAt: expect.anything()
|
|
105
|
-
},
|
|
106
|
-
order: {
|
|
107
|
-
serial: 'ASC',
|
|
108
|
-
name: 'ASC'
|
|
109
|
-
}
|
|
110
|
-
});
|
|
111
|
-
expect(result).toHaveLength(2);
|
|
112
|
-
});
|
|
113
|
-
it('returns an empty array when no languages are active', async ()=>{
|
|
114
|
-
mockRepo.find.mockResolvedValue([]);
|
|
115
|
-
const result = await service.getActiveLanguages();
|
|
116
|
-
expect(result).toEqual([]);
|
|
117
|
-
});
|
|
118
|
-
});
|
|
119
|
-
describe('setAsDefault', ()=>{
|
|
120
|
-
beforeEach(()=>{
|
|
121
|
-
mockRepo.find.mockResolvedValue([]);
|
|
122
|
-
});
|
|
123
|
-
it('unsets the previous default and sets the requested language as default', async ()=>{
|
|
124
|
-
const newDefault = buildLanguage({
|
|
125
|
-
id: 'lang-2',
|
|
126
|
-
isDefault: true,
|
|
127
|
-
code: 'bn'
|
|
128
|
-
});
|
|
129
|
-
mockRepo.findOne.mockResolvedValue(newDefault);
|
|
130
|
-
const result = await service.setAsDefault('lang-2');
|
|
131
|
-
expect(mockRepo.update).toHaveBeenNthCalledWith(1, {
|
|
132
|
-
isDefault: true
|
|
133
|
-
}, {
|
|
134
|
-
isDefault: false
|
|
135
|
-
});
|
|
136
|
-
expect(mockRepo.update).toHaveBeenNthCalledWith(2, {
|
|
137
|
-
id: 'lang-2'
|
|
138
|
-
}, {
|
|
139
|
-
isDefault: true
|
|
140
|
-
});
|
|
141
|
-
expect(mockRepo.findOne).toHaveBeenCalledWith({
|
|
142
|
-
where: {
|
|
143
|
-
id: 'lang-2'
|
|
144
|
-
}
|
|
145
|
-
});
|
|
146
|
-
expect(result).toEqual(newDefault);
|
|
147
|
-
});
|
|
148
|
-
it('invalidates the language list cache and both the old and new default entries', async ()=>{
|
|
149
|
-
const previousDefault = buildLanguage({
|
|
150
|
-
id: 'lang-1',
|
|
151
|
-
isDefault: true,
|
|
152
|
-
code: 'en'
|
|
153
|
-
});
|
|
154
|
-
mockRepo.find.mockResolvedValue([
|
|
155
|
-
previousDefault
|
|
156
|
-
]);
|
|
157
|
-
mockRepo.findOne.mockResolvedValue(buildLanguage({
|
|
158
|
-
id: 'lang-2',
|
|
159
|
-
isDefault: true
|
|
160
|
-
}));
|
|
161
|
-
await service.setAsDefault('lang-2');
|
|
162
|
-
expect(mockUtilsService.clearCache).toHaveBeenCalledWith('language', expect.anything());
|
|
163
|
-
expect(mockUtilsService.clearCache).toHaveBeenCalledWith('language', expect.anything(), 'lang-1');
|
|
164
|
-
expect(mockUtilsService.clearCache).toHaveBeenCalledWith('language', expect.anything(), 'lang-2');
|
|
165
|
-
});
|
|
166
|
-
it('returns null when the id does not correspond to any language after the update', async ()=>{
|
|
167
|
-
mockRepo.findOne.mockResolvedValue(null);
|
|
168
|
-
const result = await service.setAsDefault('non-existent-id');
|
|
169
|
-
expect(result).toBeNull();
|
|
170
|
-
});
|
|
171
|
-
it('still unsets other defaults first even when the target id is unknown (no exception thrown)', async ()=>{
|
|
172
|
-
mockRepo.findOne.mockResolvedValue(null);
|
|
173
|
-
await service.setAsDefault('unknown-id');
|
|
174
|
-
expect(mockRepo.update).toHaveBeenCalledWith({
|
|
175
|
-
isDefault: true
|
|
176
|
-
}, {
|
|
177
|
-
isDefault: false
|
|
178
|
-
});
|
|
179
|
-
});
|
|
180
|
-
});
|
|
181
|
-
describe('beforeUpdateOperation', ()=>{
|
|
182
|
-
it('rejects renaming the code of a readonly language', async ()=>{
|
|
183
|
-
mockRepo.find.mockResolvedValue([
|
|
184
|
-
buildLanguage({
|
|
185
|
-
isReadonly: true,
|
|
186
|
-
code: 'en'
|
|
187
|
-
})
|
|
188
|
-
]);
|
|
189
|
-
await expect(service.beforeUpdateOperation({
|
|
190
|
-
id: 'language-uuid-1',
|
|
191
|
-
code: 'fr'
|
|
192
|
-
}, null, {})).rejects.toThrow('Cannot modify code/name of readonly language');
|
|
193
|
-
});
|
|
194
|
-
it('allows updating isActive on a readonly language when identity fields are unchanged', async ()=>{
|
|
195
|
-
mockRepo.find.mockResolvedValue([
|
|
196
|
-
buildLanguage({
|
|
197
|
-
isReadonly: true,
|
|
198
|
-
code: 'en',
|
|
199
|
-
name: 'English'
|
|
200
|
-
})
|
|
201
|
-
]);
|
|
202
|
-
await expect(service.beforeUpdateOperation({
|
|
203
|
-
id: 'language-uuid-1',
|
|
204
|
-
code: 'en',
|
|
205
|
-
name: 'English',
|
|
206
|
-
isActive: false
|
|
207
|
-
}, null, {})).resolves.toBeUndefined();
|
|
208
|
-
});
|
|
209
|
-
it('allows any field change on a non-readonly language', async ()=>{
|
|
210
|
-
mockRepo.find.mockResolvedValue([
|
|
211
|
-
buildLanguage({
|
|
212
|
-
isReadonly: false,
|
|
213
|
-
code: 'en'
|
|
214
|
-
})
|
|
215
|
-
]);
|
|
216
|
-
await expect(service.beforeUpdateOperation({
|
|
217
|
-
id: 'language-uuid-1',
|
|
218
|
-
code: 'fr'
|
|
219
|
-
}, null, {})).resolves.toBeUndefined();
|
|
220
|
-
});
|
|
221
|
-
});
|
|
222
|
-
describe('beforeDeleteOperation', ()=>{
|
|
223
|
-
it('rejects deleting a readonly language', async ()=>{
|
|
224
|
-
mockRepo.find.mockResolvedValue([
|
|
225
|
-
buildLanguage({
|
|
226
|
-
isReadonly: true
|
|
227
|
-
})
|
|
228
|
-
]);
|
|
229
|
-
await expect(service.beforeDeleteOperation({
|
|
230
|
-
id: 'language-uuid-1'
|
|
231
|
-
}, null, {})).rejects.toThrow('Cannot delete readonly language');
|
|
232
|
-
});
|
|
233
|
-
it('rejects deleting the default language', async ()=>{
|
|
234
|
-
mockRepo.find.mockResolvedValue([
|
|
235
|
-
buildLanguage({
|
|
236
|
-
isReadonly: false,
|
|
237
|
-
isDefault: true
|
|
238
|
-
})
|
|
239
|
-
]);
|
|
240
|
-
await expect(service.beforeDeleteOperation({
|
|
241
|
-
id: 'language-uuid-1'
|
|
242
|
-
}, null, {})).rejects.toThrow('Cannot delete the default language');
|
|
243
|
-
});
|
|
244
|
-
it('allows deleting a non-readonly, non-default language', async ()=>{
|
|
245
|
-
mockRepo.find.mockResolvedValue([
|
|
246
|
-
buildLanguage({
|
|
247
|
-
isReadonly: false,
|
|
248
|
-
isDefault: false
|
|
249
|
-
})
|
|
250
|
-
]);
|
|
251
|
-
await expect(service.beforeDeleteOperation({
|
|
252
|
-
id: 'language-uuid-1'
|
|
253
|
-
}, null, {})).resolves.toBeUndefined();
|
|
254
|
-
});
|
|
255
|
-
});
|
|
256
|
-
});
|
|
@@ -1,66 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", {
|
|
3
|
-
value: true
|
|
4
|
-
});
|
|
5
|
-
Object.defineProperty(exports, "LocalizationConfigService", {
|
|
6
|
-
enumerable: true,
|
|
7
|
-
get: function() {
|
|
8
|
-
return LocalizationConfigService;
|
|
9
|
-
}
|
|
10
|
-
});
|
|
11
|
-
const _common = require("@nestjs/common");
|
|
12
|
-
const _localizationconstants = require("../config/localization.constants");
|
|
13
|
-
const _interfaces = require("../interfaces");
|
|
14
|
-
function _define_property(obj, key, value) {
|
|
15
|
-
if (key in obj) {
|
|
16
|
-
Object.defineProperty(obj, key, {
|
|
17
|
-
value: value,
|
|
18
|
-
enumerable: true,
|
|
19
|
-
configurable: true,
|
|
20
|
-
writable: true
|
|
21
|
-
});
|
|
22
|
-
} else {
|
|
23
|
-
obj[key] = value;
|
|
24
|
-
}
|
|
25
|
-
return obj;
|
|
26
|
-
}
|
|
27
|
-
function _ts_decorate(decorators, target, key, desc) {
|
|
28
|
-
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
29
|
-
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
30
|
-
else for(var i = decorators.length - 1; i >= 0; i--)if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
31
|
-
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
32
|
-
}
|
|
33
|
-
function _ts_metadata(k, v) {
|
|
34
|
-
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
35
|
-
}
|
|
36
|
-
function _ts_param(paramIndex, decorator) {
|
|
37
|
-
return function(target, key) {
|
|
38
|
-
decorator(target, key, paramIndex);
|
|
39
|
-
};
|
|
40
|
-
}
|
|
41
|
-
let LocalizationConfigService = class LocalizationConfigService {
|
|
42
|
-
isCompanyFeatureEnabled() {
|
|
43
|
-
return false;
|
|
44
|
-
}
|
|
45
|
-
getDatabaseMode() {
|
|
46
|
-
return this.options.bootstrapAppConfig?.databaseMode ?? 'single';
|
|
47
|
-
}
|
|
48
|
-
isMultiTenant() {
|
|
49
|
-
return this.getDatabaseMode() === 'multi-tenant';
|
|
50
|
-
}
|
|
51
|
-
getOptions() {
|
|
52
|
-
return this.options;
|
|
53
|
-
}
|
|
54
|
-
constructor(options){
|
|
55
|
-
_define_property(this, "options", void 0);
|
|
56
|
-
this.options = options;
|
|
57
|
-
}
|
|
58
|
-
};
|
|
59
|
-
LocalizationConfigService = _ts_decorate([
|
|
60
|
-
(0, _common.Injectable)(),
|
|
61
|
-
_ts_param(0, (0, _common.Inject)(_localizationconstants.LOCALIZATION_MODULE_OPTIONS)),
|
|
62
|
-
_ts_metadata("design:type", Function),
|
|
63
|
-
_ts_metadata("design:paramtypes", [
|
|
64
|
-
typeof _interfaces.LocalizationModuleOptions === "undefined" ? Object : _interfaces.LocalizationModuleOptions
|
|
65
|
-
])
|
|
66
|
-
], LocalizationConfigService);
|