metro-runtime 0.84.1 → 0.84.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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "metro-runtime",
3
- "version": "0.84.1",
3
+ "version": "0.84.3",
4
4
  "description": "🚇 Module required for evaluating Metro bundles.",
5
5
  "exports": {
6
6
  "./package.json": "./package.json",
@@ -1,6 +1,7 @@
1
1
  "use strict";
2
2
 
3
3
  const EventEmitter = require("./vendor/eventemitter3");
4
+ const HEARTBEAT_INTERVAL_MS = 20_000;
4
5
  const inject = ({ module: [id, code], sourceURL }) => {
5
6
  if (global.globalEvalWithSourceUrl) {
6
7
  global.globalEvalWithSourceUrl(code, sourceURL);
@@ -17,11 +18,13 @@ class HMRClient extends EventEmitter {
17
18
  _pendingUpdate = null;
18
19
  _queue = [];
19
20
  _state = "opening";
21
+ _heartbeatTimer = null;
20
22
  constructor(url) {
21
23
  super();
22
24
  this._ws = new global.WebSocket(url);
23
25
  this._ws.onopen = () => {
24
26
  this._state = "open";
27
+ this._startHeartbeat();
25
28
  this.emit("open");
26
29
  this._flushQueue();
27
30
  };
@@ -30,11 +33,14 @@ class HMRClient extends EventEmitter {
30
33
  };
31
34
  this._ws.onclose = (closeEvent) => {
32
35
  this._state = "closed";
36
+ this._stopHeartbeat();
33
37
  this.emit("close", closeEvent);
34
38
  };
35
39
  this._ws.onmessage = (message) => {
36
40
  const data = JSON.parse(String(message.data));
37
41
  switch (data.type) {
42
+ case "heartbeat":
43
+ break;
38
44
  case "bundle-registered":
39
45
  this.emit("bundle-registered");
40
46
  break;
@@ -45,7 +51,7 @@ class HMRClient extends EventEmitter {
45
51
  this.emit("update", data.body);
46
52
  break;
47
53
  case "update-done":
48
- this.emit("update-done");
54
+ this.emit("update-done", data.body);
49
55
  break;
50
56
  case "error":
51
57
  this.emit("error", data.body);
@@ -88,6 +94,20 @@ class HMRClient extends EventEmitter {
88
94
  this._queue.forEach((message) => this.send(message));
89
95
  this._queue.length = 0;
90
96
  }
97
+ _startHeartbeat() {
98
+ this._stopHeartbeat();
99
+ this._heartbeatTimer = setInterval(() => {
100
+ if (this._state === "open") {
101
+ this._ws.send('{"type":"heartbeat"}');
102
+ }
103
+ }, HEARTBEAT_INTERVAL_MS);
104
+ }
105
+ _stopHeartbeat() {
106
+ if (this._heartbeatTimer != null) {
107
+ clearInterval(this._heartbeatTimer);
108
+ this._heartbeatTimer = null;
109
+ }
110
+ }
91
111
  enable() {
92
112
  this._isEnabled = true;
93
113
  const update = this._pendingUpdate;
@@ -15,6 +15,8 @@ import type {HmrMessage, HmrUpdate} from './types';
15
15
 
16
16
  const EventEmitter = require('./vendor/eventemitter3');
17
17
 
18
+ const HEARTBEAT_INTERVAL_MS = 20_000;
19
+
18
20
  type SocketState = 'opening' | 'open' | 'closed';
19
21
 
20
22
  const inject = ({module: [id, code], sourceURL}: HmrModule) => {
@@ -39,6 +41,7 @@ class HMRClient extends EventEmitter {
39
41
  _queue: Array<string> = [];
40
42
  _state: SocketState = 'opening';
41
43
  _ws: WebSocket;
44
+ _heartbeatTimer: ?IntervalID = null;
42
45
 
43
46
  constructor(url: string) {
44
47
  super();
@@ -48,6 +51,7 @@ class HMRClient extends EventEmitter {
48
51
  this._ws = new global.WebSocket(url);
49
52
  this._ws.onopen = () => {
50
53
  this._state = 'open';
54
+ this._startHeartbeat();
51
55
  this.emit('open');
52
56
  this._flushQueue();
53
57
  };
@@ -56,12 +60,17 @@ class HMRClient extends EventEmitter {
56
60
  };
57
61
  this._ws.onclose = closeEvent => {
58
62
  this._state = 'closed';
63
+ this._stopHeartbeat();
59
64
  this.emit('close', closeEvent);
60
65
  };
61
66
  this._ws.onmessage = message => {
62
67
  const data: HmrMessage = JSON.parse(String(message.data));
63
68
 
64
69
  switch (data.type) {
70
+ case 'heartbeat':
71
+ // Not exposed to consumers
72
+ break;
73
+
65
74
  case 'bundle-registered':
66
75
  this.emit('bundle-registered');
67
76
  break;
@@ -75,7 +84,7 @@ class HMRClient extends EventEmitter {
75
84
  break;
76
85
 
77
86
  case 'update-done':
78
- this.emit('update-done');
87
+ this.emit('update-done', data.body);
79
88
  break;
80
89
 
81
90
  case 'error':
@@ -123,6 +132,22 @@ class HMRClient extends EventEmitter {
123
132
  this._queue.length = 0;
124
133
  }
125
134
 
135
+ _startHeartbeat(): void {
136
+ this._stopHeartbeat();
137
+ this._heartbeatTimer = setInterval(() => {
138
+ if (this._state === 'open') {
139
+ this._ws.send('{"type":"heartbeat"}');
140
+ }
141
+ }, HEARTBEAT_INTERVAL_MS);
142
+ }
143
+
144
+ _stopHeartbeat(): void {
145
+ if (this._heartbeatTimer != null) {
146
+ clearInterval(this._heartbeatTimer);
147
+ this._heartbeatTimer = null;
148
+ }
149
+ }
150
+
126
151
  enable() {
127
152
  this._isEnabled = true;
128
153
  const update = this._pendingUpdate;
@@ -0,0 +1,104 @@
1
+ /**
2
+ * Copyright (c) Meta Platforms, Inc. and affiliates.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ *
7
+ * @noformat
8
+ * @oncall react_native
9
+ * @generated SignedSource<<117ae8d35a498c8c16f22a36d6ee14ef>>
10
+ *
11
+ * This file was translated from Flow by scripts/generateTypeScriptDefinitions.js
12
+ * Original file: packages/metro-runtime/src/modules/types.js
13
+ * To regenerate, run:
14
+ * js1 build metro-ts-defs (internal) OR
15
+ * yarn run build-ts-defs (OSS)
16
+ */
17
+
18
+ export type ModuleMap = ReadonlyArray<[number, string]>;
19
+ export type Bundle = {
20
+ readonly modules: ModuleMap;
21
+ readonly post: string;
22
+ readonly pre: string;
23
+ };
24
+ export type DeltaBundle = {
25
+ readonly added: ModuleMap;
26
+ readonly modified: ModuleMap;
27
+ readonly deleted: ReadonlyArray<number>;
28
+ };
29
+ export type BundleVariant =
30
+ | Readonly<
31
+ Omit<Bundle, keyof {base: true; revisionId: string}> & {
32
+ base: true;
33
+ revisionId: string;
34
+ }
35
+ >
36
+ | Readonly<
37
+ Omit<DeltaBundle, keyof {base: false; revisionId: string}> & {
38
+ base: false;
39
+ revisionId: string;
40
+ }
41
+ >;
42
+ export type BundleMetadata = {
43
+ readonly pre: number;
44
+ readonly post: number;
45
+ readonly modules: ReadonlyArray<[number, number]>;
46
+ };
47
+ export type FormattedError = {
48
+ readonly type: string;
49
+ readonly message: string;
50
+ readonly errors: Array<{description: string}>;
51
+ };
52
+ export type HmrModule = {
53
+ readonly module: [number, string];
54
+ readonly sourceMappingURL: string;
55
+ readonly sourceURL: string;
56
+ };
57
+ export type HmrUpdate = {
58
+ readonly added: ReadonlyArray<HmrModule>;
59
+ readonly deleted: ReadonlyArray<number>;
60
+ readonly isInitialUpdate: boolean;
61
+ readonly modified: ReadonlyArray<HmrModule>;
62
+ readonly revisionId: string;
63
+ };
64
+ export type HmrUpdateMessage = {
65
+ readonly type: 'update';
66
+ readonly body: HmrUpdate;
67
+ };
68
+ export type HmrErrorMessage = {
69
+ readonly type: 'error';
70
+ readonly body: FormattedError;
71
+ };
72
+ export type HmrClientMessage =
73
+ | {
74
+ readonly type: 'register-entrypoints';
75
+ readonly entryPoints: Array<string>;
76
+ }
77
+ | {
78
+ readonly type: 'log';
79
+ readonly level:
80
+ | 'trace'
81
+ | 'info'
82
+ | 'warn'
83
+ | 'log'
84
+ | 'group'
85
+ | 'groupCollapsed'
86
+ | 'groupEnd'
87
+ | 'debug';
88
+ readonly data: Array<unknown>;
89
+ }
90
+ | {readonly type: 'log-opt-in'}
91
+ | {readonly type: 'heartbeat'};
92
+ export type HmrMessage =
93
+ | {readonly type: 'bundle-registered'}
94
+ | {
95
+ readonly type: 'update-start';
96
+ readonly body: {readonly isInitialUpdate: boolean};
97
+ }
98
+ | {
99
+ readonly type: 'update-done';
100
+ readonly body?: {readonly changeId?: string};
101
+ }
102
+ | HmrUpdateMessage
103
+ | HmrErrorMessage
104
+ | {readonly type: 'heartbeat'};
@@ -83,6 +83,9 @@ export type HmrClientMessage =
83
83
  }
84
84
  | {
85
85
  +type: 'log-opt-in',
86
+ }
87
+ | {
88
+ +type: 'heartbeat',
86
89
  };
87
90
 
88
91
  export type HmrMessage =
@@ -97,6 +100,10 @@ export type HmrMessage =
97
100
  }
98
101
  | {
99
102
  +type: 'update-done',
103
+ +body?: {+changeId?: string},
100
104
  }
101
105
  | HmrUpdateMessage
102
- | HmrErrorMessage;
106
+ | HmrErrorMessage
107
+ | {
108
+ +type: 'heartbeat',
109
+ };