@modern-js/server 1.3.1-beta.0 → 1.4.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/CHANGELOG.md +68 -0
- package/dist/js/modern/dev-tools/babel/register.js +1 -0
- package/dist/js/modern/dev-tools/dev-server-plugin.js +1 -2
- package/dist/js/modern/dev-tools/mock/getMockData.js +24 -1
- package/dist/js/modern/dev-tools/mock/index.js +1 -26
- package/dist/js/modern/dev-tools/socket-server.js +4 -2
- package/dist/js/modern/dev-tools/watcher/index.js +4 -7
- package/dist/js/modern/dev-tools/watcher/stats-cache.js +32 -20
- package/dist/js/modern/libs/context/context.js +6 -0
- package/dist/js/modern/libs/hook-api/route.js +6 -4
- package/dist/js/modern/libs/render/index.js +1 -0
- package/dist/js/modern/libs/render/reader.js +1 -2
- package/dist/js/modern/libs/render/ssr.js +7 -2
- package/dist/js/modern/libs/route/index.js +0 -1
- package/dist/js/modern/libs/route/matcher.js +15 -3
- package/dist/js/modern/libs/route/route.js +1 -0
- package/dist/js/modern/server/dev-server/dev-server.js +3 -0
- package/dist/js/modern/server/index.js +5 -4
- package/dist/js/modern/server/modern-server-split.js +1 -1
- package/dist/js/modern/server/modern-server.js +13 -34
- package/dist/js/modern/utils.js +39 -0
- package/dist/js/node/dev-tools/babel/register.js +1 -0
- package/dist/js/node/dev-tools/dev-server-plugin.js +1 -2
- package/dist/js/node/dev-tools/mock/getMockData.js +29 -2
- package/dist/js/node/dev-tools/mock/index.js +5 -26
- package/dist/js/node/dev-tools/socket-server.js +4 -2
- package/dist/js/node/dev-tools/watcher/index.js +7 -5
- package/dist/js/node/dev-tools/watcher/stats-cache.js +33 -20
- package/dist/js/node/libs/context/context.js +6 -0
- package/dist/js/node/libs/hook-api/route.js +6 -4
- package/dist/js/node/libs/render/index.js +1 -0
- package/dist/js/node/libs/render/reader.js +2 -1
- package/dist/js/node/libs/render/ssr.js +8 -2
- package/dist/js/node/libs/route/index.js +0 -1
- package/dist/js/node/libs/route/matcher.js +16 -3
- package/dist/js/node/libs/route/route.js +1 -0
- package/dist/js/node/server/dev-server/dev-server.js +3 -0
- package/dist/js/node/server/index.js +9 -6
- package/dist/js/node/server/modern-server-split.js +1 -1
- package/dist/js/node/server/modern-server.js +12 -33
- package/dist/js/node/utils.js +51 -2
- package/dist/types/dev-tools/mock/getMockData.d.ts +2 -1
- package/dist/types/dev-tools/socket-server.d.ts +1 -2
- package/dist/types/dev-tools/watcher/index.d.ts +2 -1
- package/dist/types/dev-tools/watcher/stats-cache.d.ts +3 -2
- package/dist/types/libs/context/context.d.ts +2 -0
- package/dist/types/libs/hook-api/route.d.ts +3 -2
- package/dist/types/libs/render/reader.d.ts +13 -0
- package/dist/types/libs/render/ssr.d.ts +1 -0
- package/dist/types/libs/route/matcher.d.ts +1 -1
- package/dist/types/libs/route/route.d.ts +1 -0
- package/dist/types/server/dev-server/dev-server-split.d.ts +3 -3
- package/dist/types/server/modern-server-split.d.ts +3 -3
- package/dist/types/server/modern-server.d.ts +1 -2
- package/dist/types/type.d.ts +6 -4
- package/dist/types/utils.d.ts +5 -1
- package/package.json +13 -12
- package/tests/context.test.ts +12 -1
- package/tests/dev.test.ts +306 -7
- package/tests/fixtures/mock/exist/config/mock/index.ts +11 -0
- package/tests/fixtures/mock/zero/config/mock/index.ts +1 -0
- package/tests/fixtures/pure/tsconfig.json +0 -1
- package/tests/fixtures/reader/index.ts +3 -0
- package/tests/fixtures/route-spec/dynamic.json +13 -0
- package/tests/fixtures/ssr/bundle.js +5 -0
- package/tests/fixtures/static-dir/bar.html +11 -0
- package/tests/fixtures/static-dir/baz/index.html +11 -0
- package/tests/fixtures/static-dir/foo/index.html +11 -0
- package/tests/fixtures/watch/a.ts +3 -0
- package/tests/fixtures/watch/index.ts +5 -0
- package/tests/fixtures/watch/stats.txt +1 -0
- package/tests/hook.test.ts +1 -1
- package/tests/render.test.ts +102 -0
- package/tests/route.test.ts +26 -3
- package/tests/utils.test.ts +35 -0
- package/tests/watcher.test.ts +6 -4
- package/src/constants.ts +0 -26
- package/src/dev-tools/babel/register.ts +0 -37
- package/src/dev-tools/dev-server-plugin.ts +0 -48
- package/src/dev-tools/https/global.d.ts +0 -3
- package/src/dev-tools/https/index.ts +0 -12
- package/src/dev-tools/launch-editor/index.ts +0 -29
- package/src/dev-tools/mock/getMockData.ts +0 -109
- package/src/dev-tools/mock/index.ts +0 -63
- package/src/dev-tools/socket-server.ts +0 -192
- package/src/dev-tools/watcher/dependency-tree.ts +0 -94
- package/src/dev-tools/watcher/index.ts +0 -81
- package/src/dev-tools/watcher/stats-cache.ts +0 -53
- package/src/index.ts +0 -16
- package/src/libs/context/context.ts +0 -176
- package/src/libs/context/index.ts +0 -7
- package/src/libs/hook-api/route.ts +0 -38
- package/src/libs/hook-api/template.ts +0 -53
- package/src/libs/metrics.ts +0 -15
- package/src/libs/proxy.ts +0 -85
- package/src/libs/render/cache/__tests__/cache.fun.test.ts +0 -94
- package/src/libs/render/cache/__tests__/cache.test.ts +0 -240
- package/src/libs/render/cache/__tests__/cacheable.ts +0 -44
- package/src/libs/render/cache/__tests__/error-configuration.ts +0 -34
- package/src/libs/render/cache/__tests__/matched-cache.ts +0 -88
- package/src/libs/render/cache/index.ts +0 -75
- package/src/libs/render/cache/page-caches/index.ts +0 -11
- package/src/libs/render/cache/page-caches/lru.ts +0 -38
- package/src/libs/render/cache/spr.ts +0 -301
- package/src/libs/render/cache/type.ts +0 -59
- package/src/libs/render/cache/util.ts +0 -97
- package/src/libs/render/index.ts +0 -78
- package/src/libs/render/modern/browser-list.ts +0 -7
- package/src/libs/render/modern/index.ts +0 -41
- package/src/libs/render/modern/module.d.ts +0 -4
- package/src/libs/render/reader.ts +0 -119
- package/src/libs/render/ssr.ts +0 -62
- package/src/libs/render/static.ts +0 -52
- package/src/libs/render/type.ts +0 -38
- package/src/libs/route/index.ts +0 -77
- package/src/libs/route/matcher.ts +0 -93
- package/src/libs/route/route.ts +0 -32
- package/src/libs/serve-file.ts +0 -34
- package/src/server/dev-server/dev-server-split.ts +0 -41
- package/src/server/dev-server/dev-server.ts +0 -300
- package/src/server/dev-server/index.ts +0 -2
- package/src/server/index.ts +0 -163
- package/src/server/modern-server-split.ts +0 -97
- package/src/server/modern-server.ts +0 -636
- package/src/type.ts +0 -88
- package/src/utils.ts +0 -79
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,73 @@
|
|
|
1
1
|
# @modern-js/server
|
|
2
2
|
|
|
3
|
+
## 1.4.1
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- 2cfc4235: support cssPath/jsPath/mediaPath in production mode
|
|
8
|
+
- 8d55e234: fix: catch api error
|
|
9
|
+
- Updated dependencies [53aca274]
|
|
10
|
+
- Updated dependencies [78279953]
|
|
11
|
+
- Updated dependencies [e116ace5]
|
|
12
|
+
- Updated dependencies [4d72edea]
|
|
13
|
+
- @modern-js/core@1.4.1
|
|
14
|
+
- @modern-js/utils@1.3.1
|
|
15
|
+
|
|
16
|
+
## 1.4.0
|
|
17
|
+
|
|
18
|
+
### Minor Changes
|
|
19
|
+
|
|
20
|
+
- ec4dbffb: feat: support as a pure api service
|
|
21
|
+
|
|
22
|
+
### Patch Changes
|
|
23
|
+
|
|
24
|
+
- 816fd721: support more server context
|
|
25
|
+
- d9cc5ea9: support resatrt options transfer
|
|
26
|
+
- bfbea9a7: support multi base url and dynamic base url
|
|
27
|
+
- d099e5c5: fix error when modify modern.config.js
|
|
28
|
+
- 24f616ca: feat: support custom meta info
|
|
29
|
+
- 272cab15: refactor server plugin manager
|
|
30
|
+
- Updated dependencies [d9cc5ea9]
|
|
31
|
+
- Updated dependencies [bd819a8d]
|
|
32
|
+
- Updated dependencies [ec4dbffb]
|
|
33
|
+
- Updated dependencies [d099e5c5]
|
|
34
|
+
- Updated dependencies [bada2879]
|
|
35
|
+
- Updated dependencies [24f616ca]
|
|
36
|
+
- Updated dependencies [bd819a8d]
|
|
37
|
+
- Updated dependencies [272cab15]
|
|
38
|
+
- @modern-js/core@1.4.0
|
|
39
|
+
- @modern-js/utils@1.3.0
|
|
40
|
+
- @modern-js/server-core@1.2.2
|
|
41
|
+
|
|
42
|
+
## 1.3.2
|
|
43
|
+
|
|
44
|
+
### Patch Changes
|
|
45
|
+
|
|
46
|
+
- 83166714: change .npmignore
|
|
47
|
+
- Updated dependencies [83166714]
|
|
48
|
+
- Updated dependencies [c3de9882]
|
|
49
|
+
- Updated dependencies [33ff48af]
|
|
50
|
+
- @modern-js/core@1.3.2
|
|
51
|
+
- @modern-js/bff-utils@1.2.2
|
|
52
|
+
- @modern-js/hmr-client@1.2.1
|
|
53
|
+
- @modern-js/server-plugin@1.2.1
|
|
54
|
+
- @modern-js/server-utils@1.2.1
|
|
55
|
+
- @modern-js/utils@1.2.2
|
|
56
|
+
|
|
57
|
+
## 1.3.1
|
|
58
|
+
|
|
59
|
+
### Patch Changes
|
|
60
|
+
|
|
61
|
+
- e2d3a575: fix extending core config interface
|
|
62
|
+
- 823809c6: fix: hot reload not working on windows
|
|
63
|
+
- e2d3a575: fix extending core config interface
|
|
64
|
+
- Updated dependencies [823809c6]
|
|
65
|
+
- Updated dependencies [4584cc04]
|
|
66
|
+
- Updated dependencies [7c19fd94]
|
|
67
|
+
- @modern-js/bff-utils@1.2.1
|
|
68
|
+
- @modern-js/utils@1.2.1
|
|
69
|
+
- @modern-js/core@1.3.1
|
|
70
|
+
|
|
3
71
|
## 1.3.0
|
|
4
72
|
|
|
5
73
|
### Minor Changes
|
|
@@ -18,6 +18,7 @@ export const enableRegister = (projectRoot, config) => {
|
|
|
18
18
|
return require('@babel/register')(_objectSpread(_objectSpread({}, babelConfig), {}, {
|
|
19
19
|
only: [function (filePath) {
|
|
20
20
|
// TODO: wait params
|
|
21
|
+
// FIXME: 删除hardcode,根据 AppContext 中的 metaName 设置路径
|
|
21
22
|
if (filePath.includes(`node_modules${path.sep}.modern-js`)) {
|
|
22
23
|
return true;
|
|
23
24
|
}
|
|
@@ -14,8 +14,7 @@ export default class DevServerPlugin {
|
|
|
14
14
|
} = this;
|
|
15
15
|
const host = `&host=${options.client.host || 'localhost'}`;
|
|
16
16
|
const path = `&path=${options.client.path}`;
|
|
17
|
-
const port = `&port=${options.client.port}`;
|
|
18
|
-
|
|
17
|
+
const port = `&port=${options.client.port}`;
|
|
19
18
|
const clientEntry = `${require.resolve('@modern-js/hmr-client')}?${host}${path}${port}`;
|
|
20
19
|
|
|
21
20
|
const hotEntry = require.resolve('webpack/hot/dev-server');
|
|
@@ -5,6 +5,7 @@ function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { va
|
|
|
5
5
|
function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
|
|
6
6
|
|
|
7
7
|
import { compatRequire } from '@modern-js/utils';
|
|
8
|
+
import { match } from 'path-to-regexp';
|
|
8
9
|
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
9
10
|
const VALID_METHODS = ['get', 'post', 'put', 'delete', 'patch']; // eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
10
11
|
|
|
@@ -81,4 +82,26 @@ export default (filepath => {
|
|
|
81
82
|
|
|
82
83
|
const data = normalizeConfig(mockModule);
|
|
83
84
|
return data;
|
|
84
|
-
});
|
|
85
|
+
});
|
|
86
|
+
export const getMatched = (context, mockApiList) => {
|
|
87
|
+
const {
|
|
88
|
+
path: targetPathname,
|
|
89
|
+
method: targetMethod
|
|
90
|
+
} = context;
|
|
91
|
+
const matched = mockApiList.find(mockApi => {
|
|
92
|
+
const {
|
|
93
|
+
method,
|
|
94
|
+
path: pathname
|
|
95
|
+
} = mockApi;
|
|
96
|
+
|
|
97
|
+
if (method.toLowerCase() === targetMethod.toLowerCase()) {
|
|
98
|
+
return match(pathname, {
|
|
99
|
+
encode: encodeURI,
|
|
100
|
+
decode: decodeURIComponent
|
|
101
|
+
})(targetPathname);
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
return false;
|
|
105
|
+
});
|
|
106
|
+
return matched;
|
|
107
|
+
};
|
|
@@ -1,32 +1,7 @@
|
|
|
1
1
|
import path from 'path';
|
|
2
2
|
import { fs } from '@modern-js/utils';
|
|
3
|
-
import { match } from 'path-to-regexp';
|
|
4
3
|
import { AGGRED_DIR } from "../../constants";
|
|
5
|
-
import getMockData from "./getMockData";
|
|
6
|
-
|
|
7
|
-
const getMatched = (context, mockApiList) => {
|
|
8
|
-
const {
|
|
9
|
-
path: targetPathname,
|
|
10
|
-
method: targetMethod
|
|
11
|
-
} = context;
|
|
12
|
-
const matched = mockApiList.find(mockApi => {
|
|
13
|
-
const {
|
|
14
|
-
method,
|
|
15
|
-
path: pathname
|
|
16
|
-
} = mockApi;
|
|
17
|
-
|
|
18
|
-
if (method.toLowerCase() === targetMethod.toLowerCase()) {
|
|
19
|
-
return match(pathname, {
|
|
20
|
-
encode: encodeURI,
|
|
21
|
-
decode: decodeURIComponent
|
|
22
|
-
})(targetPathname);
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
return false;
|
|
26
|
-
});
|
|
27
|
-
return matched;
|
|
28
|
-
};
|
|
29
|
-
|
|
4
|
+
import getMockData, { getMatched } from "./getMockData";
|
|
30
5
|
export const createMockHandler = ({
|
|
31
6
|
pwd
|
|
32
7
|
}) => {
|
|
@@ -1,18 +1,17 @@
|
|
|
1
|
+
import path from 'path';
|
|
1
2
|
import chokidar from 'chokidar';
|
|
2
3
|
import { DependencyTree } from "./dependency-tree";
|
|
3
4
|
import { StatsCache } from "./stats-cache";
|
|
4
|
-
|
|
5
|
-
const getWatchedFiles = watcher => {
|
|
5
|
+
export const getWatchedFiles = watcher => {
|
|
6
6
|
const watched = watcher.getWatched();
|
|
7
7
|
const files = [];
|
|
8
8
|
Object.keys(watched).forEach(dir => {
|
|
9
9
|
watched[dir].forEach(fileName => {
|
|
10
|
-
files.push(
|
|
10
|
+
files.push(path.join(dir, fileName));
|
|
11
11
|
});
|
|
12
12
|
});
|
|
13
13
|
return files;
|
|
14
14
|
};
|
|
15
|
-
|
|
16
15
|
export default class Watcher {
|
|
17
16
|
constructor() {
|
|
18
17
|
this.dependencyTree = null;
|
|
@@ -21,9 +20,7 @@ export default class Watcher {
|
|
|
21
20
|
|
|
22
21
|
listen(files, options, callback) {
|
|
23
22
|
const watched = files.filter(Boolean);
|
|
24
|
-
const filenames = watched.map(filename => filename.replace(/\\/g, '/'));
|
|
25
|
-
|
|
26
|
-
console.log('watched files:', filenames);
|
|
23
|
+
const filenames = watched.map(filename => filename.replace(/\\/g, '/'));
|
|
27
24
|
const cache = new StatsCache();
|
|
28
25
|
const watcher = chokidar.watch(filenames, options);
|
|
29
26
|
watcher.on('ready', () => {
|
|
@@ -1,20 +1,24 @@
|
|
|
1
1
|
import fs from 'fs';
|
|
2
|
+
import crypto from 'crypto';
|
|
2
3
|
export class StatsCache {
|
|
3
4
|
constructor() {
|
|
4
|
-
this.
|
|
5
|
+
this.cachedHash = {};
|
|
6
|
+
this.cachedSize = {};
|
|
5
7
|
}
|
|
6
8
|
|
|
7
9
|
add(files) {
|
|
8
10
|
const {
|
|
9
|
-
|
|
11
|
+
cachedHash,
|
|
12
|
+
cachedSize
|
|
10
13
|
} = this;
|
|
11
14
|
|
|
12
15
|
for (const filename of files) {
|
|
13
16
|
if (fs.existsSync(filename)) {
|
|
14
|
-
const
|
|
17
|
+
const stats = fs.statSync(filename);
|
|
15
18
|
|
|
16
|
-
if (
|
|
17
|
-
|
|
19
|
+
if (stats.isFile() && !cachedHash[filename]) {
|
|
20
|
+
cachedHash[filename] = this.hash(stats, filename);
|
|
21
|
+
cachedSize[filename] = stats.size;
|
|
18
22
|
}
|
|
19
23
|
}
|
|
20
24
|
}
|
|
@@ -22,32 +26,41 @@ export class StatsCache {
|
|
|
22
26
|
|
|
23
27
|
refresh(filename) {
|
|
24
28
|
const {
|
|
25
|
-
|
|
29
|
+
cachedHash,
|
|
30
|
+
cachedSize
|
|
26
31
|
} = this;
|
|
27
32
|
|
|
28
33
|
if (fs.existsSync(filename)) {
|
|
29
|
-
const
|
|
34
|
+
const stats = fs.statSync(filename);
|
|
30
35
|
|
|
31
|
-
if (
|
|
32
|
-
|
|
36
|
+
if (stats.isFile()) {
|
|
37
|
+
cachedHash[filename] = this.hash(stats, filename);
|
|
38
|
+
cachedSize[filename] = stats.size;
|
|
33
39
|
}
|
|
34
40
|
}
|
|
35
41
|
}
|
|
36
42
|
|
|
37
43
|
del(filename) {
|
|
38
|
-
if (this.
|
|
39
|
-
delete this.
|
|
44
|
+
if (this.cachedHash[filename]) {
|
|
45
|
+
delete this.cachedHash[filename];
|
|
46
|
+
delete this.cachedSize[filename];
|
|
40
47
|
}
|
|
41
48
|
}
|
|
42
49
|
|
|
43
50
|
isDiff(filename) {
|
|
44
51
|
const {
|
|
45
|
-
|
|
52
|
+
cachedHash,
|
|
53
|
+
cachedSize
|
|
46
54
|
} = this;
|
|
47
|
-
const
|
|
48
|
-
const
|
|
55
|
+
const stats = fs.statSync(filename);
|
|
56
|
+
const hash = cachedHash[filename];
|
|
57
|
+
const size = cachedSize[filename];
|
|
49
58
|
|
|
50
|
-
if (
|
|
59
|
+
if (stats.size !== size) {
|
|
60
|
+
return true;
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
if (this.hash(stats, filename) !== hash) {
|
|
51
64
|
return true;
|
|
52
65
|
}
|
|
53
66
|
|
|
@@ -55,12 +68,11 @@ export class StatsCache {
|
|
|
55
68
|
}
|
|
56
69
|
|
|
57
70
|
has(filename) {
|
|
58
|
-
return Boolean(this.
|
|
59
|
-
}
|
|
60
|
-
|
|
71
|
+
return Boolean(this.cachedHash[filename]);
|
|
72
|
+
}
|
|
61
73
|
|
|
62
|
-
|
|
63
|
-
return
|
|
74
|
+
hash(stats, filename) {
|
|
75
|
+
return crypto.createHash('md5').update(fs.readFileSync(filename)).digest('hex');
|
|
64
76
|
}
|
|
65
77
|
|
|
66
78
|
}
|
|
@@ -19,10 +19,12 @@ export class ModernServerContext {
|
|
|
19
19
|
this.params = {};
|
|
20
20
|
this.logger = void 0;
|
|
21
21
|
this.metrics = void 0;
|
|
22
|
+
this.serverData = void 0;
|
|
22
23
|
this.req = req;
|
|
23
24
|
this.res = res;
|
|
24
25
|
this.logger = req.logger;
|
|
25
26
|
this.metrics = req.metrics;
|
|
27
|
+
this.serverData = {};
|
|
26
28
|
this.bind();
|
|
27
29
|
}
|
|
28
30
|
|
|
@@ -41,6 +43,10 @@ export class ModernServerContext {
|
|
|
41
43
|
this.params = params;
|
|
42
44
|
}
|
|
43
45
|
|
|
46
|
+
setServerData(key, value) {
|
|
47
|
+
this.serverData[key] = value;
|
|
48
|
+
}
|
|
49
|
+
|
|
44
50
|
getReqHeader(key) {
|
|
45
51
|
const {
|
|
46
52
|
req
|
|
@@ -1,13 +1,15 @@
|
|
|
1
1
|
class RouteAPI {
|
|
2
|
-
constructor(matched, router) {
|
|
2
|
+
constructor(matched, router, url) {
|
|
3
3
|
this.router = void 0;
|
|
4
4
|
this.current = void 0;
|
|
5
|
+
this.url = void 0;
|
|
5
6
|
this.current = matched;
|
|
6
7
|
this.router = router;
|
|
8
|
+
this.url = url;
|
|
7
9
|
}
|
|
8
10
|
|
|
9
11
|
cur() {
|
|
10
|
-
return this.current.generate();
|
|
12
|
+
return this.current.generate(this.url);
|
|
11
13
|
}
|
|
12
14
|
|
|
13
15
|
get(entryName) {
|
|
@@ -15,7 +17,7 @@ class RouteAPI {
|
|
|
15
17
|
router
|
|
16
18
|
} = this;
|
|
17
19
|
const matched = router.matchEntry(entryName);
|
|
18
|
-
return matched ? matched.generate() : null;
|
|
20
|
+
return matched ? matched.generate(this.url) : null;
|
|
19
21
|
}
|
|
20
22
|
|
|
21
23
|
use(entryName) {
|
|
@@ -34,4 +36,4 @@ class RouteAPI {
|
|
|
34
36
|
|
|
35
37
|
}
|
|
36
38
|
|
|
37
|
-
export const createRouteAPI = (matched, router) => new RouteAPI(matched, router);
|
|
39
|
+
export const createRouteAPI = (matched, router, url) => new RouteAPI(matched, router, url);
|
|
@@ -14,7 +14,7 @@ const createCacheItem = async (filepath, mtime) => {
|
|
|
14
14
|
};
|
|
15
15
|
};
|
|
16
16
|
|
|
17
|
-
class LruReader {
|
|
17
|
+
export class LruReader {
|
|
18
18
|
// private timer?: NodeJS.Timeout;
|
|
19
19
|
constructor() {
|
|
20
20
|
this.cache = void 0;
|
|
@@ -96,7 +96,6 @@ class LruReader {
|
|
|
96
96
|
|
|
97
97
|
|
|
98
98
|
}
|
|
99
|
-
|
|
100
99
|
const reader = new LruReader();
|
|
101
100
|
export const readFile = async filepath => {
|
|
102
101
|
const file = await reader.read(filepath);
|
|
@@ -1,9 +1,11 @@
|
|
|
1
1
|
import path from 'path';
|
|
2
2
|
import { SERVER_RENDER_FUNCTION_NAME } from '@modern-js/utils';
|
|
3
3
|
import mime from 'mime-types';
|
|
4
|
+
import cookie from 'cookie';
|
|
4
5
|
import cache from "./cache";
|
|
5
6
|
export const render = async (ctx, renderOptions, runner) => {
|
|
6
7
|
const {
|
|
8
|
+
urlPath,
|
|
7
9
|
bundle,
|
|
8
10
|
distDir,
|
|
9
11
|
template,
|
|
@@ -13,11 +15,14 @@ export const render = async (ctx, renderOptions, runner) => {
|
|
|
13
15
|
const bundleJS = path.join(distDir, bundle);
|
|
14
16
|
const context = {
|
|
15
17
|
request: {
|
|
18
|
+
baseUrl: urlPath,
|
|
16
19
|
params: ctx.params,
|
|
17
20
|
pathname: ctx.path,
|
|
21
|
+
host: ctx.host,
|
|
18
22
|
query: ctx.query,
|
|
19
|
-
|
|
20
|
-
|
|
23
|
+
url: ctx.href,
|
|
24
|
+
cookieMap: cookie.parse(ctx.headers.cookie || ''),
|
|
25
|
+
headers: ctx.headers
|
|
21
26
|
},
|
|
22
27
|
redirection: {},
|
|
23
28
|
template,
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { removeTailSlash } from '@modern-js/utils';
|
|
2
2
|
import { match, pathToRegexp } from 'path-to-regexp';
|
|
3
|
+
import { toPath } from "../../utils";
|
|
3
4
|
import { ModernRoute } from "./route"; // eslint-disable-next-line no-useless-escape
|
|
4
5
|
|
|
5
6
|
const regCharsDetector = /[^a-zA-Z\-_0-9\/\.]/;
|
|
@@ -14,8 +15,16 @@ export class RouteMatcher {
|
|
|
14
15
|
} // generate modern route object
|
|
15
16
|
|
|
16
17
|
|
|
17
|
-
generate() {
|
|
18
|
-
|
|
18
|
+
generate(url) {
|
|
19
|
+
const route = new ModernRoute(this.spec);
|
|
20
|
+
|
|
21
|
+
if (this.urlPath) {
|
|
22
|
+
const params = this.parseURLParams(url);
|
|
23
|
+
route.urlPath = toPath(route.urlPath, params);
|
|
24
|
+
route.params = params;
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
return route;
|
|
19
28
|
}
|
|
20
29
|
|
|
21
30
|
parseURLParams(pathname) {
|
|
@@ -73,9 +82,12 @@ export class RouteMatcher {
|
|
|
73
82
|
|
|
74
83
|
if (useReg) {
|
|
75
84
|
this.urlMatcher = match(urlPath, {
|
|
85
|
+
end: false,
|
|
76
86
|
decode: decodeURIComponent
|
|
77
87
|
});
|
|
78
|
-
this.urlReg = pathToRegexp(urlPath
|
|
88
|
+
this.urlReg = pathToRegexp(urlPath, [], {
|
|
89
|
+
end: false
|
|
90
|
+
});
|
|
79
91
|
}
|
|
80
92
|
}
|
|
81
93
|
|
|
@@ -118,6 +118,8 @@ export class ModernDevServer extends ModernServer {
|
|
|
118
118
|
}
|
|
119
119
|
|
|
120
120
|
async close() {
|
|
121
|
+
var _this$socketServer2;
|
|
122
|
+
|
|
121
123
|
super.close();
|
|
122
124
|
await this.watcher.close();
|
|
123
125
|
await new Promise(resolve => {
|
|
@@ -129,6 +131,7 @@ export class ModernDevServer extends ModernServer {
|
|
|
129
131
|
resolve();
|
|
130
132
|
}
|
|
131
133
|
});
|
|
134
|
+
(_this$socketServer2 = this.socketServer) === null || _this$socketServer2 === void 0 ? void 0 : _this$socketServer2.close();
|
|
132
135
|
}
|
|
133
136
|
|
|
134
137
|
async createHTTPServer(handler) {
|
|
@@ -5,9 +5,9 @@ function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { va
|
|
|
5
5
|
function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
|
|
6
6
|
|
|
7
7
|
import path from 'path';
|
|
8
|
-
import { serverManager } from '@modern-js/server-
|
|
9
|
-
import { logger as defaultLogger } from '@modern-js/utils';
|
|
10
|
-
import {
|
|
8
|
+
import { serverManager, AppContext, ConfigContext } from '@modern-js/server-core';
|
|
9
|
+
import { compatRequire, logger as defaultLogger } from '@modern-js/utils';
|
|
10
|
+
import { initAppContext, initAppDir, loadUserConfig } from '@modern-js/core';
|
|
11
11
|
import { metrics as defaultMetrics } from "../libs/metrics";
|
|
12
12
|
import { ModernServer } from "./modern-server";
|
|
13
13
|
import { ModernAPIServer, ModernSSRServer, ModernWebServer } from "./modern-server-split";
|
|
@@ -115,8 +115,9 @@ export class Server {
|
|
|
115
115
|
const {
|
|
116
116
|
options
|
|
117
117
|
} = this;
|
|
118
|
+
serverManager.clear();
|
|
118
119
|
(_options$plugins = options.plugins) === null || _options$plugins === void 0 ? void 0 : _options$plugins.forEach(p => {
|
|
119
|
-
serverManager.usePlugin(p);
|
|
120
|
+
serverManager.usePlugin(compatRequire(p.pluginPath));
|
|
120
121
|
});
|
|
121
122
|
const appContext = await this.initAppContext();
|
|
122
123
|
serverManager.run(() => {
|
|
@@ -21,7 +21,7 @@ import clone from 'lodash.clone';
|
|
|
21
21
|
import { RouteMatchManager } from "../libs/route";
|
|
22
22
|
import { createRenderHandler } from "../libs/render";
|
|
23
23
|
import { createStaticFileHandler } from "../libs/serve-file";
|
|
24
|
-
import { createErrorDocument, createMiddlewareCollecter, mergeExtension, noop } from "../utils";
|
|
24
|
+
import { createErrorDocument, createMiddlewareCollecter, getStaticReg, mergeExtension, noop } from "../utils";
|
|
25
25
|
import * as reader from "../libs/render/reader";
|
|
26
26
|
import { createProxyHandler } from "../libs/proxy";
|
|
27
27
|
import { createContext } from "../libs/context";
|
|
@@ -126,15 +126,10 @@ export class ModernServer {
|
|
|
126
126
|
this.warmupSSRBundle();
|
|
127
127
|
}
|
|
128
128
|
|
|
129
|
-
await this.prepareFrameHandler();
|
|
130
|
-
const {
|
|
131
|
-
favicon,
|
|
132
|
-
faviconByEntries
|
|
133
|
-
} = this.conf.output || {};
|
|
134
|
-
const favicons = this.prepareFavicons(favicon, faviconByEntries); // Only work when without setting `assetPrefix`.
|
|
129
|
+
await this.prepareFrameHandler(); // Only work when without setting `assetPrefix`.
|
|
135
130
|
// Setting `assetPrefix` means these resources should be uploaded to CDN.
|
|
136
131
|
|
|
137
|
-
const staticPathRegExp =
|
|
132
|
+
const staticPathRegExp = getStaticReg(this.conf.output || {});
|
|
138
133
|
this.staticFileHandler = createStaticFileHandler([{
|
|
139
134
|
path: staticPathRegExp,
|
|
140
135
|
target: distDir
|
|
@@ -353,7 +348,7 @@ export class ModernServer {
|
|
|
353
348
|
return;
|
|
354
349
|
}
|
|
355
350
|
|
|
356
|
-
const routeAPI = createRouteAPI(matched, this.router);
|
|
351
|
+
const routeAPI = createRouteAPI(matched, this.router, context.url);
|
|
357
352
|
await this.emitRouteHook('afterMatch', {
|
|
358
353
|
context,
|
|
359
354
|
routeAPI
|
|
@@ -366,12 +361,15 @@ export class ModernServer {
|
|
|
366
361
|
const {
|
|
367
362
|
current
|
|
368
363
|
} = routeAPI;
|
|
369
|
-
const route = current.generate();
|
|
370
|
-
|
|
371
|
-
context.
|
|
364
|
+
const route = current.generate(context.url);
|
|
365
|
+
context.setParams(route.params);
|
|
366
|
+
context.setServerData('router', {
|
|
367
|
+
baseUrl: route.urlPath,
|
|
368
|
+
params: route.params
|
|
369
|
+
}); // route is api service
|
|
372
370
|
|
|
373
371
|
if (route.isApi) {
|
|
374
|
-
this.handleAPI(context);
|
|
372
|
+
await this.handleAPI(context);
|
|
375
373
|
return;
|
|
376
374
|
}
|
|
377
375
|
|
|
@@ -413,6 +411,7 @@ export class ModernServer {
|
|
|
413
411
|
templateAPI
|
|
414
412
|
});
|
|
415
413
|
await this.injectMicroFE(context, templateAPI);
|
|
414
|
+
templateAPI.appendHead(`<script>window._SERVER_DATA=${JSON.stringify(context.serverData)}</script>`);
|
|
416
415
|
response = templateAPI.get();
|
|
417
416
|
}
|
|
418
417
|
|
|
@@ -555,7 +554,7 @@ export class ModernServer {
|
|
|
555
554
|
const matched = this.router.match(statusPage) || this.router.match(customErrorPage); // if no custom status page find
|
|
556
555
|
|
|
557
556
|
if (matched) {
|
|
558
|
-
const route = matched.generate();
|
|
557
|
+
const route = matched.generate(context.url);
|
|
559
558
|
const {
|
|
560
559
|
entryName
|
|
561
560
|
} = route; // check entryName, aviod matched '/' route
|
|
@@ -581,25 +580,5 @@ export class ModernServer {
|
|
|
581
580
|
res.end(createErrorDocument(status, text));
|
|
582
581
|
}
|
|
583
582
|
|
|
584
|
-
prepareFavicons(favicon, faviconByEntries) {
|
|
585
|
-
const faviconNames = [];
|
|
586
|
-
|
|
587
|
-
if (favicon) {
|
|
588
|
-
faviconNames.push(favicon.substring(favicon.lastIndexOf('/') + 1));
|
|
589
|
-
}
|
|
590
|
-
|
|
591
|
-
if (faviconByEntries) {
|
|
592
|
-
Object.keys(faviconByEntries).forEach(f => {
|
|
593
|
-
const curFavicon = faviconByEntries[f];
|
|
594
|
-
|
|
595
|
-
if (curFavicon) {
|
|
596
|
-
faviconNames.push(curFavicon.substring(curFavicon.lastIndexOf('/') + 1));
|
|
597
|
-
}
|
|
598
|
-
});
|
|
599
|
-
}
|
|
600
|
-
|
|
601
|
-
return faviconNames;
|
|
602
|
-
}
|
|
603
|
-
|
|
604
583
|
}
|
|
605
584
|
/* eslint-enable max-lines */
|
package/dist/js/modern/utils.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { compile } from 'path-to-regexp';
|
|
1
2
|
export const mergeExtension = users => {
|
|
2
3
|
const output = [];
|
|
3
4
|
return {
|
|
@@ -70,4 +71,42 @@ export const createMiddlewareCollecter = () => {
|
|
|
70
71
|
addWebMiddleware,
|
|
71
72
|
addAPIMiddleware
|
|
72
73
|
};
|
|
74
|
+
};
|
|
75
|
+
export const toPath = (reg, params) => {
|
|
76
|
+
const fn = compile(reg, {
|
|
77
|
+
encode: encodeURIComponent
|
|
78
|
+
});
|
|
79
|
+
return fn(params);
|
|
80
|
+
};
|
|
81
|
+
export const getStaticReg = (output = {}) => {
|
|
82
|
+
const {
|
|
83
|
+
favicon,
|
|
84
|
+
faviconByEntries,
|
|
85
|
+
cssPath,
|
|
86
|
+
jsPath,
|
|
87
|
+
mediaPath
|
|
88
|
+
} = output;
|
|
89
|
+
const favicons = prepareFavicons(favicon, faviconByEntries);
|
|
90
|
+
const staticFiles = [cssPath, jsPath, mediaPath].filter(v => Boolean(v));
|
|
91
|
+
const staticPathRegExp = new RegExp(`^/(static/|upload/|favicon.ico|icon.png${favicons.length > 0 ? `|${favicons.join('|')}` : ''}|${staticFiles.join('|')})`);
|
|
92
|
+
return staticPathRegExp;
|
|
93
|
+
};
|
|
94
|
+
export const prepareFavicons = (favicon, faviconByEntries) => {
|
|
95
|
+
const faviconNames = [];
|
|
96
|
+
|
|
97
|
+
if (favicon) {
|
|
98
|
+
faviconNames.push(favicon.substring(favicon.lastIndexOf('/') + 1));
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
if (faviconByEntries) {
|
|
102
|
+
Object.keys(faviconByEntries).forEach(f => {
|
|
103
|
+
const curFavicon = faviconByEntries[f];
|
|
104
|
+
|
|
105
|
+
if (curFavicon) {
|
|
106
|
+
faviconNames.push(curFavicon.substring(curFavicon.lastIndexOf('/') + 1));
|
|
107
|
+
}
|
|
108
|
+
});
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
return faviconNames;
|
|
73
112
|
};
|