@tramvai/module-child-app 4.9.0 → 4.10.1
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/lib/browser/loader.browser.js +13 -1
- package/lib/browser/loader.d.ts +1 -0
- package/lib/browser/preload.browser.js +15 -9
- package/lib/browser/providers.browser.js +15 -4
- package/lib/browser/runCommand.browser.js +8 -2
- package/lib/browser/runCommand.d.ts +3 -1
- package/lib/server/loader.d.ts +1 -0
- package/lib/server/loader.es.js +3 -0
- package/lib/server/loader.js +3 -0
- package/lib/server/providers.es.js +9 -2
- package/lib/server/providers.js +9 -2
- package/lib/server/render-slots.es.js +6 -1
- package/lib/server/render-slots.js +6 -1
- package/lib/shared/loader.d.ts +1 -0
- package/package.json +12 -12
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { loadModule } from '@tinkoff/module-loader-client';
|
|
1
|
+
import { loadModule, waitModule } from '@tinkoff/module-loader-client';
|
|
2
2
|
import { Loader } from '../shared/loader.browser.js';
|
|
3
3
|
import { initModuleFederation, getModuleFederation } from '../shared/webpack/moduleFederation.browser.js';
|
|
4
4
|
|
|
@@ -52,6 +52,10 @@ class BrowserLoader extends Loader {
|
|
|
52
52
|
async init(config) {
|
|
53
53
|
const container = getModuleFromGlobal(config.client.entry);
|
|
54
54
|
if (container) {
|
|
55
|
+
this.log.debug({
|
|
56
|
+
event: 'init',
|
|
57
|
+
moduleName: config.name,
|
|
58
|
+
});
|
|
55
59
|
await initModuleFederation(container);
|
|
56
60
|
const factory = (await getModuleFederation(container, 'entry'));
|
|
57
61
|
const entry = factory();
|
|
@@ -63,6 +67,14 @@ class BrowserLoader extends Loader {
|
|
|
63
67
|
const entry = container && this.initializedMap.get(container);
|
|
64
68
|
return entry && this.resolve(entry);
|
|
65
69
|
}
|
|
70
|
+
async waitFor(config) {
|
|
71
|
+
this.log.debug({
|
|
72
|
+
event: 'wait-for',
|
|
73
|
+
moduleName: config.name,
|
|
74
|
+
});
|
|
75
|
+
// wait for entry chunk
|
|
76
|
+
await waitModule(config.client.entry);
|
|
77
|
+
}
|
|
66
78
|
}
|
|
67
79
|
|
|
68
80
|
export { BrowserLoader, getModuleFromGlobal };
|
package/lib/browser/loader.d.ts
CHANGED
|
@@ -13,5 +13,6 @@ export declare class BrowserLoader extends Loader {
|
|
|
13
13
|
load(config: ChildAppFinalConfig): Promise<ChildApp | void>;
|
|
14
14
|
init(config: ChildAppFinalConfig): Promise<void>;
|
|
15
15
|
get(config: ChildAppFinalConfig): ChildApp | void;
|
|
16
|
+
waitFor(config: ChildAppFinalConfig): Promise<void>;
|
|
16
17
|
}
|
|
17
18
|
//# sourceMappingURL=loader.d.ts.map
|
|
@@ -77,13 +77,24 @@ class PreloadManager {
|
|
|
77
77
|
const promises = [];
|
|
78
78
|
this.currentlyPreloaded.forEach((config) => {
|
|
79
79
|
promises.push((async () => {
|
|
80
|
+
// double check that preloaded Child App entry chunk is already loaded on the client.
|
|
81
|
+
// in streaming mode with async scripts it may not be loaded yet, and we need to wait this script.
|
|
82
|
+
// we don't need to load this script, because for server preloaded Child Apps it already been in HTML,
|
|
83
|
+
// for not preloaded Child Apps we don't want to delay hydration
|
|
84
|
+
if (!getModuleFromGlobal(config.client.entry)) {
|
|
85
|
+
// TODO: current test cases work with `loader.load`, need to be sure that new `loader.waitFor` method is necessary
|
|
86
|
+
await this.loader.waitFor(config).catch((e) => {
|
|
87
|
+
// it is expected case if entry chunk is not existed or failed
|
|
88
|
+
});
|
|
89
|
+
}
|
|
90
|
+
// if entry chunk is already loaded, here other Child App chunks will be waited or loaded
|
|
80
91
|
await this.loader.init(config);
|
|
81
92
|
// case for client initialization of Child App
|
|
82
93
|
await this.resolveComponent(config);
|
|
83
94
|
await this.run('customer', config);
|
|
84
95
|
})());
|
|
85
96
|
});
|
|
86
|
-
await Promise.
|
|
97
|
+
await Promise.allSettled(promises);
|
|
87
98
|
}
|
|
88
99
|
pageRender() {
|
|
89
100
|
this.pageHasRendered = true;
|
|
@@ -112,13 +123,8 @@ class PreloadManager {
|
|
|
112
123
|
preloaded.forEach((request) => {
|
|
113
124
|
const config = this.resolveExternalConfig(request);
|
|
114
125
|
if (config) {
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
// and we will run client initialization flow for this Child App, like it was not preloaded
|
|
118
|
-
if (getModuleFromGlobal(config.client.entry)) {
|
|
119
|
-
this.currentlyPreloaded.set(config.key, config);
|
|
120
|
-
this.hasPreloadBefore.add(config.key);
|
|
121
|
-
}
|
|
126
|
+
this.currentlyPreloaded.set(config.key, config);
|
|
127
|
+
this.hasPreloadBefore.add(config.key);
|
|
122
128
|
}
|
|
123
129
|
});
|
|
124
130
|
this.hasInitialized = true;
|
|
@@ -126,7 +132,7 @@ class PreloadManager {
|
|
|
126
132
|
}
|
|
127
133
|
async init() {
|
|
128
134
|
await this.resolutionConfigManager.init();
|
|
129
|
-
this.initServerPreloaded();
|
|
135
|
+
await this.initServerPreloaded();
|
|
130
136
|
}
|
|
131
137
|
async run(status, config) {
|
|
132
138
|
const childApp = this.loader.get(config);
|
|
@@ -48,17 +48,24 @@ const browserProviders = [
|
|
|
48
48
|
provide({
|
|
49
49
|
provide: commandLineListTokens.resolvePageDeps,
|
|
50
50
|
multi: true,
|
|
51
|
-
useFactory: ({ preloader }) => {
|
|
51
|
+
useFactory: ({ preloader, logger }) => {
|
|
52
52
|
let isSpaNavigation = false;
|
|
53
53
|
return function childAppRunPreloaded() {
|
|
54
54
|
if (isSpaNavigation)
|
|
55
55
|
return;
|
|
56
56
|
isSpaNavigation = true;
|
|
57
|
-
return preloader.runPreloaded()
|
|
57
|
+
return preloader.runPreloaded().catch((error) => {
|
|
58
|
+
const log = logger('child-app:run-preloaded');
|
|
59
|
+
log.error({
|
|
60
|
+
event: 'client-failed',
|
|
61
|
+
error,
|
|
62
|
+
});
|
|
63
|
+
});
|
|
58
64
|
};
|
|
59
65
|
},
|
|
60
66
|
deps: {
|
|
61
67
|
preloader: CHILD_APP_PRELOAD_MANAGER_TOKEN,
|
|
68
|
+
logger: LOGGER_TOKEN,
|
|
62
69
|
},
|
|
63
70
|
}),
|
|
64
71
|
provide({
|
|
@@ -78,7 +85,7 @@ const browserProviders = [
|
|
|
78
85
|
provide({
|
|
79
86
|
provide: commandLineListTokens.spaTransition,
|
|
80
87
|
multi: true,
|
|
81
|
-
useFactory: ({ preloader, runner, diManager, pageService }) => {
|
|
88
|
+
useFactory: ({ preloader, runner, diManager, pageService, logger }) => {
|
|
82
89
|
return async function childAppRunPreloaded() {
|
|
83
90
|
await runCommand({
|
|
84
91
|
preloader,
|
|
@@ -87,6 +94,7 @@ const browserProviders = [
|
|
|
87
94
|
pageService,
|
|
88
95
|
status: 'spa',
|
|
89
96
|
forcePreload: false,
|
|
97
|
+
logger,
|
|
90
98
|
});
|
|
91
99
|
};
|
|
92
100
|
},
|
|
@@ -95,12 +103,13 @@ const browserProviders = [
|
|
|
95
103
|
runner: CHILD_APP_COMMAND_LINE_RUNNER_TOKEN,
|
|
96
104
|
diManager: CHILD_APP_DI_MANAGER_TOKEN,
|
|
97
105
|
pageService: PAGE_SERVICE_TOKEN,
|
|
106
|
+
logger: LOGGER_TOKEN,
|
|
98
107
|
},
|
|
99
108
|
}),
|
|
100
109
|
provide({
|
|
101
110
|
provide: commandLineListTokens.afterSpaTransition,
|
|
102
111
|
multi: true,
|
|
103
|
-
useFactory: ({ preloader, runner, diManager, pageService }) => {
|
|
112
|
+
useFactory: ({ preloader, runner, diManager, pageService, logger }) => {
|
|
104
113
|
return async function childAppRunPreloaded() {
|
|
105
114
|
await runCommand({
|
|
106
115
|
preloader,
|
|
@@ -109,6 +118,7 @@ const browserProviders = [
|
|
|
109
118
|
pageService,
|
|
110
119
|
status: 'afterSpa',
|
|
111
120
|
forcePreload: true,
|
|
121
|
+
logger,
|
|
112
122
|
});
|
|
113
123
|
};
|
|
114
124
|
},
|
|
@@ -117,6 +127,7 @@ const browserProviders = [
|
|
|
117
127
|
runner: CHILD_APP_COMMAND_LINE_RUNNER_TOKEN,
|
|
118
128
|
diManager: CHILD_APP_DI_MANAGER_TOKEN,
|
|
119
129
|
pageService: PAGE_SERVICE_TOKEN,
|
|
130
|
+
logger: LOGGER_TOKEN,
|
|
120
131
|
},
|
|
121
132
|
}),
|
|
122
133
|
];
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
const runCommand = async ({ status, forcePreload, runner, preloader, diManager, pageService, }) => {
|
|
1
|
+
const runCommand = async ({ status, forcePreload, runner, preloader, diManager, pageService, logger, }) => {
|
|
2
2
|
const childApps = preloader.getPreloadedList();
|
|
3
3
|
await Promise.all(childApps.map(async (config) => {
|
|
4
4
|
if (forcePreload) {
|
|
@@ -6,7 +6,13 @@ const runCommand = async ({ status, forcePreload, runner, preloader, diManager,
|
|
|
6
6
|
await preloader.preload(config, pageService.getCurrentRoute());
|
|
7
7
|
}
|
|
8
8
|
return runner.run('client', status, config);
|
|
9
|
-
}))
|
|
9
|
+
})).catch((error) => {
|
|
10
|
+
const log = logger('child-app:run-preloaded');
|
|
11
|
+
log.error({
|
|
12
|
+
event: 'spa-failed',
|
|
13
|
+
error,
|
|
14
|
+
});
|
|
15
|
+
});
|
|
10
16
|
};
|
|
11
17
|
|
|
12
18
|
export { runCommand };
|
|
@@ -1,12 +1,14 @@
|
|
|
1
1
|
import type { CHILD_APP_DI_MANAGER_TOKEN } from '@tramvai/tokens-child-app';
|
|
2
2
|
import { type CHILD_APP_COMMAND_LINE_RUNNER_TOKEN, type CHILD_APP_PRELOAD_MANAGER_TOKEN } from '@tramvai/tokens-child-app';
|
|
3
|
+
import type { LOGGER_TOKEN } from '@tramvai/tokens-common';
|
|
3
4
|
import type { PAGE_SERVICE_TOKEN } from '@tramvai/tokens-router';
|
|
4
|
-
export declare const runCommand: ({ status, forcePreload, runner, preloader, diManager, pageService, }: {
|
|
5
|
+
export declare const runCommand: ({ status, forcePreload, runner, preloader, diManager, pageService, logger, }: {
|
|
5
6
|
status: string;
|
|
6
7
|
forcePreload: boolean;
|
|
7
8
|
runner: typeof CHILD_APP_COMMAND_LINE_RUNNER_TOKEN;
|
|
8
9
|
preloader: typeof CHILD_APP_PRELOAD_MANAGER_TOKEN;
|
|
9
10
|
diManager: typeof CHILD_APP_DI_MANAGER_TOKEN;
|
|
10
11
|
pageService: typeof PAGE_SERVICE_TOKEN;
|
|
12
|
+
logger: typeof LOGGER_TOKEN;
|
|
11
13
|
}) => Promise<void>;
|
|
12
14
|
//# sourceMappingURL=runCommand.d.ts.map
|
package/lib/server/loader.d.ts
CHANGED
|
@@ -18,5 +18,6 @@ export declare class ServerLoader extends Loader {
|
|
|
18
18
|
get(config: ChildAppFinalConfig): ChildApp | void;
|
|
19
19
|
getStats(config: ChildAppFinalConfig): ModuleFederationStats | void;
|
|
20
20
|
getLoadableStats(config: ChildAppFinalConfig): LoadableStats | void;
|
|
21
|
+
waitFor(): Promise<void>;
|
|
21
22
|
}
|
|
22
23
|
//# sourceMappingURL=loader.d.ts.map
|
package/lib/server/loader.es.js
CHANGED
package/lib/server/loader.js
CHANGED
|
@@ -98,6 +98,9 @@ class ServerLoader extends loader.Loader {
|
|
|
98
98
|
}
|
|
99
99
|
return this.loader.getByUrl(config.client.statsLoadable);
|
|
100
100
|
}
|
|
101
|
+
async waitFor() {
|
|
102
|
+
throw Error('Method "waitFor" is not implemented for server loader');
|
|
103
|
+
}
|
|
101
104
|
}
|
|
102
105
|
|
|
103
106
|
exports.ServerLoader = ServerLoader;
|
|
@@ -110,13 +110,20 @@ const serverProviders = [
|
|
|
110
110
|
provide({
|
|
111
111
|
provide: commandLineListTokens.resolvePageDeps,
|
|
112
112
|
multi: true,
|
|
113
|
-
useFactory: ({ preloader }) => {
|
|
113
|
+
useFactory: ({ preloader, logger }) => {
|
|
114
114
|
return function childAppRunPreloaded() {
|
|
115
|
-
return preloader.runPreloaded()
|
|
115
|
+
return preloader.runPreloaded().catch((error) => {
|
|
116
|
+
const log = logger('child-app:run-preloaded');
|
|
117
|
+
log.error({
|
|
118
|
+
event: 'server-failed',
|
|
119
|
+
error,
|
|
120
|
+
});
|
|
121
|
+
});
|
|
116
122
|
};
|
|
117
123
|
},
|
|
118
124
|
deps: {
|
|
119
125
|
preloader: CHILD_APP_PRELOAD_MANAGER_TOKEN,
|
|
126
|
+
logger: LOGGER_TOKEN,
|
|
120
127
|
},
|
|
121
128
|
}),
|
|
122
129
|
provide({
|
package/lib/server/providers.js
CHANGED
|
@@ -114,13 +114,20 @@ const serverProviders = [
|
|
|
114
114
|
core.provide({
|
|
115
115
|
provide: core.commandLineListTokens.resolvePageDeps,
|
|
116
116
|
multi: true,
|
|
117
|
-
useFactory: ({ preloader }) => {
|
|
117
|
+
useFactory: ({ preloader, logger }) => {
|
|
118
118
|
return function childAppRunPreloaded() {
|
|
119
|
-
return preloader.runPreloaded()
|
|
119
|
+
return preloader.runPreloaded().catch((error) => {
|
|
120
|
+
const log = logger('child-app:run-preloaded');
|
|
121
|
+
log.error({
|
|
122
|
+
event: 'server-failed',
|
|
123
|
+
error,
|
|
124
|
+
});
|
|
125
|
+
});
|
|
120
126
|
};
|
|
121
127
|
},
|
|
122
128
|
deps: {
|
|
123
129
|
preloader: tokensChildApp.CHILD_APP_PRELOAD_MANAGER_TOKEN,
|
|
130
|
+
logger: tokensCommon.LOGGER_TOKEN,
|
|
124
131
|
},
|
|
125
132
|
}),
|
|
126
133
|
core.provide({
|
|
@@ -20,6 +20,11 @@ const entryAttrs = {
|
|
|
20
20
|
onload: `this.setAttribute('loaded', 'true')`,
|
|
21
21
|
onerror: `this.setAttribute('loaded', 'false')`,
|
|
22
22
|
};
|
|
23
|
+
// for cases when preloaded chunk loading is failed before webpack add this script loading handlers,
|
|
24
|
+
// we need to remove script and webpack will try to load it itself https://github.com/webpack/webpack/issues/14874
|
|
25
|
+
const chunkAttrs = {
|
|
26
|
+
onerror: `this.remove()`,
|
|
27
|
+
};
|
|
23
28
|
const registerChildAppRenderSlots = ({ logger, diManager, resolveFullConfig, preloadManager, loader, renderMode, resourcesRegistry, }) => async () => {
|
|
24
29
|
const log = logger('child-app:render:slots');
|
|
25
30
|
const result = [];
|
|
@@ -41,7 +46,7 @@ const registerChildAppRenderSlots = ({ logger, diManager, resolveFullConfig, pre
|
|
|
41
46
|
attrs: {
|
|
42
47
|
'data-critical': 'true',
|
|
43
48
|
...scriptTypeAttr,
|
|
44
|
-
...(isEntry ? entryAttrs :
|
|
49
|
+
...(isEntry ? entryAttrs : chunkAttrs),
|
|
45
50
|
},
|
|
46
51
|
});
|
|
47
52
|
break;
|
|
@@ -28,6 +28,11 @@ const entryAttrs = {
|
|
|
28
28
|
onload: `this.setAttribute('loaded', 'true')`,
|
|
29
29
|
onerror: `this.setAttribute('loaded', 'false')`,
|
|
30
30
|
};
|
|
31
|
+
// for cases when preloaded chunk loading is failed before webpack add this script loading handlers,
|
|
32
|
+
// we need to remove script and webpack will try to load it itself https://github.com/webpack/webpack/issues/14874
|
|
33
|
+
const chunkAttrs = {
|
|
34
|
+
onerror: `this.remove()`,
|
|
35
|
+
};
|
|
31
36
|
const registerChildAppRenderSlots = ({ logger, diManager, resolveFullConfig, preloadManager, loader, renderMode, resourcesRegistry, }) => async () => {
|
|
32
37
|
const log = logger('child-app:render:slots');
|
|
33
38
|
const result = [];
|
|
@@ -49,7 +54,7 @@ const registerChildAppRenderSlots = ({ logger, diManager, resolveFullConfig, pre
|
|
|
49
54
|
attrs: {
|
|
50
55
|
'data-critical': 'true',
|
|
51
56
|
...scriptTypeAttr,
|
|
52
|
-
...(isEntry ? entryAttrs :
|
|
57
|
+
...(isEntry ? entryAttrs : chunkAttrs),
|
|
53
58
|
},
|
|
54
59
|
});
|
|
55
60
|
break;
|
package/lib/shared/loader.d.ts
CHANGED
|
@@ -5,6 +5,7 @@ export declare abstract class Loader implements ChildAppLoader {
|
|
|
5
5
|
abstract get(config: ChildAppFinalConfig): ChildApp | void;
|
|
6
6
|
abstract load(config: ChildAppFinalConfig): Promise<ChildApp | void>;
|
|
7
7
|
abstract init(config: ChildAppFinalConfig): Promise<void>;
|
|
8
|
+
abstract waitFor(config: ChildAppFinalConfig): Promise<void>;
|
|
8
9
|
protected resolve(entry: ChildAppModuleWrapper): ChildApp;
|
|
9
10
|
}
|
|
10
11
|
//# sourceMappingURL=loader.d.ts.map
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@tramvai/module-child-app",
|
|
3
|
-
"version": "4.
|
|
3
|
+
"version": "4.10.1",
|
|
4
4
|
"description": "Module for child apps",
|
|
5
5
|
"browser": {
|
|
6
6
|
"./lib/server.js": "./lib/browser.js",
|
|
@@ -31,25 +31,25 @@
|
|
|
31
31
|
"dependencies": {
|
|
32
32
|
"@loadable/server": "^5.15.0",
|
|
33
33
|
"@tinkoff/env-validators": "0.3.1",
|
|
34
|
-
"@tinkoff/module-loader-client": "0.6.
|
|
34
|
+
"@tinkoff/module-loader-client": "0.6.3",
|
|
35
35
|
"@tinkoff/module-loader-server": "0.7.1",
|
|
36
|
-
"@tramvai/module-common": "4.
|
|
36
|
+
"@tramvai/module-common": "4.10.1",
|
|
37
37
|
"@tinkoff/url": "0.10.1",
|
|
38
|
-
"@tramvai/child-app-core": "4.
|
|
38
|
+
"@tramvai/child-app-core": "4.10.1",
|
|
39
39
|
"@tramvai/safe-strings": "0.7.1",
|
|
40
|
-
"@tramvai/tokens-child-app": "4.
|
|
40
|
+
"@tramvai/tokens-child-app": "4.10.1"
|
|
41
41
|
},
|
|
42
42
|
"devDependencies": {},
|
|
43
43
|
"peerDependencies": {
|
|
44
44
|
"@tinkoff/dippy": "0.10.2",
|
|
45
|
-
"@tinkoff/router": "0.4.
|
|
45
|
+
"@tinkoff/router": "0.4.34",
|
|
46
46
|
"@tinkoff/utils": "^2.1.2",
|
|
47
|
-
"@tramvai/core": "4.
|
|
48
|
-
"@tramvai/state": "4.
|
|
49
|
-
"@tramvai/react": "4.
|
|
50
|
-
"@tramvai/tokens-common": "4.
|
|
51
|
-
"@tramvai/tokens-render": "4.
|
|
52
|
-
"@tramvai/tokens-router": "4.
|
|
47
|
+
"@tramvai/core": "4.10.1",
|
|
48
|
+
"@tramvai/state": "4.10.1",
|
|
49
|
+
"@tramvai/react": "4.10.1",
|
|
50
|
+
"@tramvai/tokens-common": "4.10.1",
|
|
51
|
+
"@tramvai/tokens-render": "4.10.1",
|
|
52
|
+
"@tramvai/tokens-router": "4.10.1",
|
|
53
53
|
"react": ">=16.14.0",
|
|
54
54
|
"react-dom": ">=16.14.0",
|
|
55
55
|
"object-assign": "^4.1.1",
|