nx 20.2.0-beta.1 → 20.2.0-beta.3

Sign up to get free protection for your applications and to get access to all the features.
@@ -1 +1 @@
1
- "use strict";(self.webpackChunk=self.webpackChunk||[]).push([[532],{71970:()=>{}},s=>{var e;e=71970,s(s.s=e)}]);
1
+ "use strict";(self.webpackChunk=self.webpackChunk||[]).push([[532],{94357:()=>{}},s=>{var e;e=94357,s(s.s=e)}]);
@@ -406,6 +406,9 @@ class DaemonClient {
406
406
  }
407
407
  }
408
408
  async startInBackground() {
409
+ if (global.NX_PLUGIN_WORKER) {
410
+ throw new Error('Fatal Error: Something unexpected has occurred. Plugin Workers should not start a new daemon process. Please report this issue.');
411
+ }
409
412
  (0, node_fs_1.mkdirSync)(tmp_dir_1.DAEMON_DIR_FOR_CURRENT_WORKSPACE, { recursive: true });
410
413
  if (!(0, node_fs_1.existsSync)(tmp_dir_1.DAEMON_OUTPUT_LOG_FILE)) {
411
414
  (0, node_fs_1.writeFileSync)(tmp_dir_1.DAEMON_OUTPUT_LOG_FILE, '');
@@ -353,6 +353,15 @@ async function startServer() {
353
353
  server.listen((0, socket_utils_1.getFullOsSocketPath)(), async () => {
354
354
  try {
355
355
  logger_1.serverLogger.log(`Started listening on: ${(0, socket_utils_1.getFullOsSocketPath)()}`);
356
+ setInterval(() => {
357
+ if ((0, cache_1.getDaemonProcessIdSync)() !== process.pid) {
358
+ return (0, shutdown_utils_1.handleServerProcessTermination)({
359
+ server,
360
+ reason: 'this process is no longer the current daemon (native)',
361
+ sockets: exports.openSockets,
362
+ });
363
+ }
364
+ }).unref();
356
365
  // this triggers the storage of the lock file hash
357
366
  daemonIsOutdated();
358
367
  if (!(0, shutdown_utils_1.getWatcherInstance)()) {
@@ -43,7 +43,7 @@ function isDaemonDisabled() {
43
43
  function socketDirName() {
44
44
  const hasher = (0, crypto_1.createHash)('sha256');
45
45
  hasher.update(workspace_root_1.workspaceRoot.toLowerCase());
46
- const unique = hasher.digest('hex').substring(0, 10);
46
+ const unique = hasher.digest('hex').substring(0, 20);
47
47
  return (0, path_1.join)(tmp_1.tmpdir, unique);
48
48
  }
49
49
  /**
Binary file
@@ -12,7 +12,15 @@ const pluginNames = new Map();
12
12
  const PLUGIN_TIMEOUT_HINT_TEXT = 'As a last resort, you can set NX_PLUGIN_NO_TIMEOUTS=true to bypass this timeout.';
13
13
  const MINUTES = 10;
14
14
  const MAX_MESSAGE_WAIT = process.env.NX_PLUGIN_NO_TIMEOUTS === 'true'
15
- ? undefined
15
+ ? // Registering a timeout prevents the process from exiting
16
+ // if the call to a plugin happens to be the only thing
17
+ // keeping the process alive. As such, even if timeouts are disabled
18
+ // we need to register one. 2147483647 is the max timeout
19
+ // that Node.js allows, and is equivalent to 24.8 days....
20
+ // This does mean that the NX_PLUGIN_NO_TIMEOUTS env var
21
+ // would still timeout after 24.8 days, but that seems
22
+ // like a reasonable compromise.
23
+ 2147483647
16
24
  : 1000 * 60 * MINUTES; // 10 minutes
17
25
  const nxPluginWorkerCache = (global['nxPluginWorkerCache'] ??= new Map());
18
26
  async function loadRemoteNxPlugin(plugin, root) {
@@ -35,11 +43,9 @@ async function loadRemoteNxPlugin(plugin, root) {
35
43
  payload: { plugin, root },
36
44
  });
37
45
  // logger.verbose(`[plugin-worker] started worker: ${worker.pid}`);
38
- const loadTimeout = MAX_MESSAGE_WAIT
39
- ? setTimeout(() => {
40
- rej(new Error(`Loading "${plugin}" timed out after ${MINUTES} minutes. ${PLUGIN_TIMEOUT_HINT_TEXT}`));
41
- }, MAX_MESSAGE_WAIT)
42
- : undefined;
46
+ const loadTimeout = setTimeout(() => {
47
+ rej(new Error(`Loading "${typeof plugin === 'string' ? plugin : plugin.plugin}" timed out after ${MINUTES} minutes. ${PLUGIN_TIMEOUT_HINT_TEXT}`));
48
+ }, MAX_MESSAGE_WAIT);
43
49
  socket.on('data', (0, consume_messages_from_socket_1.consumeMessagesFromSocket)(createWorkerHandler(worker, pendingPromises, (val) => {
44
50
  if (loadTimeout)
45
51
  clearTimeout(loadTimeout);
@@ -169,11 +175,9 @@ function registerPendingPromise(tx, pending, callback, context) {
169
175
  const promise = new Promise((res, rej) => {
170
176
  rejector = rej;
171
177
  resolver = res;
172
- timeout = MAX_MESSAGE_WAIT
173
- ? setTimeout(() => {
174
- rej(new Error(`${context.plugin} timed out after ${MINUTES} minutes during ${context.operation}. ${PLUGIN_TIMEOUT_HINT_TEXT}`));
175
- }, MAX_MESSAGE_WAIT)
176
- : undefined;
178
+ timeout = setTimeout(() => {
179
+ rej(new Error(`${context.plugin} timed out after ${MINUTES} minutes during ${context.operation}. ${PLUGIN_TIMEOUT_HINT_TEXT}`));
180
+ }, MAX_MESSAGE_WAIT);
177
181
  callback();
178
182
  }).finally(() => {
179
183
  pending.delete(tx);
@@ -10,9 +10,19 @@ if (process.env.NX_PERF_LOGGING === 'true') {
10
10
  require('../../../utils/perf-logging');
11
11
  }
12
12
  global.NX_GRAPH_CREATION = true;
13
+ global.NX_PLUGIN_WORKER = true;
14
+ let connected = false;
13
15
  let plugin;
14
16
  const socketPath = process.argv[2];
15
17
  const server = (0, net_1.createServer)((socket) => {
18
+ connected = true;
19
+ // This handles cases where the host process was killed
20
+ // after the worker connected but before the worker was
21
+ // instructed to load the plugin.
22
+ const loadTimeout = setTimeout(() => {
23
+ console.error(`Plugin Worker exited because no plugin was loaded within 10 seconds of starting up.`);
24
+ process.exit(1);
25
+ }, 10000).unref();
16
26
  socket.on('data', (0, consume_messages_from_socket_1.consumeMessagesFromSocket)((raw) => {
17
27
  const message = JSON.parse(raw.toString());
18
28
  if (!(0, messaging_1.isPluginWorkerMessage)(message)) {
@@ -20,6 +30,8 @@ const server = (0, net_1.createServer)((socket) => {
20
30
  }
21
31
  return (0, messaging_1.consumeMessage)(socket, message, {
22
32
  load: async ({ plugin: pluginConfiguration, root }) => {
33
+ if (loadTimeout)
34
+ clearTimeout(loadTimeout);
23
35
  process.chdir(root);
24
36
  try {
25
37
  const [promise] = (0, loader_1.loadNxPlugin)(pluginConfiguration, root);
@@ -112,6 +124,8 @@ const server = (0, net_1.createServer)((socket) => {
112
124
  // since the worker is spawned per host process. As such,
113
125
  // we can safely close the worker when the host disconnects.
114
126
  socket.on('end', () => {
127
+ // Destroys the socket once it's fully closed.
128
+ socket.destroySoon();
115
129
  // Stops accepting new connections, but existing connections are
116
130
  // not closed immediately.
117
131
  server.close(() => {
@@ -121,11 +135,15 @@ const server = (0, net_1.createServer)((socket) => {
121
135
  catch (e) { }
122
136
  process.exit(0);
123
137
  });
124
- // Destroys the socket once it's fully closed.
125
- socket.destroySoon();
126
138
  });
127
139
  });
128
140
  server.listen(socketPath);
141
+ setTimeout(() => {
142
+ if (!connected) {
143
+ console.error('The plugin worker is exiting as it was not connected to within 5 seconds.');
144
+ process.exit(1);
145
+ }
146
+ }, 5000).unref();
129
147
  const exitHandler = (exitCode) => () => {
130
148
  server.close();
131
149
  try {