@modern-js/main-doc 0.0.0-nightly-20231130170642 → 0.0.0-nightly-20231201170631

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.
@@ -0,0 +1,148 @@
1
+ ---
2
+ sidebar_position: 4
3
+ ---
4
+
5
+ # 热更新问题
6
+
7
+ ### 热更新不生效,如何排查?
8
+
9
+ 热更新不生效有很多种可能的原因,在这篇文档中会介绍大部分常见的原因,你可以参照以下内容进行排查。
10
+
11
+ 在开始排查之前,请简单了解一下热更新的原理:
12
+
13
+ :::tip 热更新原理
14
+
15
+ 1. 浏览器和开发服务器建立一个 Web Socket 连接,用于实时通信。
16
+ 2. 当开发服务器每次重新编译完成后,会通过 Web Socket 通知浏览器,浏览器向开发服务器发送 `hot-update.xxx` 请求,从而加载编译后的新模块。
17
+ 3. 当浏览器收到新的模块后,如果是 React 项目,则会通过 React 官方的 React Refresh 来更新 React 组件,其他框架也是类似。
18
+
19
+ :::
20
+
21
+ 了解完热更新的原理后,你可以按照以下步骤来进行基本的排查:
22
+
23
+ #### 1. 检查 Web Socket 连接
24
+
25
+ 打开浏览器的控制台,查看是否有 `[HMR] connected.` 日志。
26
+
27
+ - 如果有,说明 Web Socket 连接正常,请继续检查后续步骤。
28
+ - 如果没有,请打开 Chrome 的 Network 面板,查看 `ws://[host]:[port]/webpack-hmr` 的请求状态,若请求异常,说明热更新失败的原因是 Web Socket 请求没有建立成功。
29
+
30
+ Web Socket 请求没有建立成功的原因可能有很多种,例如开启了网络代理,导致 Web Socket 请求没有正确发送到开发服务器。你可以检查 Web Socket 请求的地址是否为你的开发服务器地址,如果不是,则可以通过 [tools.devServer.client](/configure/app/tools/dev-server.html#client) 来配置 Web Socket 请求的地址。
31
+
32
+ #### 2. 检查 hot-update 请求
33
+
34
+ 当你修改一个模块的代码,并触发重新编译后,浏览器会向开发服务器发送若干个 `hot-update.json` 和 `hot-update.js` 请求,用于获取更新后的代码。
35
+
36
+ 你可以尝试修改一个模块并检查 `hot-update.xxx` 请求的内容,如果请求的内容是最新的代码,说明热更新的请求正常。
37
+
38
+ 如果请求的内容错误,大概率也是由于开启了网络代理,请检查 `hot-update.xxx` 请求的地址是否为你的开发服务器地址,如果不是,则需要调整代理规则,将 `hot-update.xxx` 请求代理到开发服务器地址。
39
+
40
+ #### 3. 检查其他原因
41
+
42
+ 如果以上两个步骤都没有问题,那么可能是其他原因导致的热更新失败,比如没有符合 React 对热更新的要求,你可以参考下列的问题进行排查。
43
+
44
+ ---
45
+
46
+ ### 打包时 external React 后,热更新不生效?
47
+
48
+ 为了保证热更新生效,我们需要使用 React 和 ReactDOM 的开发环境产物。
49
+
50
+ 当你将 React 通过 externals 排除后,通常会通过 CDN 等方式注入 React 的生产环境产物,所以热更新会不生效。
51
+
52
+ ```js
53
+ export default {
54
+ output: {
55
+ externals: {
56
+ react: 'React',
57
+ 'react-dom': 'ReactDOM',
58
+ },
59
+ },
60
+ };
61
+ ```
62
+
63
+ 为了解决该问题,你需要引用 React 的开发环境产物,或者在开发环境下不配置 `externals`。
64
+
65
+ 如果你不确定当前使用的 React 产物类型,可以参考:[React 官方文档 - Use the Production Build](https://legacy.reactjs.org/docs/optimizing-performance.html#use-the-production-build)
66
+
67
+ ---
68
+
69
+ ### 开发环境设置文件名的 hash 后,热更新不生效?
70
+
71
+ 通常来说,我们只会在生产环境下设置文件名的 hash 值(即 `process.env.NODE_ENV === 'production'` 时)。
72
+
73
+ 如果你在开发环境下设置了文件名的 hash,那么可能会导致热更新不生效(尤其是 CSS 文件)。这是因为每次文件内容变化时,都会引起 hash 变化,导致 [mini-css-extract-plugin](https://www.npmjs.com/package/mini-css-extract-plugin) 等工具无法读取到最新的文件内容。
74
+
75
+ - 正确用法:
76
+
77
+ ```js
78
+ export default {
79
+ output: {
80
+ filename: {
81
+ css:
82
+ process.env.NODE_ENV === 'production'
83
+ ? '[name].[contenthash:8].css'
84
+ : '[name].css',
85
+ },
86
+ },
87
+ };
88
+ ```
89
+
90
+ - 错误用法:
91
+
92
+ ```js
93
+ export default {
94
+ output: {
95
+ filename: {
96
+ css: '[name].[contenthash:8].css',
97
+ },
98
+ },
99
+ };
100
+ ```
101
+
102
+ ---
103
+
104
+ ### React 组件的热更新无法生效?
105
+
106
+ Modern.js 使用 React 官方的 [Fast Refresh](https://github.com/pmmmwh/react-refresh-webpack-plugin) 能力来进行组件热更新。
107
+
108
+ 如果出现 React 组件的热更新无法生效的问题,或者是热更新后 React 组件的 state 丢失,这通常是因为你的 React 组件使用了匿名函数。在 React Fast Refresh 的官方实践中,要求组件不能为匿名函数,否则热更新后无法保留 React 组件的 state。
109
+
110
+ 以下是一些错误用法的例子:
111
+
112
+ ```tsx
113
+ // 错误写法 1
114
+ export default function () {
115
+ return <div>Hello World</div>;
116
+ }
117
+
118
+ // 错误写法 2
119
+ export default () => <div>Hello World</div>;
120
+ ```
121
+
122
+ 正确用法是给每个组件函数声明一个名称:
123
+
124
+ ```tsx
125
+ // 正确写法 1
126
+ export default function MyComponent() {
127
+ return <div>Hello World</div>;
128
+ }
129
+
130
+ // 正确写法 2
131
+ const MyComponent = () => <div>Hello World</div>;
132
+
133
+ export default MyComponent;
134
+ ```
135
+
136
+ ---
137
+
138
+ ### 开启 https 后,热更新不生效?
139
+
140
+ 当开启 https 时,由于证书的问题,可能会出现 HMR 连接失败的情况,此时打开控制台,会出现 HMR connect failed 的报错。
141
+
142
+ ![hmr-connect-error-0](https://lf3-static.bytednsdoc.com/obj/eden-cn/6221eh7uhbfvhn/modern/img_v2_2f90d027-a232-4bd8-8021-dac3c651682g.jpg)
143
+
144
+ 此问题的解决方法为:点击 Chrome 浏览器问题页面的「高级」->「继续前往 xxx(不安全)」。
145
+
146
+ ![hmr-connect-error-1](https://lf3-static.bytednsdoc.com/obj/eden-cn/6221eh7uhbfvhn/modern/59b37606-52ad-4886-a423-af2edaa49245.png)
147
+
148
+ > Tips: 当通过 Localhost 访问页面时,「您的连接不是私密连接」字样可能不会出现,可访问 Network 域名进行处理。
package/package.json CHANGED
@@ -15,17 +15,17 @@
15
15
  "modern",
16
16
  "modern.js"
17
17
  ],
18
- "version": "0.0.0-nightly-20231130170642",
18
+ "version": "0.0.0-nightly-20231201170631",
19
19
  "publishConfig": {
20
20
  "registry": "https://registry.npmjs.org/",
21
21
  "access": "public",
22
22
  "provenance": true
23
23
  },
24
24
  "dependencies": {
25
- "@modern-js/sandpack-react": "0.0.0-nightly-20231130170642"
25
+ "@modern-js/sandpack-react": "0.0.0-nightly-20231201170631"
26
26
  },
27
27
  "peerDependencies": {
28
- "@modern-js/builder-doc": "0.0.0-nightly-20231130170642"
28
+ "@modern-js/builder-doc": "0.0.0-nightly-20231201170631"
29
29
  },
30
30
  "devDependencies": {
31
31
  "classnames": "^2",
@@ -39,8 +39,8 @@
39
39
  "@rspress/shared": "1.7.4",
40
40
  "@types/node": "^16",
41
41
  "@types/fs-extra": "9.0.13",
42
- "@modern-js/builder-doc": "0.0.0-nightly-20231130170642",
43
- "@modern-js/doc-plugin-auto-sidebar": "0.0.0-nightly-20231130170642"
42
+ "@modern-js/builder-doc": "0.0.0-nightly-20231201170631",
43
+ "@modern-js/doc-plugin-auto-sidebar": "0.0.0-nightly-20231201170631"
44
44
  },
45
45
  "scripts": {
46
46
  "dev": "rspress dev",