miaoda-expo-devkit 0.1.1-dev.development-build.2 → 0.1.1-dev.development-build.3
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/README.md
CHANGED
|
@@ -173,13 +173,13 @@ Web 注入内容包括:
|
|
|
173
173
|
### Development Build 批量编辑控制
|
|
174
174
|
|
|
175
175
|
启用 `EXPO_MIAODA_HMR_CONTROL=1` 后,Agent 可通过 POST
|
|
176
|
-
`/
|
|
177
|
-
客户端每 2 秒通过 GET `
|
|
176
|
+
`/_hmr/off` 暂停更新,完成文件写入后调用 `/_hmr/on` 恢复;
|
|
177
|
+
客户端每 2 秒通过 GET `/_hmr/status` 校验状态,补偿 `/hot` WebSocket 断连。
|
|
178
178
|
服务端等待客户端暂停确认,并在恢复前同步文件监听队列、编译最终增量;WebSocket 保持
|
|
179
179
|
连接,用户 Fast Refresh 偏好独立保留。断线期间漏掉控制消息时,客户端会完整加载最终
|
|
180
180
|
Bundle,避免使用失效的增量 revision。最终编译失败会返回 `422` 并继续保持暂停。
|
|
181
181
|
|
|
182
|
-
普通恢复执行 Fast Refresh
|
|
182
|
+
普通恢复执行 Fast Refresh;`/_hmr/reload` 执行完整 Bundle 重载,若当前暂停则延迟到
|
|
183
183
|
恢复时执行。协议、返回值、版本要求和加载边界见 [Metro HMR 批量编辑控制](../../docs/metro-hmr-control.md)。
|
|
184
184
|
|
|
185
185
|
### Metro 编译错误采集
|
package/package.json
CHANGED
|
@@ -354,10 +354,10 @@ index bd1d604..02db474 100644
|
|
|
354
354
|
hmrServer,
|
|
355
355
|
diff --git a/build/src/start/server/metro/miaodaHmrControl.js b/build/src/start/server/metro/miaodaHmrControl.js
|
|
356
356
|
new file mode 100644
|
|
357
|
-
index 0000000..
|
|
357
|
+
index 0000000..6466921
|
|
358
358
|
--- /dev/null
|
|
359
359
|
+++ b/build/src/start/server/metro/miaodaHmrControl.js
|
|
360
|
-
@@ -0,0 +1,
|
|
360
|
+
@@ -0,0 +1,328 @@
|
|
361
361
|
+"use strict";
|
|
362
362
|
+
|
|
363
363
|
+// Miaoda HMR 批量编辑控制,适配 SDK 55 / Metro 0.83.3。
|
|
@@ -372,7 +372,7 @@ index 0000000..8d5d129
|
|
|
372
372
|
+// reload / error)。pause 携带 `id`,客户端在运行时停止应用更新后回复
|
|
373
373
|
+// {type: 'miaoda-hmr-ack', version: 1, id},因此 pause 成功即意味着
|
|
374
374
|
+// 不会再有在途更新落到设备上。
|
|
375
|
-
+// - 客户端每 2 秒轮询 GET
|
|
375
|
+
+// - 客户端每 2 秒轮询 GET /_hmr/status,作为 WebSocket 消息丢失时的兜底。
|
|
376
376
|
+// 每次状态变化都会递增 `stateVersion`;轮询方若发现一个从未通过 socket
|
|
377
377
|
+// 收到的版本号,则执行完整 Bundle reload 而不是 resume,因为此时已无法
|
|
378
378
|
+// 证明增量 revision 的连续性。
|
|
@@ -386,11 +386,13 @@ index 0000000..8d5d129
|
|
|
386
386
|
+const fs = require('node:fs');
|
|
387
387
|
+const path = require('node:path');
|
|
388
388
|
+const CONTROL = 'miaoda-hmr-control';
|
|
389
|
+
+// 控制接口直接挂在 Metro 根路径(/_hmr/*),不带内部 API 前缀:端侧裸轮询
|
|
390
|
+
+// 请求不携带平台凭证,带 /innerapi 类前缀的路径可能被路由层权限拦截。
|
|
389
391
|
+const ROUTES = new Map([
|
|
390
|
-
+ ['/
|
|
391
|
-
+ ['/
|
|
392
|
-
+ ['/
|
|
393
|
-
+ ['/
|
|
392
|
+
+ ['/_hmr/off', 'pause'],
|
|
393
|
+
+ ['/_hmr/on', 'resume'],
|
|
394
|
+
+ ['/_hmr/reload', 'reload'],
|
|
395
|
+
+ ['/_hmr/status', 'status'],
|
|
394
396
|
+]);
|
|
395
397
|
+
|
|
396
398
|
+function attachMiaodaHmrControl({hmrServer: hmr, metro, middleware, stateFile, timeout = 5000}) {
|
|
@@ -608,7 +610,7 @@ index 0000000..8d5d129
|
|
|
608
610
|
+ // 把最终错误告知客户端(设备端可以据此行动),但保持闸门关闭,
|
|
609
611
|
+ // 让 Agent 修好代码后重试。
|
|
610
612
|
+ for (const info of clients.values()) control(info, 'error', {error: compileErrors[0].body});
|
|
611
|
-
+ fail(422, 'Final code failed to compile; HMR remains paused. Fix the code and retry
|
|
613
|
+
+ fail(422, 'Final code failed to compile; HMR remains paused. Fix the code and retry /_hmr/on.');
|
|
612
614
|
+ }
|
|
613
615
|
+ const reload = reloadPending || errors.some(result => staleGraph(result.body)) || [...clients.values()].some(info => info.buffer.some(message => {
|
|
614
616
|
+ const data = JSON.parse(String(message));
|
|
@@ -21,7 +21,7 @@ index e2b8941..355deae 100644
|
|
|
21
21
|
"jest-expo": "~55.0.9",
|
|
22
22
|
"lottie-react-native": "~7.3.4",
|
|
23
23
|
diff --git a/src/async-require/hmr.ts b/src/async-require/hmr.ts
|
|
24
|
-
index c0ea71e..
|
|
24
|
+
index c0ea71e..be9cb40 100644
|
|
25
25
|
--- a/src/async-require/hmr.ts
|
|
26
26
|
+++ b/src/async-require/hmr.ts
|
|
27
27
|
@@ -17,6 +17,7 @@ import {
|
|
@@ -71,7 +71,7 @@ index c0ea71e..953cf53 100644
|
|
|
71
71
|
const pendingLogs: [LogLevel, any[]][] = [];
|
|
72
72
|
|
|
73
73
|
type LogLevel =
|
|
74
|
-
@@ -42,6 +75,
|
|
74
|
+
@@ -42,6 +75,102 @@ type LogLevel =
|
|
75
75
|
| 'groupEnd'
|
|
76
76
|
| 'debug';
|
|
77
77
|
|
|
@@ -87,7 +87,9 @@ index c0ea71e..953cf53 100644
|
|
|
87
87
|
+}
|
|
88
88
|
+
|
|
89
89
|
+function miaodaStatusUrl(protocol: MiaodaStatusProtocol) {
|
|
90
|
-
+
|
|
90
|
+
+ // 控制接口直接挂在 Metro 根路径(/_hmr/*):端侧裸轮询请求不携带平台凭证,
|
|
91
|
+
+ // 带内部 API 前缀的路径可能被路由层权限拦截。
|
|
92
|
+
+ return `${protocol}://${miaodaStatusHost}/_hmr/status`;
|
|
91
93
|
+}
|
|
92
94
|
+
|
|
93
95
|
+function alternateMiaodaStatusProtocol(protocol: MiaodaStatusProtocol): MiaodaStatusProtocol {
|
|
@@ -172,7 +174,7 @@ index c0ea71e..953cf53 100644
|
|
|
172
174
|
function assert(foo: any, msg: string): asserts foo {
|
|
173
175
|
if (!foo) throw new Error(msg);
|
|
174
176
|
}
|
|
175
|
-
@@ -52,6 +
|
|
177
|
+
@@ -52,6 +181,9 @@ function assert(foo: any, msg: string): asserts foo {
|
|
176
178
|
*/
|
|
177
179
|
const HMRClient = {
|
|
178
180
|
enable() {
|
|
@@ -182,7 +184,7 @@ index c0ea71e..953cf53 100644
|
|
|
182
184
|
if (hmrUnavailableReason !== null) {
|
|
183
185
|
// If HMR became unavailable while you weren't using it,
|
|
184
186
|
// explain why when you try to turn it on.
|
|
185
|
-
@@ -87,6 +
|
|
187
|
+
@@ -87,6 +219,7 @@ const HMRClient = {
|
|
186
188
|
},
|
|
187
189
|
|
|
188
190
|
disable() {
|
|
@@ -190,7 +192,7 @@ index c0ea71e..953cf53 100644
|
|
|
190
192
|
assert(hmrClient, 'Expected HMRClient.setup() call at startup.');
|
|
191
193
|
hmrClient.disable();
|
|
192
194
|
},
|
|
193
|
-
@@ -180,6 +
|
|
195
|
+
@@ -180,6 +313,13 @@ const HMRClient = {
|
|
194
196
|
const origin = `${serverScheme}://${serverHost}`;
|
|
195
197
|
const client = new MetroHMRClient(`${origin}/hot`);
|
|
196
198
|
hmrClient = client;
|
|
@@ -204,7 +206,7 @@ index c0ea71e..953cf53 100644
|
|
|
204
206
|
|
|
205
207
|
pendingEntryPoints.push(
|
|
206
208
|
// HMRServer understands regular bundle URLs, so prefer that in case
|
|
207
|
-
@@ -193,6 +
|
|
209
|
+
@@ -193,6 +333,55 @@ const HMRClient = {
|
|
208
210
|
})
|
|
209
211
|
);
|
|
210
212
|
|
|
@@ -260,7 +262,7 @@ index c0ea71e..953cf53 100644
|
|
|
260
262
|
client.on('connection-error', (e: Error) => {
|
|
261
263
|
setHMRUnavailableReason(getConnectionError(serverHost, e));
|
|
262
264
|
});
|
|
263
|
-
@@ -234,6 +
|
|
265
|
+
@@ -234,6 +423,10 @@ const HMRClient = {
|
|
264
266
|
client.on('error', (data) => this._onMetroError(data));
|
|
265
267
|
|
|
266
268
|
client.on('close', (closeEvent?: { code: number; reason: string }) => {
|
|
@@ -271,7 +273,7 @@ index c0ea71e..953cf53 100644
|
|
|
271
273
|
hideLoading();
|
|
272
274
|
const reason = closeEvent?.reason;
|
|
273
275
|
const code = closeEvent?.code || 1000;
|
|
274
|
-
@@ -326,6 +
|
|
276
|
+
@@ -326,6 +519,9 @@ function registerBundleEntryPoints(client: MetroHMRClient | null) {
|
|
275
277
|
client?.send(
|
|
276
278
|
JSON.stringify({
|
|
277
279
|
type: 'register-entrypoints',
|
package/pnpmfile.cjs
CHANGED
|
@@ -18,6 +18,7 @@ const managedPatches = {
|
|
|
18
18
|
[EXPO_CLI_PATCH_SELECTOR]: {
|
|
19
19
|
filename: '@expo__cli@55.0.16-55.0.22.patch',
|
|
20
20
|
legacyHashes: new Set([
|
|
21
|
+
'29f03d7d2633dad8e8ff99815c38a4f4059e46a235a5e66c508125975d920385',
|
|
21
22
|
'98c96a6bae56f47c0a47efe9a68e7a6751022d812b569b68d03b93753635c32c',
|
|
22
23
|
'9a0d662675fba8088396c6cdbab7d36d81fbe9acb3727144a50826ff3500b093',
|
|
23
24
|
]),
|
|
@@ -49,6 +50,7 @@ const managedPatches = {
|
|
|
49
50
|
'expo@55.0.6': {
|
|
50
51
|
filename: 'expo@55.0.6.patch',
|
|
51
52
|
legacyHashes: new Set([
|
|
53
|
+
'1df9b522728e93daf64f9e2298ab835ce52d55b4aa2de92a68b947e7ed08f40a',
|
|
52
54
|
'8ac63998a9852ddafda7af96deb4d7ac4c3a5da5e65e865af32be9d4fd966e02',
|
|
53
55
|
'12efbb4c64bc67744a838cc5d9d88604ad2a99cdd578a5cfab31b8d1c2be1144',
|
|
54
56
|
'd2507f55976f6c5da8f35d26906f4bd46415e042570afc3bd7c543c86abc5a61',
|