@openmrs/esm-app-shell 5.3.3-pre.1231 → 5.3.3-pre.1247
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/.turbo/turbo-build.log +98 -98
- package/dist/9c276181fc6599f8.js.map +1 -0
- package/dist/d81faa62d5818f52.js.map +1 -0
- package/dist/index.html +1 -1
- package/dist/{openmrs.954886865de0b85a.js → openmrs.6213811dbd70a295.js} +2 -2
- package/dist/openmrs.6213811dbd70a295.js.map +1 -0
- package/dist/openmrs.c9c4fe7ea57e9920.css.map +1 -1
- package/dist/service-worker.js +1 -1
- package/dist/service-worker.js.map +1 -1
- package/lib/{3975decbab0164f3.js → 9b51c0739002f900.js} +1 -1
- package/lib/{f29978db163aaa3d.js → c074b9133e91fad3.js} +5 -5
- package/lib/esm-devtools-app/68.js.map +1 -1
- package/lib/esm-devtools-app/889.js +1 -1
- package/lib/esm-devtools-app/988.js.map +1 -1
- package/lib/esm-devtools-app/main.js +1 -1
- package/lib/esm-devtools-app/main.js.map +1 -1
- package/lib/esm-devtools-app/openmrs-esm-devtools-app.js +1 -1
- package/lib/esm-devtools-app/openmrs-esm-devtools-app.js.buildmanifest.json +5 -5
- package/lib/esm-devtools-app/routes.json +1 -1
- package/lib/esm-implementer-tools-app/426.js.map +1 -1
- package/lib/esm-implementer-tools-app/560.js +1 -1
- package/lib/esm-implementer-tools-app/560.js.map +1 -1
- package/lib/esm-implementer-tools-app/587.js.map +1 -1
- package/lib/esm-implementer-tools-app/727.js +1 -1
- package/lib/esm-implementer-tools-app/727.js.map +1 -1
- package/lib/esm-implementer-tools-app/main.js +1 -1
- package/lib/esm-implementer-tools-app/main.js.map +1 -1
- package/lib/esm-implementer-tools-app/openmrs-esm-implementer-tools-app.js +1 -1
- package/lib/esm-implementer-tools-app/openmrs-esm-implementer-tools-app.js.buildmanifest.json +13 -13
- package/lib/esm-implementer-tools-app/routes.json +1 -1
- package/lib/esm-login-app/370.js +1 -1
- package/lib/esm-login-app/370.js.map +1 -1
- package/lib/esm-login-app/main.js +1 -1
- package/lib/esm-login-app/main.js.map +1 -1
- package/lib/esm-login-app/openmrs-esm-login-app.js +1 -1
- package/lib/esm-login-app/openmrs-esm-login-app.js.buildmanifest.json +8 -8
- package/lib/esm-login-app/routes.json +1 -1
- package/lib/esm-offline-tools-app/102.js +1 -1
- package/lib/esm-offline-tools-app/102.js.map +1 -1
- package/lib/esm-offline-tools-app/main.js +1 -1
- package/lib/esm-offline-tools-app/main.js.map +1 -1
- package/lib/esm-offline-tools-app/openmrs-esm-offline-tools-app.js +1 -1
- package/lib/esm-offline-tools-app/openmrs-esm-offline-tools-app.js.buildmanifest.json +8 -8
- package/lib/esm-offline-tools-app/routes.json +1 -1
- package/lib/esm-primary-navigation-app/735.js +1 -1
- package/lib/esm-primary-navigation-app/735.js.map +1 -1
- package/lib/esm-primary-navigation-app/main.js +1 -1
- package/lib/esm-primary-navigation-app/main.js.map +1 -1
- package/lib/esm-primary-navigation-app/openmrs-esm-primary-navigation-app.js +1 -1
- package/lib/esm-primary-navigation-app/openmrs-esm-primary-navigation-app.js.buildmanifest.json +8 -8
- package/lib/esm-primary-navigation-app/routes.json +1 -1
- package/lib/index.html +1 -1
- package/lib/openmrs.js +135 -135
- package/lib/service-worker.js +9 -9
- package/package.json +3 -3
- package/src/apps.ts +32 -72
- package/src/declarations.d.ts +3 -6
- package/src/helpers.ts +2 -4
- package/src/index.ts +13 -15
- package/src/locale.ts +24 -34
- package/src/run.ts +53 -87
- package/src/service-worker/caching.ts +14 -22
- package/src/service-worker/constants.ts +8 -13
- package/src/service-worker/http-header-utils.ts +5 -15
- package/src/service-worker/import-map-utils.ts +14 -25
- package/src/service-worker/index.ts +8 -8
- package/src/service-worker/message.ts +9 -15
- package/src/service-worker/routing.ts +23 -50
- package/src/service-worker/storage.ts +5 -5
- package/src/service-worker/types.ts +1 -1
- package/src/ui/breadcrumbs.tsx +14 -29
- package/src/ui/index.ts +6 -6
- package/tools/helpers.js +3 -7
- package/webpack.config.js +95 -117
- package/dist/966c4dfec919951f.js.map +0 -1
- package/dist/fca8d09359d3b887.js.map +0 -1
- package/dist/openmrs.954886865de0b85a.js.map +0 -1
- /package/dist/{fca8d09359d3b887.js → 9c276181fc6599f8.js} +0 -0
- /package/dist/{966c4dfec919951f.js → d81faa62d5818f52.js} +0 -0
- /package/dist/{openmrs.954886865de0b85a.js.LICENSE.txt → openmrs.6213811dbd70a295.js.LICENSE.txt} +0 -0
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@openmrs/esm-app-shell",
|
|
3
|
-
"version": "5.3.3-pre.
|
|
3
|
+
"version": "5.3.3-pre.1247",
|
|
4
4
|
"license": "MPL-2.0",
|
|
5
5
|
"main": "dist/openmrs.js",
|
|
6
6
|
"scripts": {
|
|
@@ -34,8 +34,8 @@
|
|
|
34
34
|
},
|
|
35
35
|
"dependencies": {
|
|
36
36
|
"@carbon/react": "~1.37.0",
|
|
37
|
-
"@openmrs/esm-framework": "5.3.3-pre.
|
|
38
|
-
"@openmrs/esm-styleguide": "5.3.3-pre.
|
|
37
|
+
"@openmrs/esm-framework": "5.3.3-pre.1247",
|
|
38
|
+
"@openmrs/esm-styleguide": "5.3.3-pre.1247",
|
|
39
39
|
"dayjs": "^1.10.4",
|
|
40
40
|
"dexie": "^3.0.3",
|
|
41
41
|
"html-webpack-plugin": "^5.5.0",
|
package/src/apps.ts
CHANGED
|
@@ -7,14 +7,9 @@ import {
|
|
|
7
7
|
ExtensionDefinition,
|
|
8
8
|
OpenmrsAppRoutes,
|
|
9
9
|
RouteDefinition,
|
|
10
|
-
} from
|
|
11
|
-
import {
|
|
12
|
-
|
|
13
|
-
LifeCycles,
|
|
14
|
-
pathToActiveWhen,
|
|
15
|
-
registerApplication,
|
|
16
|
-
} from "single-spa";
|
|
17
|
-
import { emptyLifecycle, routeRegex } from "./helpers";
|
|
10
|
+
} from '@openmrs/esm-framework';
|
|
11
|
+
import { ActivityFn, LifeCycles, pathToActiveWhen, registerApplication } from 'single-spa';
|
|
12
|
+
import { emptyLifecycle, routeRegex } from './helpers';
|
|
18
13
|
|
|
19
14
|
const pages: Array<RegisteredPageDefinition> = [];
|
|
20
15
|
|
|
@@ -28,13 +23,11 @@ const pages: Array<RegisteredPageDefinition> = [];
|
|
|
28
23
|
* strings, regexps, and booleans
|
|
29
24
|
* @returns An activityFn suitable to use for a single-spa application
|
|
30
25
|
*/
|
|
31
|
-
function getActivityFn(
|
|
32
|
-
route: RouteDefinition | Array<RouteDefinition>
|
|
33
|
-
): ActivityFn {
|
|
26
|
+
function getActivityFn(route: RouteDefinition | Array<RouteDefinition>): ActivityFn {
|
|
34
27
|
if (Array.isArray(route)) {
|
|
35
28
|
const activators = route.map(getActivityFn);
|
|
36
29
|
return (location) => activators.some((activator) => activator(location));
|
|
37
|
-
} else if (typeof route ===
|
|
30
|
+
} else if (typeof route === 'string') {
|
|
38
31
|
return pathToActiveWhen(window.getOpenmrsSpaBase() + route);
|
|
39
32
|
} else if (route instanceof RegExp) {
|
|
40
33
|
return (location) => routeRegex(route, location);
|
|
@@ -55,20 +48,12 @@ function getActivityFn(
|
|
|
55
48
|
* @param pageDefinition The RegisteredPageDefinition object for this page
|
|
56
49
|
* @returns An activityFn suitable to use for a single-spa application
|
|
57
50
|
*/
|
|
58
|
-
function wrapPageActivityFn(
|
|
59
|
-
activityFn: ActivityFn,
|
|
60
|
-
{ online, offline }: RegisteredPageDefinition
|
|
61
|
-
) {
|
|
51
|
+
function wrapPageActivityFn(activityFn: ActivityFn, { online, offline }: RegisteredPageDefinition) {
|
|
62
52
|
return (location: Location) => {
|
|
63
53
|
// basically, if the page should only work online and we're offline or if the
|
|
64
54
|
// page should only work offline and we're online, defaulting to always rendering
|
|
65
55
|
// the page
|
|
66
|
-
if (
|
|
67
|
-
!(
|
|
68
|
-
(navigator.onLine && (online ?? true)) ||
|
|
69
|
-
(!navigator.onLine && (offline ?? false))
|
|
70
|
-
)
|
|
71
|
-
) {
|
|
56
|
+
if (!((navigator.onLine && (online ?? true)) || (!navigator.onLine && (offline ?? false)))) {
|
|
72
57
|
return false;
|
|
73
58
|
}
|
|
74
59
|
|
|
@@ -76,7 +61,7 @@ function wrapPageActivityFn(
|
|
|
76
61
|
};
|
|
77
62
|
}
|
|
78
63
|
|
|
79
|
-
const STARTUP_FUNCTION =
|
|
64
|
+
const STARTUP_FUNCTION = 'startupApp';
|
|
80
65
|
/**
|
|
81
66
|
* @internal
|
|
82
67
|
*
|
|
@@ -98,28 +83,18 @@ const initializedApps = new Map<string, Promise<unknown>>();
|
|
|
98
83
|
* React-based pages or extensions should generally use the framework's
|
|
99
84
|
* `getAsyncLifecycle()` or `getSyncLifecycle()` functions.
|
|
100
85
|
*/
|
|
101
|
-
function getLoader(
|
|
102
|
-
appName: string,
|
|
103
|
-
component: string
|
|
104
|
-
): () => Promise<LifeCycles> {
|
|
86
|
+
function getLoader(appName: string, component: string): () => Promise<LifeCycles> {
|
|
105
87
|
return async () => {
|
|
106
88
|
const module = await importDynamic<
|
|
107
|
-
Record<
|
|
108
|
-
Exclude<string, "startupApp">,
|
|
109
|
-
() => LifeCycles | Promise<LifeCycles>
|
|
110
|
-
> & { startupApp?: () => unknown }
|
|
89
|
+
Record<Exclude<string, 'startupApp'>, () => LifeCycles | Promise<LifeCycles>> & { startupApp?: () => unknown }
|
|
111
90
|
>(appName);
|
|
112
91
|
|
|
113
|
-
if (
|
|
114
|
-
module &&
|
|
115
|
-
Object.hasOwn(module, component) &&
|
|
116
|
-
typeof module[component] === "function"
|
|
117
|
-
) {
|
|
92
|
+
if (module && Object.hasOwn(module, component) && typeof module[component] === 'function') {
|
|
118
93
|
if (!(appName in initializedApps)) {
|
|
119
94
|
await (initializedApps[appName] = new Promise((resolve, reject) => {
|
|
120
95
|
if (Object.hasOwn(module, STARTUP_FUNCTION)) {
|
|
121
96
|
const startup = module[STARTUP_FUNCTION];
|
|
122
|
-
if (typeof startup ===
|
|
97
|
+
if (typeof startup === 'function') {
|
|
123
98
|
return Promise.resolve(startup()).then(resolve).catch(reject);
|
|
124
99
|
}
|
|
125
100
|
}
|
|
@@ -133,13 +108,9 @@ function getLoader(
|
|
|
133
108
|
return Promise.resolve(module[component]());
|
|
134
109
|
} else {
|
|
135
110
|
if (module && Object.hasOwn(module, component)) {
|
|
136
|
-
console.warn(
|
|
137
|
-
`The export ${component} of the app ${appName} is not a function`
|
|
138
|
-
);
|
|
111
|
+
console.warn(`The export ${component} of the app ${appName} is not a function`);
|
|
139
112
|
} else {
|
|
140
|
-
console.warn(
|
|
141
|
-
`The app ${appName} does not define a component called ${component}, this cannot be loaded`
|
|
142
|
-
);
|
|
113
|
+
console.warn(`The app ${appName} does not define a component called ${component}, this cannot be loaded`);
|
|
143
114
|
}
|
|
144
115
|
}
|
|
145
116
|
|
|
@@ -157,11 +128,10 @@ function getLoader(
|
|
|
157
128
|
* definition.
|
|
158
129
|
*/
|
|
159
130
|
export function registerApp(appName: string, routes: OpenmrsAppRoutes) {
|
|
160
|
-
if (appName && routes && typeof routes ===
|
|
131
|
+
if (appName && routes && typeof routes === 'object') {
|
|
161
132
|
defineConfigSchema(appName, {});
|
|
162
133
|
|
|
163
|
-
const availableExtensions: Array<ExtensionDefinition> =
|
|
164
|
-
routes.extensions ?? [];
|
|
134
|
+
const availableExtensions: Array<ExtensionDefinition> = routes.extensions ?? [];
|
|
165
135
|
|
|
166
136
|
routes.pages?.forEach((p) => {
|
|
167
137
|
pages.push({ ...p, order: p.order ?? Number.MAX_SAFE_INTEGER, appName });
|
|
@@ -187,7 +157,7 @@ export function finishRegisteringAllApps() {
|
|
|
187
157
|
if (sort != 0) {
|
|
188
158
|
return sort;
|
|
189
159
|
}
|
|
190
|
-
return a.appName.localeCompare(b.appName,
|
|
160
|
+
return a.appName.localeCompare(b.appName, 'en');
|
|
191
161
|
});
|
|
192
162
|
|
|
193
163
|
// Create a div for each page. This ensures their DOM order.
|
|
@@ -203,7 +173,7 @@ export function finishRegisteringAllApps() {
|
|
|
203
173
|
const index = appIndices.get(page.appName);
|
|
204
174
|
|
|
205
175
|
const name = `${page.appName}-page-${index}`;
|
|
206
|
-
const div = document.createElement(
|
|
176
|
+
const div = document.createElement('div');
|
|
207
177
|
div.id = `single-spa-application:${name}`;
|
|
208
178
|
document.body.appendChild(div);
|
|
209
179
|
tryRegisterPage(name, page);
|
|
@@ -218,22 +188,19 @@ export function finishRegisteringAllApps() {
|
|
|
218
188
|
* @param appName The name of the app containing this page
|
|
219
189
|
* @param page A Javascript object that describes the page defintion, derived from `routes.json`
|
|
220
190
|
*/
|
|
221
|
-
export function tryRegisterPage(
|
|
222
|
-
appName: string,
|
|
223
|
-
page: RegisteredPageDefinition
|
|
224
|
-
) {
|
|
191
|
+
export function tryRegisterPage(appName: string, page: RegisteredPageDefinition) {
|
|
225
192
|
const route =
|
|
226
|
-
typeof page.route !==
|
|
193
|
+
typeof page.route !== 'undefined'
|
|
227
194
|
? page.route
|
|
228
|
-
: typeof page.routeRegex !==
|
|
229
|
-
|
|
230
|
-
|
|
195
|
+
: typeof page.routeRegex !== 'undefined'
|
|
196
|
+
? new RegExp(page.routeRegex)
|
|
197
|
+
: false;
|
|
231
198
|
|
|
232
199
|
if (route === false) {
|
|
233
200
|
console.warn(
|
|
234
201
|
`A registered page definition is missing a route and thus cannot be registered.
|
|
235
202
|
To fix this, ensure that you define the "route" (or alternatively the "routeRegex") field inside the extension definition.`,
|
|
236
|
-
appName
|
|
203
|
+
appName,
|
|
237
204
|
);
|
|
238
205
|
return;
|
|
239
206
|
}
|
|
@@ -242,7 +209,7 @@ To fix this, ensure that you define the "route" (or alternatively the "routeRege
|
|
|
242
209
|
console.warn(
|
|
243
210
|
`A registered page definition is missing a component and thus cannot be registered.
|
|
244
211
|
To fix this, ensure that you define the "component" field inside the page definition.`,
|
|
245
|
-
appName
|
|
212
|
+
appName,
|
|
246
213
|
);
|
|
247
214
|
return;
|
|
248
215
|
}
|
|
@@ -259,17 +226,14 @@ To fix this, ensure that you define the "component" field inside the page defini
|
|
|
259
226
|
* @param appName The name of the app containing this page
|
|
260
227
|
* @param extension A Javascript object that describes the extension defintion, derived from `routes.json`
|
|
261
228
|
*/
|
|
262
|
-
export function tryRegisterExtension(
|
|
263
|
-
appName: string,
|
|
264
|
-
extension: ExtensionDefinition
|
|
265
|
-
) {
|
|
229
|
+
export function tryRegisterExtension(appName: string, extension: ExtensionDefinition) {
|
|
266
230
|
const name = extension.name;
|
|
267
231
|
if (!name) {
|
|
268
232
|
console.error(
|
|
269
233
|
`An extension definition in ${appName} is missing an name and thus cannot be
|
|
270
234
|
registered. To fix this, ensure that you define the "name" field inside the
|
|
271
235
|
extension definition.`,
|
|
272
|
-
extension
|
|
236
|
+
extension,
|
|
273
237
|
);
|
|
274
238
|
return;
|
|
275
239
|
}
|
|
@@ -277,20 +241,16 @@ extension definition.`,
|
|
|
277
241
|
if (extension.slots && extension.slot) {
|
|
278
242
|
console.warn(
|
|
279
243
|
`The extension ${name} from ${appName} declares both a 'slots' property and
|
|
280
|
-
a 'slot' property. Only the 'slots' property will be honored
|
|
244
|
+
a 'slot' property. Only the 'slots' property will be honored.`,
|
|
281
245
|
);
|
|
282
246
|
}
|
|
283
|
-
const slots = extension.slots
|
|
284
|
-
? extension.slots
|
|
285
|
-
: extension.slot
|
|
286
|
-
? [extension.slot]
|
|
287
|
-
: [];
|
|
247
|
+
const slots = extension.slots ? extension.slots : extension.slot ? [extension.slot] : [];
|
|
288
248
|
|
|
289
249
|
if (!extension.component && !extension.load) {
|
|
290
250
|
console.error(
|
|
291
251
|
`The extension ${name} from ${appName} is missing a 'component' entry and thus cannot be registered.
|
|
292
252
|
To fix this, ensure that you define a 'component' field inside the extension definition.`,
|
|
293
|
-
extension
|
|
253
|
+
extension,
|
|
294
254
|
);
|
|
295
255
|
return;
|
|
296
256
|
}
|
|
@@ -299,10 +259,10 @@ To fix this, ensure that you define a 'component' field inside the extension def
|
|
|
299
259
|
if (extension.component) {
|
|
300
260
|
loader = getLoader(appName, extension.component);
|
|
301
261
|
} else if (extension.load) {
|
|
302
|
-
if (typeof extension.load !==
|
|
262
|
+
if (typeof extension.load !== 'function') {
|
|
303
263
|
console.error(
|
|
304
264
|
`The extension ${name} from ${appName} declares a 'load' property that is not a function. This is not
|
|
305
|
-
supported, so the extension will not be loaded
|
|
265
|
+
supported, so the extension will not be loaded.`,
|
|
306
266
|
);
|
|
307
267
|
return;
|
|
308
268
|
}
|
package/src/declarations.d.ts
CHANGED
|
@@ -1,9 +1,6 @@
|
|
|
1
|
-
declare module
|
|
2
|
-
declare module
|
|
1
|
+
declare module '*.css';
|
|
2
|
+
declare module '*.scss';
|
|
3
3
|
declare const __webpack_share_scopes__: Record<
|
|
4
4
|
string,
|
|
5
|
-
Record<
|
|
6
|
-
string,
|
|
7
|
-
{ loaded?: 1; get: () => Promise<unknown>; from: string; eager: boolean }
|
|
8
|
-
>
|
|
5
|
+
Record<string, { loaded?: 1; get: () => Promise<unknown>; from: string; eager: boolean }>
|
|
9
6
|
>;
|
package/src/helpers.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { LifeCycles } from
|
|
1
|
+
import { LifeCycles } from 'single-spa';
|
|
2
2
|
|
|
3
3
|
export const emptyLifecycle: LifeCycles<never> = {
|
|
4
4
|
bootstrap() {
|
|
@@ -13,8 +13,6 @@ export const emptyLifecycle: LifeCycles<never> = {
|
|
|
13
13
|
};
|
|
14
14
|
|
|
15
15
|
export function routeRegex(regex: RegExp, location: Location) {
|
|
16
|
-
const result = regex.test(
|
|
17
|
-
location.pathname.replace(window.getOpenmrsSpaBase(), "")
|
|
18
|
-
);
|
|
16
|
+
const result = regex.test(location.pathname.replace(window.getOpenmrsSpaBase(), ''));
|
|
19
17
|
return result;
|
|
20
18
|
}
|
package/src/index.ts
CHANGED
|
@@ -1,37 +1,35 @@
|
|
|
1
|
-
import
|
|
2
|
-
import
|
|
3
|
-
import
|
|
4
|
-
import type { SpaConfig } from
|
|
1
|
+
import '@openmrs/esm-styleguide/dist/openmrs-esm-styleguide.css';
|
|
2
|
+
import 'import-map-overrides';
|
|
3
|
+
import '@openmrs/esm-framework';
|
|
4
|
+
import type { SpaConfig } from '@openmrs/esm-framework/src/internal';
|
|
5
5
|
|
|
6
6
|
export function setupPaths(config: SpaConfig) {
|
|
7
7
|
let error = false;
|
|
8
8
|
if (!config.apiUrl) {
|
|
9
9
|
console.error(
|
|
10
|
-
|
|
10
|
+
'initializeSpa() was called without supplying an apiUrl. This means that the application cannot communicate with the backend.',
|
|
11
11
|
);
|
|
12
12
|
error = true;
|
|
13
13
|
}
|
|
14
14
|
|
|
15
15
|
if (!config.spaPath) {
|
|
16
16
|
console.error(
|
|
17
|
-
|
|
17
|
+
'initializeSpa() was called without supplying a spaPath. This means that the application cannot properly generate urls.',
|
|
18
18
|
);
|
|
19
19
|
error = true;
|
|
20
20
|
}
|
|
21
21
|
|
|
22
22
|
if (error) {
|
|
23
23
|
throw new Error(
|
|
24
|
-
|
|
24
|
+
'One or more required properties in the basic configuration of the application was missing and the application cannot be rendered. Please see the browser console for details.',
|
|
25
25
|
);
|
|
26
26
|
}
|
|
27
27
|
|
|
28
28
|
window.openmrsBase = config.apiUrl;
|
|
29
29
|
window.spaBase = config.spaPath;
|
|
30
|
-
window.spaEnv = config.env ||
|
|
30
|
+
window.spaEnv = config.env || 'production';
|
|
31
31
|
window.spaVersion = process.env.BUILD_VERSION;
|
|
32
|
-
const spaBaseWithSlash = window.spaBase.endsWith(
|
|
33
|
-
? window.spaBase
|
|
34
|
-
: window.spaBase + "/";
|
|
32
|
+
const spaBaseWithSlash = window.spaBase.endsWith('/') ? window.spaBase : window.spaBase + '/';
|
|
35
33
|
window.getOpenmrsSpaBase = () => spaBaseWithSlash;
|
|
36
34
|
}
|
|
37
35
|
|
|
@@ -44,14 +42,14 @@ export function setupUtils() {
|
|
|
44
42
|
r.selectNode(source);
|
|
45
43
|
sel.removeAllRanges();
|
|
46
44
|
sel.addRange(r);
|
|
47
|
-
document.execCommand(
|
|
45
|
+
document.execCommand('copy');
|
|
48
46
|
sel.removeAllRanges();
|
|
49
47
|
}
|
|
50
48
|
};
|
|
51
49
|
}
|
|
52
50
|
|
|
53
51
|
function wireSpaPaths() {
|
|
54
|
-
const baseElement = document.createElement(
|
|
52
|
+
const baseElement = document.createElement('base');
|
|
55
53
|
const baseHref = window.getOpenmrsSpaBase();
|
|
56
54
|
baseElement.href = baseHref;
|
|
57
55
|
document.head.appendChild(baseElement);
|
|
@@ -66,9 +64,9 @@ function initializeSpa(config: SpaConfig) {
|
|
|
66
64
|
setupUtils();
|
|
67
65
|
setupPaths(config);
|
|
68
66
|
wireSpaPaths();
|
|
69
|
-
return Promise.resolve(__webpack_init_sharing__(
|
|
67
|
+
return Promise.resolve(__webpack_init_sharing__('default')).then(async () => {
|
|
70
68
|
const { configUrls = [], offline = true } = config;
|
|
71
|
-
const { run } = await import(
|
|
69
|
+
const { run } = await import('./run');
|
|
72
70
|
return run(configUrls, offline);
|
|
73
71
|
});
|
|
74
72
|
}
|
package/src/locale.ts
CHANGED
|
@@ -1,48 +1,43 @@
|
|
|
1
|
-
import * as i18next from
|
|
2
|
-
import LanguageDetector from
|
|
3
|
-
import { initReactI18next } from
|
|
4
|
-
import merge from
|
|
5
|
-
import {
|
|
6
|
-
getConfigInternal,
|
|
7
|
-
importDynamic,
|
|
8
|
-
} from "@openmrs/esm-framework/src/internal";
|
|
1
|
+
import * as i18next from 'i18next';
|
|
2
|
+
import LanguageDetector from 'i18next-browser-languagedetector';
|
|
3
|
+
import { initReactI18next } from 'react-i18next';
|
|
4
|
+
import merge from 'lodash-es/merge';
|
|
5
|
+
import { getConfigInternal, importDynamic } from '@openmrs/esm-framework/src/internal';
|
|
9
6
|
|
|
10
7
|
export function setupI18n() {
|
|
11
8
|
window.i18next = i18next.default || i18next;
|
|
12
9
|
|
|
13
10
|
const languageChangeObserver = new MutationObserver(() => {
|
|
14
11
|
const reDetect: any = undefined;
|
|
15
|
-
window.i18next
|
|
16
|
-
.changeLanguage(reDetect)
|
|
17
|
-
.catch((e) => console.error("i18next failed to re-detect language", e));
|
|
12
|
+
window.i18next.changeLanguage(reDetect).catch((e) => console.error('i18next failed to re-detect language', e));
|
|
18
13
|
});
|
|
19
14
|
|
|
20
15
|
languageChangeObserver.observe(document.documentElement, {
|
|
21
|
-
attributeFilter: [
|
|
16
|
+
attributeFilter: ['lang'],
|
|
22
17
|
attributes: true,
|
|
23
18
|
});
|
|
24
19
|
|
|
25
|
-
window.i18next.on(
|
|
26
|
-
document.documentElement.setAttribute(
|
|
20
|
+
window.i18next.on('languageChanged', () => {
|
|
21
|
+
document.documentElement.setAttribute('dir', window.i18next.dir());
|
|
27
22
|
});
|
|
28
23
|
|
|
29
24
|
return window.i18next
|
|
30
25
|
.use(LanguageDetector)
|
|
31
26
|
.use<i18next.BackendModule>({
|
|
32
|
-
type:
|
|
27
|
+
type: 'backend',
|
|
33
28
|
init() {},
|
|
34
29
|
read(language, namespace, callback) {
|
|
35
|
-
if (namespace ===
|
|
30
|
+
if (namespace === 'translation') {
|
|
36
31
|
callback(Error("can't handle translation namespace"), null);
|
|
37
32
|
} else if (namespace === undefined || language === undefined) {
|
|
38
33
|
callback(Error(), null);
|
|
39
|
-
} else if (namespace ===
|
|
34
|
+
} else if (namespace === '@openmrs/esm-app-shell') {
|
|
40
35
|
// currently, we don't have translations in the app shell
|
|
41
36
|
getConfigInternal(namespace)
|
|
42
37
|
.then((config) => {
|
|
43
38
|
let translations = {};
|
|
44
|
-
if (config &&
|
|
45
|
-
const overrides = config[
|
|
39
|
+
if (config && 'Translation overrides' in config) {
|
|
40
|
+
const overrides = config['Translation overrides'];
|
|
46
41
|
if (language in overrides) {
|
|
47
42
|
translations = overrides[language];
|
|
48
43
|
}
|
|
@@ -56,16 +51,13 @@ export function setupI18n() {
|
|
|
56
51
|
} else {
|
|
57
52
|
importDynamic(namespace)
|
|
58
53
|
.then((module) =>
|
|
59
|
-
Promise.all([
|
|
60
|
-
getImportPromise(module, namespace, language),
|
|
61
|
-
getConfigInternal(namespace),
|
|
62
|
-
])
|
|
54
|
+
Promise.all([getImportPromise(module, namespace, language), getConfigInternal(namespace)]),
|
|
63
55
|
)
|
|
64
56
|
.then(([json, config]) => {
|
|
65
57
|
let translations = json ?? {};
|
|
66
58
|
|
|
67
|
-
if (config &&
|
|
68
|
-
const overrides = config[
|
|
59
|
+
if (config && 'Translation overrides' in config) {
|
|
60
|
+
const overrides = config['Translation overrides'];
|
|
69
61
|
if (language in overrides) {
|
|
70
62
|
translations = merge(translations, overrides[language]);
|
|
71
63
|
}
|
|
@@ -82,10 +74,10 @@ export function setupI18n() {
|
|
|
82
74
|
.use(initReactI18next)
|
|
83
75
|
.init({
|
|
84
76
|
detection: {
|
|
85
|
-
order: [
|
|
86
|
-
lookupQuerystring:
|
|
77
|
+
order: ['querystring', 'htmlTag', 'localStorage', 'navigator'],
|
|
78
|
+
lookupQuerystring: 'lang',
|
|
87
79
|
},
|
|
88
|
-
fallbackLng:
|
|
80
|
+
fallbackLng: 'en',
|
|
89
81
|
});
|
|
90
82
|
}
|
|
91
83
|
|
|
@@ -94,19 +86,17 @@ function getImportPromise(
|
|
|
94
86
|
importTranslation: (language: string) => Promise<Record<string, string>>;
|
|
95
87
|
},
|
|
96
88
|
namespace: string,
|
|
97
|
-
language: string
|
|
89
|
+
language: string,
|
|
98
90
|
) {
|
|
99
|
-
if (typeof module.importTranslation !==
|
|
100
|
-
throw Error(
|
|
101
|
-
`Module ${namespace} does not export an importTranslation function`
|
|
102
|
-
);
|
|
91
|
+
if (typeof module.importTranslation !== 'function') {
|
|
92
|
+
throw Error(`Module ${namespace} does not export an importTranslation function`);
|
|
103
93
|
}
|
|
104
94
|
|
|
105
95
|
const importPromise = module.importTranslation(`./${language}.json`);
|
|
106
96
|
|
|
107
97
|
if (!(importPromise instanceof Promise)) {
|
|
108
98
|
throw Error(
|
|
109
|
-
`Module ${namespace} exports an importTranslation function that does not return a promise. Did you forget to set require.context mode to 'lazy'
|
|
99
|
+
`Module ${namespace} exports an importTranslation function that does not return a promise. Did you forget to set require.context mode to 'lazy'?`,
|
|
110
100
|
);
|
|
111
101
|
}
|
|
112
102
|
|