remotelink 0.4.3 → 0.4.5
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 +15 -4
- package/dist/index.js +2268 -317
- package/dist/index.js.map +1 -1
- package/package.json +6 -3
package/dist/index.js
CHANGED
|
@@ -32,6 +32,1591 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
|
|
|
32
32
|
mod
|
|
33
33
|
));
|
|
34
34
|
|
|
35
|
+
// ../../node_modules/.pnpm/graceful-fs@4.2.11/node_modules/graceful-fs/polyfills.js
|
|
36
|
+
var require_polyfills = __commonJS({
|
|
37
|
+
"../../node_modules/.pnpm/graceful-fs@4.2.11/node_modules/graceful-fs/polyfills.js"(exports, module) {
|
|
38
|
+
"use strict";
|
|
39
|
+
var constants = __require("constants");
|
|
40
|
+
var origCwd = process.cwd;
|
|
41
|
+
var cwd = null;
|
|
42
|
+
var platform = process.env.GRACEFUL_FS_PLATFORM || process.platform;
|
|
43
|
+
process.cwd = function() {
|
|
44
|
+
if (!cwd)
|
|
45
|
+
cwd = origCwd.call(process);
|
|
46
|
+
return cwd;
|
|
47
|
+
};
|
|
48
|
+
try {
|
|
49
|
+
process.cwd();
|
|
50
|
+
} catch (er) {
|
|
51
|
+
}
|
|
52
|
+
if (typeof process.chdir === "function") {
|
|
53
|
+
chdir = process.chdir;
|
|
54
|
+
process.chdir = function(d) {
|
|
55
|
+
cwd = null;
|
|
56
|
+
chdir.call(process, d);
|
|
57
|
+
};
|
|
58
|
+
if (Object.setPrototypeOf) Object.setPrototypeOf(process.chdir, chdir);
|
|
59
|
+
}
|
|
60
|
+
var chdir;
|
|
61
|
+
module.exports = patch;
|
|
62
|
+
function patch(fs8) {
|
|
63
|
+
if (constants.hasOwnProperty("O_SYMLINK") && process.version.match(/^v0\.6\.[0-2]|^v0\.5\./)) {
|
|
64
|
+
patchLchmod(fs8);
|
|
65
|
+
}
|
|
66
|
+
if (!fs8.lutimes) {
|
|
67
|
+
patchLutimes(fs8);
|
|
68
|
+
}
|
|
69
|
+
fs8.chown = chownFix(fs8.chown);
|
|
70
|
+
fs8.fchown = chownFix(fs8.fchown);
|
|
71
|
+
fs8.lchown = chownFix(fs8.lchown);
|
|
72
|
+
fs8.chmod = chmodFix(fs8.chmod);
|
|
73
|
+
fs8.fchmod = chmodFix(fs8.fchmod);
|
|
74
|
+
fs8.lchmod = chmodFix(fs8.lchmod);
|
|
75
|
+
fs8.chownSync = chownFixSync(fs8.chownSync);
|
|
76
|
+
fs8.fchownSync = chownFixSync(fs8.fchownSync);
|
|
77
|
+
fs8.lchownSync = chownFixSync(fs8.lchownSync);
|
|
78
|
+
fs8.chmodSync = chmodFixSync(fs8.chmodSync);
|
|
79
|
+
fs8.fchmodSync = chmodFixSync(fs8.fchmodSync);
|
|
80
|
+
fs8.lchmodSync = chmodFixSync(fs8.lchmodSync);
|
|
81
|
+
fs8.stat = statFix(fs8.stat);
|
|
82
|
+
fs8.fstat = statFix(fs8.fstat);
|
|
83
|
+
fs8.lstat = statFix(fs8.lstat);
|
|
84
|
+
fs8.statSync = statFixSync(fs8.statSync);
|
|
85
|
+
fs8.fstatSync = statFixSync(fs8.fstatSync);
|
|
86
|
+
fs8.lstatSync = statFixSync(fs8.lstatSync);
|
|
87
|
+
if (fs8.chmod && !fs8.lchmod) {
|
|
88
|
+
fs8.lchmod = function(path8, mode, cb) {
|
|
89
|
+
if (cb) process.nextTick(cb);
|
|
90
|
+
};
|
|
91
|
+
fs8.lchmodSync = function() {
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
if (fs8.chown && !fs8.lchown) {
|
|
95
|
+
fs8.lchown = function(path8, uid, gid, cb) {
|
|
96
|
+
if (cb) process.nextTick(cb);
|
|
97
|
+
};
|
|
98
|
+
fs8.lchownSync = function() {
|
|
99
|
+
};
|
|
100
|
+
}
|
|
101
|
+
if (platform === "win32") {
|
|
102
|
+
fs8.rename = typeof fs8.rename !== "function" ? fs8.rename : (function(fs$rename) {
|
|
103
|
+
function rename(from, to, cb) {
|
|
104
|
+
var start = Date.now();
|
|
105
|
+
var backoff = 0;
|
|
106
|
+
fs$rename(from, to, function CB(er) {
|
|
107
|
+
if (er && (er.code === "EACCES" || er.code === "EPERM" || er.code === "EBUSY") && Date.now() - start < 6e4) {
|
|
108
|
+
setTimeout(function() {
|
|
109
|
+
fs8.stat(to, function(stater, st) {
|
|
110
|
+
if (stater && stater.code === "ENOENT")
|
|
111
|
+
fs$rename(from, to, CB);
|
|
112
|
+
else
|
|
113
|
+
cb(er);
|
|
114
|
+
});
|
|
115
|
+
}, backoff);
|
|
116
|
+
if (backoff < 100)
|
|
117
|
+
backoff += 10;
|
|
118
|
+
return;
|
|
119
|
+
}
|
|
120
|
+
if (cb) cb(er);
|
|
121
|
+
});
|
|
122
|
+
}
|
|
123
|
+
if (Object.setPrototypeOf) Object.setPrototypeOf(rename, fs$rename);
|
|
124
|
+
return rename;
|
|
125
|
+
})(fs8.rename);
|
|
126
|
+
}
|
|
127
|
+
fs8.read = typeof fs8.read !== "function" ? fs8.read : (function(fs$read) {
|
|
128
|
+
function read(fd, buffer, offset, length, position, callback_) {
|
|
129
|
+
var callback;
|
|
130
|
+
if (callback_ && typeof callback_ === "function") {
|
|
131
|
+
var eagCounter = 0;
|
|
132
|
+
callback = function(er, _, __) {
|
|
133
|
+
if (er && er.code === "EAGAIN" && eagCounter < 10) {
|
|
134
|
+
eagCounter++;
|
|
135
|
+
return fs$read.call(fs8, fd, buffer, offset, length, position, callback);
|
|
136
|
+
}
|
|
137
|
+
callback_.apply(this, arguments);
|
|
138
|
+
};
|
|
139
|
+
}
|
|
140
|
+
return fs$read.call(fs8, fd, buffer, offset, length, position, callback);
|
|
141
|
+
}
|
|
142
|
+
if (Object.setPrototypeOf) Object.setPrototypeOf(read, fs$read);
|
|
143
|
+
return read;
|
|
144
|
+
})(fs8.read);
|
|
145
|
+
fs8.readSync = typeof fs8.readSync !== "function" ? fs8.readSync : /* @__PURE__ */ (function(fs$readSync) {
|
|
146
|
+
return function(fd, buffer, offset, length, position) {
|
|
147
|
+
var eagCounter = 0;
|
|
148
|
+
while (true) {
|
|
149
|
+
try {
|
|
150
|
+
return fs$readSync.call(fs8, fd, buffer, offset, length, position);
|
|
151
|
+
} catch (er) {
|
|
152
|
+
if (er.code === "EAGAIN" && eagCounter < 10) {
|
|
153
|
+
eagCounter++;
|
|
154
|
+
continue;
|
|
155
|
+
}
|
|
156
|
+
throw er;
|
|
157
|
+
}
|
|
158
|
+
}
|
|
159
|
+
};
|
|
160
|
+
})(fs8.readSync);
|
|
161
|
+
function patchLchmod(fs9) {
|
|
162
|
+
fs9.lchmod = function(path8, mode, callback) {
|
|
163
|
+
fs9.open(
|
|
164
|
+
path8,
|
|
165
|
+
constants.O_WRONLY | constants.O_SYMLINK,
|
|
166
|
+
mode,
|
|
167
|
+
function(err, fd) {
|
|
168
|
+
if (err) {
|
|
169
|
+
if (callback) callback(err);
|
|
170
|
+
return;
|
|
171
|
+
}
|
|
172
|
+
fs9.fchmod(fd, mode, function(err2) {
|
|
173
|
+
fs9.close(fd, function(err22) {
|
|
174
|
+
if (callback) callback(err2 || err22);
|
|
175
|
+
});
|
|
176
|
+
});
|
|
177
|
+
}
|
|
178
|
+
);
|
|
179
|
+
};
|
|
180
|
+
fs9.lchmodSync = function(path8, mode) {
|
|
181
|
+
var fd = fs9.openSync(path8, constants.O_WRONLY | constants.O_SYMLINK, mode);
|
|
182
|
+
var threw = true;
|
|
183
|
+
var ret;
|
|
184
|
+
try {
|
|
185
|
+
ret = fs9.fchmodSync(fd, mode);
|
|
186
|
+
threw = false;
|
|
187
|
+
} finally {
|
|
188
|
+
if (threw) {
|
|
189
|
+
try {
|
|
190
|
+
fs9.closeSync(fd);
|
|
191
|
+
} catch (er) {
|
|
192
|
+
}
|
|
193
|
+
} else {
|
|
194
|
+
fs9.closeSync(fd);
|
|
195
|
+
}
|
|
196
|
+
}
|
|
197
|
+
return ret;
|
|
198
|
+
};
|
|
199
|
+
}
|
|
200
|
+
function patchLutimes(fs9) {
|
|
201
|
+
if (constants.hasOwnProperty("O_SYMLINK") && fs9.futimes) {
|
|
202
|
+
fs9.lutimes = function(path8, at, mt, cb) {
|
|
203
|
+
fs9.open(path8, constants.O_SYMLINK, function(er, fd) {
|
|
204
|
+
if (er) {
|
|
205
|
+
if (cb) cb(er);
|
|
206
|
+
return;
|
|
207
|
+
}
|
|
208
|
+
fs9.futimes(fd, at, mt, function(er2) {
|
|
209
|
+
fs9.close(fd, function(er22) {
|
|
210
|
+
if (cb) cb(er2 || er22);
|
|
211
|
+
});
|
|
212
|
+
});
|
|
213
|
+
});
|
|
214
|
+
};
|
|
215
|
+
fs9.lutimesSync = function(path8, at, mt) {
|
|
216
|
+
var fd = fs9.openSync(path8, constants.O_SYMLINK);
|
|
217
|
+
var ret;
|
|
218
|
+
var threw = true;
|
|
219
|
+
try {
|
|
220
|
+
ret = fs9.futimesSync(fd, at, mt);
|
|
221
|
+
threw = false;
|
|
222
|
+
} finally {
|
|
223
|
+
if (threw) {
|
|
224
|
+
try {
|
|
225
|
+
fs9.closeSync(fd);
|
|
226
|
+
} catch (er) {
|
|
227
|
+
}
|
|
228
|
+
} else {
|
|
229
|
+
fs9.closeSync(fd);
|
|
230
|
+
}
|
|
231
|
+
}
|
|
232
|
+
return ret;
|
|
233
|
+
};
|
|
234
|
+
} else if (fs9.futimes) {
|
|
235
|
+
fs9.lutimes = function(_a, _b, _c, cb) {
|
|
236
|
+
if (cb) process.nextTick(cb);
|
|
237
|
+
};
|
|
238
|
+
fs9.lutimesSync = function() {
|
|
239
|
+
};
|
|
240
|
+
}
|
|
241
|
+
}
|
|
242
|
+
function chmodFix(orig) {
|
|
243
|
+
if (!orig) return orig;
|
|
244
|
+
return function(target, mode, cb) {
|
|
245
|
+
return orig.call(fs8, target, mode, function(er) {
|
|
246
|
+
if (chownErOk(er)) er = null;
|
|
247
|
+
if (cb) cb.apply(this, arguments);
|
|
248
|
+
});
|
|
249
|
+
};
|
|
250
|
+
}
|
|
251
|
+
function chmodFixSync(orig) {
|
|
252
|
+
if (!orig) return orig;
|
|
253
|
+
return function(target, mode) {
|
|
254
|
+
try {
|
|
255
|
+
return orig.call(fs8, target, mode);
|
|
256
|
+
} catch (er) {
|
|
257
|
+
if (!chownErOk(er)) throw er;
|
|
258
|
+
}
|
|
259
|
+
};
|
|
260
|
+
}
|
|
261
|
+
function chownFix(orig) {
|
|
262
|
+
if (!orig) return orig;
|
|
263
|
+
return function(target, uid, gid, cb) {
|
|
264
|
+
return orig.call(fs8, target, uid, gid, function(er) {
|
|
265
|
+
if (chownErOk(er)) er = null;
|
|
266
|
+
if (cb) cb.apply(this, arguments);
|
|
267
|
+
});
|
|
268
|
+
};
|
|
269
|
+
}
|
|
270
|
+
function chownFixSync(orig) {
|
|
271
|
+
if (!orig) return orig;
|
|
272
|
+
return function(target, uid, gid) {
|
|
273
|
+
try {
|
|
274
|
+
return orig.call(fs8, target, uid, gid);
|
|
275
|
+
} catch (er) {
|
|
276
|
+
if (!chownErOk(er)) throw er;
|
|
277
|
+
}
|
|
278
|
+
};
|
|
279
|
+
}
|
|
280
|
+
function statFix(orig) {
|
|
281
|
+
if (!orig) return orig;
|
|
282
|
+
return function(target, options, cb) {
|
|
283
|
+
if (typeof options === "function") {
|
|
284
|
+
cb = options;
|
|
285
|
+
options = null;
|
|
286
|
+
}
|
|
287
|
+
function callback(er, stats) {
|
|
288
|
+
if (stats) {
|
|
289
|
+
if (stats.uid < 0) stats.uid += 4294967296;
|
|
290
|
+
if (stats.gid < 0) stats.gid += 4294967296;
|
|
291
|
+
}
|
|
292
|
+
if (cb) cb.apply(this, arguments);
|
|
293
|
+
}
|
|
294
|
+
return options ? orig.call(fs8, target, options, callback) : orig.call(fs8, target, callback);
|
|
295
|
+
};
|
|
296
|
+
}
|
|
297
|
+
function statFixSync(orig) {
|
|
298
|
+
if (!orig) return orig;
|
|
299
|
+
return function(target, options) {
|
|
300
|
+
var stats = options ? orig.call(fs8, target, options) : orig.call(fs8, target);
|
|
301
|
+
if (stats) {
|
|
302
|
+
if (stats.uid < 0) stats.uid += 4294967296;
|
|
303
|
+
if (stats.gid < 0) stats.gid += 4294967296;
|
|
304
|
+
}
|
|
305
|
+
return stats;
|
|
306
|
+
};
|
|
307
|
+
}
|
|
308
|
+
function chownErOk(er) {
|
|
309
|
+
if (!er)
|
|
310
|
+
return true;
|
|
311
|
+
if (er.code === "ENOSYS")
|
|
312
|
+
return true;
|
|
313
|
+
var nonroot = !process.getuid || process.getuid() !== 0;
|
|
314
|
+
if (nonroot) {
|
|
315
|
+
if (er.code === "EINVAL" || er.code === "EPERM")
|
|
316
|
+
return true;
|
|
317
|
+
}
|
|
318
|
+
return false;
|
|
319
|
+
}
|
|
320
|
+
}
|
|
321
|
+
}
|
|
322
|
+
});
|
|
323
|
+
|
|
324
|
+
// ../../node_modules/.pnpm/graceful-fs@4.2.11/node_modules/graceful-fs/legacy-streams.js
|
|
325
|
+
var require_legacy_streams = __commonJS({
|
|
326
|
+
"../../node_modules/.pnpm/graceful-fs@4.2.11/node_modules/graceful-fs/legacy-streams.js"(exports, module) {
|
|
327
|
+
"use strict";
|
|
328
|
+
var Stream = __require("stream").Stream;
|
|
329
|
+
module.exports = legacy;
|
|
330
|
+
function legacy(fs8) {
|
|
331
|
+
return {
|
|
332
|
+
ReadStream,
|
|
333
|
+
WriteStream
|
|
334
|
+
};
|
|
335
|
+
function ReadStream(path8, options) {
|
|
336
|
+
if (!(this instanceof ReadStream)) return new ReadStream(path8, options);
|
|
337
|
+
Stream.call(this);
|
|
338
|
+
var self = this;
|
|
339
|
+
this.path = path8;
|
|
340
|
+
this.fd = null;
|
|
341
|
+
this.readable = true;
|
|
342
|
+
this.paused = false;
|
|
343
|
+
this.flags = "r";
|
|
344
|
+
this.mode = 438;
|
|
345
|
+
this.bufferSize = 64 * 1024;
|
|
346
|
+
options = options || {};
|
|
347
|
+
var keys = Object.keys(options);
|
|
348
|
+
for (var index = 0, length = keys.length; index < length; index++) {
|
|
349
|
+
var key = keys[index];
|
|
350
|
+
this[key] = options[key];
|
|
351
|
+
}
|
|
352
|
+
if (this.encoding) this.setEncoding(this.encoding);
|
|
353
|
+
if (this.start !== void 0) {
|
|
354
|
+
if ("number" !== typeof this.start) {
|
|
355
|
+
throw TypeError("start must be a Number");
|
|
356
|
+
}
|
|
357
|
+
if (this.end === void 0) {
|
|
358
|
+
this.end = Infinity;
|
|
359
|
+
} else if ("number" !== typeof this.end) {
|
|
360
|
+
throw TypeError("end must be a Number");
|
|
361
|
+
}
|
|
362
|
+
if (this.start > this.end) {
|
|
363
|
+
throw new Error("start must be <= end");
|
|
364
|
+
}
|
|
365
|
+
this.pos = this.start;
|
|
366
|
+
}
|
|
367
|
+
if (this.fd !== null) {
|
|
368
|
+
process.nextTick(function() {
|
|
369
|
+
self._read();
|
|
370
|
+
});
|
|
371
|
+
return;
|
|
372
|
+
}
|
|
373
|
+
fs8.open(this.path, this.flags, this.mode, function(err, fd) {
|
|
374
|
+
if (err) {
|
|
375
|
+
self.emit("error", err);
|
|
376
|
+
self.readable = false;
|
|
377
|
+
return;
|
|
378
|
+
}
|
|
379
|
+
self.fd = fd;
|
|
380
|
+
self.emit("open", fd);
|
|
381
|
+
self._read();
|
|
382
|
+
});
|
|
383
|
+
}
|
|
384
|
+
function WriteStream(path8, options) {
|
|
385
|
+
if (!(this instanceof WriteStream)) return new WriteStream(path8, options);
|
|
386
|
+
Stream.call(this);
|
|
387
|
+
this.path = path8;
|
|
388
|
+
this.fd = null;
|
|
389
|
+
this.writable = true;
|
|
390
|
+
this.flags = "w";
|
|
391
|
+
this.encoding = "binary";
|
|
392
|
+
this.mode = 438;
|
|
393
|
+
this.bytesWritten = 0;
|
|
394
|
+
options = options || {};
|
|
395
|
+
var keys = Object.keys(options);
|
|
396
|
+
for (var index = 0, length = keys.length; index < length; index++) {
|
|
397
|
+
var key = keys[index];
|
|
398
|
+
this[key] = options[key];
|
|
399
|
+
}
|
|
400
|
+
if (this.start !== void 0) {
|
|
401
|
+
if ("number" !== typeof this.start) {
|
|
402
|
+
throw TypeError("start must be a Number");
|
|
403
|
+
}
|
|
404
|
+
if (this.start < 0) {
|
|
405
|
+
throw new Error("start must be >= zero");
|
|
406
|
+
}
|
|
407
|
+
this.pos = this.start;
|
|
408
|
+
}
|
|
409
|
+
this.busy = false;
|
|
410
|
+
this._queue = [];
|
|
411
|
+
if (this.fd === null) {
|
|
412
|
+
this._open = fs8.open;
|
|
413
|
+
this._queue.push([this._open, this.path, this.flags, this.mode, void 0]);
|
|
414
|
+
this.flush();
|
|
415
|
+
}
|
|
416
|
+
}
|
|
417
|
+
}
|
|
418
|
+
}
|
|
419
|
+
});
|
|
420
|
+
|
|
421
|
+
// ../../node_modules/.pnpm/graceful-fs@4.2.11/node_modules/graceful-fs/clone.js
|
|
422
|
+
var require_clone = __commonJS({
|
|
423
|
+
"../../node_modules/.pnpm/graceful-fs@4.2.11/node_modules/graceful-fs/clone.js"(exports, module) {
|
|
424
|
+
"use strict";
|
|
425
|
+
module.exports = clone;
|
|
426
|
+
var getPrototypeOf = Object.getPrototypeOf || function(obj) {
|
|
427
|
+
return obj.__proto__;
|
|
428
|
+
};
|
|
429
|
+
function clone(obj) {
|
|
430
|
+
if (obj === null || typeof obj !== "object")
|
|
431
|
+
return obj;
|
|
432
|
+
if (obj instanceof Object)
|
|
433
|
+
var copy = { __proto__: getPrototypeOf(obj) };
|
|
434
|
+
else
|
|
435
|
+
var copy = /* @__PURE__ */ Object.create(null);
|
|
436
|
+
Object.getOwnPropertyNames(obj).forEach(function(key) {
|
|
437
|
+
Object.defineProperty(copy, key, Object.getOwnPropertyDescriptor(obj, key));
|
|
438
|
+
});
|
|
439
|
+
return copy;
|
|
440
|
+
}
|
|
441
|
+
}
|
|
442
|
+
});
|
|
443
|
+
|
|
444
|
+
// ../../node_modules/.pnpm/graceful-fs@4.2.11/node_modules/graceful-fs/graceful-fs.js
|
|
445
|
+
var require_graceful_fs = __commonJS({
|
|
446
|
+
"../../node_modules/.pnpm/graceful-fs@4.2.11/node_modules/graceful-fs/graceful-fs.js"(exports, module) {
|
|
447
|
+
"use strict";
|
|
448
|
+
var fs8 = __require("fs");
|
|
449
|
+
var polyfills = require_polyfills();
|
|
450
|
+
var legacy = require_legacy_streams();
|
|
451
|
+
var clone = require_clone();
|
|
452
|
+
var util = __require("util");
|
|
453
|
+
var gracefulQueue;
|
|
454
|
+
var previousSymbol;
|
|
455
|
+
if (typeof Symbol === "function" && typeof Symbol.for === "function") {
|
|
456
|
+
gracefulQueue = /* @__PURE__ */ Symbol.for("graceful-fs.queue");
|
|
457
|
+
previousSymbol = /* @__PURE__ */ Symbol.for("graceful-fs.previous");
|
|
458
|
+
} else {
|
|
459
|
+
gracefulQueue = "___graceful-fs.queue";
|
|
460
|
+
previousSymbol = "___graceful-fs.previous";
|
|
461
|
+
}
|
|
462
|
+
function noop() {
|
|
463
|
+
}
|
|
464
|
+
function publishQueue(context, queue2) {
|
|
465
|
+
Object.defineProperty(context, gracefulQueue, {
|
|
466
|
+
get: function() {
|
|
467
|
+
return queue2;
|
|
468
|
+
}
|
|
469
|
+
});
|
|
470
|
+
}
|
|
471
|
+
var debug = noop;
|
|
472
|
+
if (util.debuglog)
|
|
473
|
+
debug = util.debuglog("gfs4");
|
|
474
|
+
else if (/\bgfs4\b/i.test(process.env.NODE_DEBUG || ""))
|
|
475
|
+
debug = function() {
|
|
476
|
+
var m = util.format.apply(util, arguments);
|
|
477
|
+
m = "GFS4: " + m.split(/\n/).join("\nGFS4: ");
|
|
478
|
+
console.error(m);
|
|
479
|
+
};
|
|
480
|
+
if (!fs8[gracefulQueue]) {
|
|
481
|
+
queue = global[gracefulQueue] || [];
|
|
482
|
+
publishQueue(fs8, queue);
|
|
483
|
+
fs8.close = (function(fs$close) {
|
|
484
|
+
function close(fd, cb) {
|
|
485
|
+
return fs$close.call(fs8, fd, function(err) {
|
|
486
|
+
if (!err) {
|
|
487
|
+
resetQueue();
|
|
488
|
+
}
|
|
489
|
+
if (typeof cb === "function")
|
|
490
|
+
cb.apply(this, arguments);
|
|
491
|
+
});
|
|
492
|
+
}
|
|
493
|
+
Object.defineProperty(close, previousSymbol, {
|
|
494
|
+
value: fs$close
|
|
495
|
+
});
|
|
496
|
+
return close;
|
|
497
|
+
})(fs8.close);
|
|
498
|
+
fs8.closeSync = (function(fs$closeSync) {
|
|
499
|
+
function closeSync2(fd) {
|
|
500
|
+
fs$closeSync.apply(fs8, arguments);
|
|
501
|
+
resetQueue();
|
|
502
|
+
}
|
|
503
|
+
Object.defineProperty(closeSync2, previousSymbol, {
|
|
504
|
+
value: fs$closeSync
|
|
505
|
+
});
|
|
506
|
+
return closeSync2;
|
|
507
|
+
})(fs8.closeSync);
|
|
508
|
+
if (/\bgfs4\b/i.test(process.env.NODE_DEBUG || "")) {
|
|
509
|
+
process.on("exit", function() {
|
|
510
|
+
debug(fs8[gracefulQueue]);
|
|
511
|
+
__require("assert").equal(fs8[gracefulQueue].length, 0);
|
|
512
|
+
});
|
|
513
|
+
}
|
|
514
|
+
}
|
|
515
|
+
var queue;
|
|
516
|
+
if (!global[gracefulQueue]) {
|
|
517
|
+
publishQueue(global, fs8[gracefulQueue]);
|
|
518
|
+
}
|
|
519
|
+
module.exports = patch(clone(fs8));
|
|
520
|
+
if (process.env.TEST_GRACEFUL_FS_GLOBAL_PATCH && !fs8.__patched) {
|
|
521
|
+
module.exports = patch(fs8);
|
|
522
|
+
fs8.__patched = true;
|
|
523
|
+
}
|
|
524
|
+
function patch(fs9) {
|
|
525
|
+
polyfills(fs9);
|
|
526
|
+
fs9.gracefulify = patch;
|
|
527
|
+
fs9.createReadStream = createReadStream2;
|
|
528
|
+
fs9.createWriteStream = createWriteStream;
|
|
529
|
+
var fs$readFile = fs9.readFile;
|
|
530
|
+
fs9.readFile = readFile;
|
|
531
|
+
function readFile(path8, options, cb) {
|
|
532
|
+
if (typeof options === "function")
|
|
533
|
+
cb = options, options = null;
|
|
534
|
+
return go$readFile(path8, options, cb);
|
|
535
|
+
function go$readFile(path9, options2, cb2, startTime) {
|
|
536
|
+
return fs$readFile(path9, options2, function(err) {
|
|
537
|
+
if (err && (err.code === "EMFILE" || err.code === "ENFILE"))
|
|
538
|
+
enqueue([go$readFile, [path9, options2, cb2], err, startTime || Date.now(), Date.now()]);
|
|
539
|
+
else {
|
|
540
|
+
if (typeof cb2 === "function")
|
|
541
|
+
cb2.apply(this, arguments);
|
|
542
|
+
}
|
|
543
|
+
});
|
|
544
|
+
}
|
|
545
|
+
}
|
|
546
|
+
var fs$writeFile = fs9.writeFile;
|
|
547
|
+
fs9.writeFile = writeFile;
|
|
548
|
+
function writeFile(path8, data, options, cb) {
|
|
549
|
+
if (typeof options === "function")
|
|
550
|
+
cb = options, options = null;
|
|
551
|
+
return go$writeFile(path8, data, options, cb);
|
|
552
|
+
function go$writeFile(path9, data2, options2, cb2, startTime) {
|
|
553
|
+
return fs$writeFile(path9, data2, options2, function(err) {
|
|
554
|
+
if (err && (err.code === "EMFILE" || err.code === "ENFILE"))
|
|
555
|
+
enqueue([go$writeFile, [path9, data2, options2, cb2], err, startTime || Date.now(), Date.now()]);
|
|
556
|
+
else {
|
|
557
|
+
if (typeof cb2 === "function")
|
|
558
|
+
cb2.apply(this, arguments);
|
|
559
|
+
}
|
|
560
|
+
});
|
|
561
|
+
}
|
|
562
|
+
}
|
|
563
|
+
var fs$appendFile = fs9.appendFile;
|
|
564
|
+
if (fs$appendFile)
|
|
565
|
+
fs9.appendFile = appendFile;
|
|
566
|
+
function appendFile(path8, data, options, cb) {
|
|
567
|
+
if (typeof options === "function")
|
|
568
|
+
cb = options, options = null;
|
|
569
|
+
return go$appendFile(path8, data, options, cb);
|
|
570
|
+
function go$appendFile(path9, data2, options2, cb2, startTime) {
|
|
571
|
+
return fs$appendFile(path9, data2, options2, function(err) {
|
|
572
|
+
if (err && (err.code === "EMFILE" || err.code === "ENFILE"))
|
|
573
|
+
enqueue([go$appendFile, [path9, data2, options2, cb2], err, startTime || Date.now(), Date.now()]);
|
|
574
|
+
else {
|
|
575
|
+
if (typeof cb2 === "function")
|
|
576
|
+
cb2.apply(this, arguments);
|
|
577
|
+
}
|
|
578
|
+
});
|
|
579
|
+
}
|
|
580
|
+
}
|
|
581
|
+
var fs$copyFile = fs9.copyFile;
|
|
582
|
+
if (fs$copyFile)
|
|
583
|
+
fs9.copyFile = copyFile;
|
|
584
|
+
function copyFile(src, dest, flags, cb) {
|
|
585
|
+
if (typeof flags === "function") {
|
|
586
|
+
cb = flags;
|
|
587
|
+
flags = 0;
|
|
588
|
+
}
|
|
589
|
+
return go$copyFile(src, dest, flags, cb);
|
|
590
|
+
function go$copyFile(src2, dest2, flags2, cb2, startTime) {
|
|
591
|
+
return fs$copyFile(src2, dest2, flags2, function(err) {
|
|
592
|
+
if (err && (err.code === "EMFILE" || err.code === "ENFILE"))
|
|
593
|
+
enqueue([go$copyFile, [src2, dest2, flags2, cb2], err, startTime || Date.now(), Date.now()]);
|
|
594
|
+
else {
|
|
595
|
+
if (typeof cb2 === "function")
|
|
596
|
+
cb2.apply(this, arguments);
|
|
597
|
+
}
|
|
598
|
+
});
|
|
599
|
+
}
|
|
600
|
+
}
|
|
601
|
+
var fs$readdir = fs9.readdir;
|
|
602
|
+
fs9.readdir = readdir;
|
|
603
|
+
var noReaddirOptionVersions = /^v[0-5]\./;
|
|
604
|
+
function readdir(path8, options, cb) {
|
|
605
|
+
if (typeof options === "function")
|
|
606
|
+
cb = options, options = null;
|
|
607
|
+
var go$readdir = noReaddirOptionVersions.test(process.version) ? function go$readdir2(path9, options2, cb2, startTime) {
|
|
608
|
+
return fs$readdir(path9, fs$readdirCallback(
|
|
609
|
+
path9,
|
|
610
|
+
options2,
|
|
611
|
+
cb2,
|
|
612
|
+
startTime
|
|
613
|
+
));
|
|
614
|
+
} : function go$readdir2(path9, options2, cb2, startTime) {
|
|
615
|
+
return fs$readdir(path9, options2, fs$readdirCallback(
|
|
616
|
+
path9,
|
|
617
|
+
options2,
|
|
618
|
+
cb2,
|
|
619
|
+
startTime
|
|
620
|
+
));
|
|
621
|
+
};
|
|
622
|
+
return go$readdir(path8, options, cb);
|
|
623
|
+
function fs$readdirCallback(path9, options2, cb2, startTime) {
|
|
624
|
+
return function(err, files) {
|
|
625
|
+
if (err && (err.code === "EMFILE" || err.code === "ENFILE"))
|
|
626
|
+
enqueue([
|
|
627
|
+
go$readdir,
|
|
628
|
+
[path9, options2, cb2],
|
|
629
|
+
err,
|
|
630
|
+
startTime || Date.now(),
|
|
631
|
+
Date.now()
|
|
632
|
+
]);
|
|
633
|
+
else {
|
|
634
|
+
if (files && files.sort)
|
|
635
|
+
files.sort();
|
|
636
|
+
if (typeof cb2 === "function")
|
|
637
|
+
cb2.call(this, err, files);
|
|
638
|
+
}
|
|
639
|
+
};
|
|
640
|
+
}
|
|
641
|
+
}
|
|
642
|
+
if (process.version.substr(0, 4) === "v0.8") {
|
|
643
|
+
var legStreams = legacy(fs9);
|
|
644
|
+
ReadStream = legStreams.ReadStream;
|
|
645
|
+
WriteStream = legStreams.WriteStream;
|
|
646
|
+
}
|
|
647
|
+
var fs$ReadStream = fs9.ReadStream;
|
|
648
|
+
if (fs$ReadStream) {
|
|
649
|
+
ReadStream.prototype = Object.create(fs$ReadStream.prototype);
|
|
650
|
+
ReadStream.prototype.open = ReadStream$open;
|
|
651
|
+
}
|
|
652
|
+
var fs$WriteStream = fs9.WriteStream;
|
|
653
|
+
if (fs$WriteStream) {
|
|
654
|
+
WriteStream.prototype = Object.create(fs$WriteStream.prototype);
|
|
655
|
+
WriteStream.prototype.open = WriteStream$open;
|
|
656
|
+
}
|
|
657
|
+
Object.defineProperty(fs9, "ReadStream", {
|
|
658
|
+
get: function() {
|
|
659
|
+
return ReadStream;
|
|
660
|
+
},
|
|
661
|
+
set: function(val) {
|
|
662
|
+
ReadStream = val;
|
|
663
|
+
},
|
|
664
|
+
enumerable: true,
|
|
665
|
+
configurable: true
|
|
666
|
+
});
|
|
667
|
+
Object.defineProperty(fs9, "WriteStream", {
|
|
668
|
+
get: function() {
|
|
669
|
+
return WriteStream;
|
|
670
|
+
},
|
|
671
|
+
set: function(val) {
|
|
672
|
+
WriteStream = val;
|
|
673
|
+
},
|
|
674
|
+
enumerable: true,
|
|
675
|
+
configurable: true
|
|
676
|
+
});
|
|
677
|
+
var FileReadStream = ReadStream;
|
|
678
|
+
Object.defineProperty(fs9, "FileReadStream", {
|
|
679
|
+
get: function() {
|
|
680
|
+
return FileReadStream;
|
|
681
|
+
},
|
|
682
|
+
set: function(val) {
|
|
683
|
+
FileReadStream = val;
|
|
684
|
+
},
|
|
685
|
+
enumerable: true,
|
|
686
|
+
configurable: true
|
|
687
|
+
});
|
|
688
|
+
var FileWriteStream = WriteStream;
|
|
689
|
+
Object.defineProperty(fs9, "FileWriteStream", {
|
|
690
|
+
get: function() {
|
|
691
|
+
return FileWriteStream;
|
|
692
|
+
},
|
|
693
|
+
set: function(val) {
|
|
694
|
+
FileWriteStream = val;
|
|
695
|
+
},
|
|
696
|
+
enumerable: true,
|
|
697
|
+
configurable: true
|
|
698
|
+
});
|
|
699
|
+
function ReadStream(path8, options) {
|
|
700
|
+
if (this instanceof ReadStream)
|
|
701
|
+
return fs$ReadStream.apply(this, arguments), this;
|
|
702
|
+
else
|
|
703
|
+
return ReadStream.apply(Object.create(ReadStream.prototype), arguments);
|
|
704
|
+
}
|
|
705
|
+
function ReadStream$open() {
|
|
706
|
+
var that = this;
|
|
707
|
+
open(that.path, that.flags, that.mode, function(err, fd) {
|
|
708
|
+
if (err) {
|
|
709
|
+
if (that.autoClose)
|
|
710
|
+
that.destroy();
|
|
711
|
+
that.emit("error", err);
|
|
712
|
+
} else {
|
|
713
|
+
that.fd = fd;
|
|
714
|
+
that.emit("open", fd);
|
|
715
|
+
that.read();
|
|
716
|
+
}
|
|
717
|
+
});
|
|
718
|
+
}
|
|
719
|
+
function WriteStream(path8, options) {
|
|
720
|
+
if (this instanceof WriteStream)
|
|
721
|
+
return fs$WriteStream.apply(this, arguments), this;
|
|
722
|
+
else
|
|
723
|
+
return WriteStream.apply(Object.create(WriteStream.prototype), arguments);
|
|
724
|
+
}
|
|
725
|
+
function WriteStream$open() {
|
|
726
|
+
var that = this;
|
|
727
|
+
open(that.path, that.flags, that.mode, function(err, fd) {
|
|
728
|
+
if (err) {
|
|
729
|
+
that.destroy();
|
|
730
|
+
that.emit("error", err);
|
|
731
|
+
} else {
|
|
732
|
+
that.fd = fd;
|
|
733
|
+
that.emit("open", fd);
|
|
734
|
+
}
|
|
735
|
+
});
|
|
736
|
+
}
|
|
737
|
+
function createReadStream2(path8, options) {
|
|
738
|
+
return new fs9.ReadStream(path8, options);
|
|
739
|
+
}
|
|
740
|
+
function createWriteStream(path8, options) {
|
|
741
|
+
return new fs9.WriteStream(path8, options);
|
|
742
|
+
}
|
|
743
|
+
var fs$open = fs9.open;
|
|
744
|
+
fs9.open = open;
|
|
745
|
+
function open(path8, flags, mode, cb) {
|
|
746
|
+
if (typeof mode === "function")
|
|
747
|
+
cb = mode, mode = null;
|
|
748
|
+
return go$open(path8, flags, mode, cb);
|
|
749
|
+
function go$open(path9, flags2, mode2, cb2, startTime) {
|
|
750
|
+
return fs$open(path9, flags2, mode2, function(err, fd) {
|
|
751
|
+
if (err && (err.code === "EMFILE" || err.code === "ENFILE"))
|
|
752
|
+
enqueue([go$open, [path9, flags2, mode2, cb2], err, startTime || Date.now(), Date.now()]);
|
|
753
|
+
else {
|
|
754
|
+
if (typeof cb2 === "function")
|
|
755
|
+
cb2.apply(this, arguments);
|
|
756
|
+
}
|
|
757
|
+
});
|
|
758
|
+
}
|
|
759
|
+
}
|
|
760
|
+
return fs9;
|
|
761
|
+
}
|
|
762
|
+
function enqueue(elem) {
|
|
763
|
+
debug("ENQUEUE", elem[0].name, elem[1]);
|
|
764
|
+
fs8[gracefulQueue].push(elem);
|
|
765
|
+
retry();
|
|
766
|
+
}
|
|
767
|
+
var retryTimer;
|
|
768
|
+
function resetQueue() {
|
|
769
|
+
var now = Date.now();
|
|
770
|
+
for (var i = 0; i < fs8[gracefulQueue].length; ++i) {
|
|
771
|
+
if (fs8[gracefulQueue][i].length > 2) {
|
|
772
|
+
fs8[gracefulQueue][i][3] = now;
|
|
773
|
+
fs8[gracefulQueue][i][4] = now;
|
|
774
|
+
}
|
|
775
|
+
}
|
|
776
|
+
retry();
|
|
777
|
+
}
|
|
778
|
+
function retry() {
|
|
779
|
+
clearTimeout(retryTimer);
|
|
780
|
+
retryTimer = void 0;
|
|
781
|
+
if (fs8[gracefulQueue].length === 0)
|
|
782
|
+
return;
|
|
783
|
+
var elem = fs8[gracefulQueue].shift();
|
|
784
|
+
var fn = elem[0];
|
|
785
|
+
var args = elem[1];
|
|
786
|
+
var err = elem[2];
|
|
787
|
+
var startTime = elem[3];
|
|
788
|
+
var lastTime = elem[4];
|
|
789
|
+
if (startTime === void 0) {
|
|
790
|
+
debug("RETRY", fn.name, args);
|
|
791
|
+
fn.apply(null, args);
|
|
792
|
+
} else if (Date.now() - startTime >= 6e4) {
|
|
793
|
+
debug("TIMEOUT", fn.name, args);
|
|
794
|
+
var cb = args.pop();
|
|
795
|
+
if (typeof cb === "function")
|
|
796
|
+
cb.call(null, err);
|
|
797
|
+
} else {
|
|
798
|
+
var sinceAttempt = Date.now() - lastTime;
|
|
799
|
+
var sinceStart = Math.max(lastTime - startTime, 1);
|
|
800
|
+
var desiredDelay = Math.min(sinceStart * 1.2, 100);
|
|
801
|
+
if (sinceAttempt >= desiredDelay) {
|
|
802
|
+
debug("RETRY", fn.name, args);
|
|
803
|
+
fn.apply(null, args.concat([startTime]));
|
|
804
|
+
} else {
|
|
805
|
+
fs8[gracefulQueue].push(elem);
|
|
806
|
+
}
|
|
807
|
+
}
|
|
808
|
+
if (retryTimer === void 0) {
|
|
809
|
+
retryTimer = setTimeout(retry, 0);
|
|
810
|
+
}
|
|
811
|
+
}
|
|
812
|
+
}
|
|
813
|
+
});
|
|
814
|
+
|
|
815
|
+
// ../../node_modules/.pnpm/retry@0.12.0/node_modules/retry/lib/retry_operation.js
|
|
816
|
+
var require_retry_operation = __commonJS({
|
|
817
|
+
"../../node_modules/.pnpm/retry@0.12.0/node_modules/retry/lib/retry_operation.js"(exports, module) {
|
|
818
|
+
"use strict";
|
|
819
|
+
function RetryOperation(timeouts, options) {
|
|
820
|
+
if (typeof options === "boolean") {
|
|
821
|
+
options = { forever: options };
|
|
822
|
+
}
|
|
823
|
+
this._originalTimeouts = JSON.parse(JSON.stringify(timeouts));
|
|
824
|
+
this._timeouts = timeouts;
|
|
825
|
+
this._options = options || {};
|
|
826
|
+
this._maxRetryTime = options && options.maxRetryTime || Infinity;
|
|
827
|
+
this._fn = null;
|
|
828
|
+
this._errors = [];
|
|
829
|
+
this._attempts = 1;
|
|
830
|
+
this._operationTimeout = null;
|
|
831
|
+
this._operationTimeoutCb = null;
|
|
832
|
+
this._timeout = null;
|
|
833
|
+
this._operationStart = null;
|
|
834
|
+
if (this._options.forever) {
|
|
835
|
+
this._cachedTimeouts = this._timeouts.slice(0);
|
|
836
|
+
}
|
|
837
|
+
}
|
|
838
|
+
module.exports = RetryOperation;
|
|
839
|
+
RetryOperation.prototype.reset = function() {
|
|
840
|
+
this._attempts = 1;
|
|
841
|
+
this._timeouts = this._originalTimeouts;
|
|
842
|
+
};
|
|
843
|
+
RetryOperation.prototype.stop = function() {
|
|
844
|
+
if (this._timeout) {
|
|
845
|
+
clearTimeout(this._timeout);
|
|
846
|
+
}
|
|
847
|
+
this._timeouts = [];
|
|
848
|
+
this._cachedTimeouts = null;
|
|
849
|
+
};
|
|
850
|
+
RetryOperation.prototype.retry = function(err) {
|
|
851
|
+
if (this._timeout) {
|
|
852
|
+
clearTimeout(this._timeout);
|
|
853
|
+
}
|
|
854
|
+
if (!err) {
|
|
855
|
+
return false;
|
|
856
|
+
}
|
|
857
|
+
var currentTime = (/* @__PURE__ */ new Date()).getTime();
|
|
858
|
+
if (err && currentTime - this._operationStart >= this._maxRetryTime) {
|
|
859
|
+
this._errors.unshift(new Error("RetryOperation timeout occurred"));
|
|
860
|
+
return false;
|
|
861
|
+
}
|
|
862
|
+
this._errors.push(err);
|
|
863
|
+
var timeout = this._timeouts.shift();
|
|
864
|
+
if (timeout === void 0) {
|
|
865
|
+
if (this._cachedTimeouts) {
|
|
866
|
+
this._errors.splice(this._errors.length - 1, this._errors.length);
|
|
867
|
+
this._timeouts = this._cachedTimeouts.slice(0);
|
|
868
|
+
timeout = this._timeouts.shift();
|
|
869
|
+
} else {
|
|
870
|
+
return false;
|
|
871
|
+
}
|
|
872
|
+
}
|
|
873
|
+
var self = this;
|
|
874
|
+
var timer = setTimeout(function() {
|
|
875
|
+
self._attempts++;
|
|
876
|
+
if (self._operationTimeoutCb) {
|
|
877
|
+
self._timeout = setTimeout(function() {
|
|
878
|
+
self._operationTimeoutCb(self._attempts);
|
|
879
|
+
}, self._operationTimeout);
|
|
880
|
+
if (self._options.unref) {
|
|
881
|
+
self._timeout.unref();
|
|
882
|
+
}
|
|
883
|
+
}
|
|
884
|
+
self._fn(self._attempts);
|
|
885
|
+
}, timeout);
|
|
886
|
+
if (this._options.unref) {
|
|
887
|
+
timer.unref();
|
|
888
|
+
}
|
|
889
|
+
return true;
|
|
890
|
+
};
|
|
891
|
+
RetryOperation.prototype.attempt = function(fn, timeoutOps) {
|
|
892
|
+
this._fn = fn;
|
|
893
|
+
if (timeoutOps) {
|
|
894
|
+
if (timeoutOps.timeout) {
|
|
895
|
+
this._operationTimeout = timeoutOps.timeout;
|
|
896
|
+
}
|
|
897
|
+
if (timeoutOps.cb) {
|
|
898
|
+
this._operationTimeoutCb = timeoutOps.cb;
|
|
899
|
+
}
|
|
900
|
+
}
|
|
901
|
+
var self = this;
|
|
902
|
+
if (this._operationTimeoutCb) {
|
|
903
|
+
this._timeout = setTimeout(function() {
|
|
904
|
+
self._operationTimeoutCb();
|
|
905
|
+
}, self._operationTimeout);
|
|
906
|
+
}
|
|
907
|
+
this._operationStart = (/* @__PURE__ */ new Date()).getTime();
|
|
908
|
+
this._fn(this._attempts);
|
|
909
|
+
};
|
|
910
|
+
RetryOperation.prototype.try = function(fn) {
|
|
911
|
+
console.log("Using RetryOperation.try() is deprecated");
|
|
912
|
+
this.attempt(fn);
|
|
913
|
+
};
|
|
914
|
+
RetryOperation.prototype.start = function(fn) {
|
|
915
|
+
console.log("Using RetryOperation.start() is deprecated");
|
|
916
|
+
this.attempt(fn);
|
|
917
|
+
};
|
|
918
|
+
RetryOperation.prototype.start = RetryOperation.prototype.try;
|
|
919
|
+
RetryOperation.prototype.errors = function() {
|
|
920
|
+
return this._errors;
|
|
921
|
+
};
|
|
922
|
+
RetryOperation.prototype.attempts = function() {
|
|
923
|
+
return this._attempts;
|
|
924
|
+
};
|
|
925
|
+
RetryOperation.prototype.mainError = function() {
|
|
926
|
+
if (this._errors.length === 0) {
|
|
927
|
+
return null;
|
|
928
|
+
}
|
|
929
|
+
var counts = {};
|
|
930
|
+
var mainError = null;
|
|
931
|
+
var mainErrorCount = 0;
|
|
932
|
+
for (var i = 0; i < this._errors.length; i++) {
|
|
933
|
+
var error = this._errors[i];
|
|
934
|
+
var message = error.message;
|
|
935
|
+
var count = (counts[message] || 0) + 1;
|
|
936
|
+
counts[message] = count;
|
|
937
|
+
if (count >= mainErrorCount) {
|
|
938
|
+
mainError = error;
|
|
939
|
+
mainErrorCount = count;
|
|
940
|
+
}
|
|
941
|
+
}
|
|
942
|
+
return mainError;
|
|
943
|
+
};
|
|
944
|
+
}
|
|
945
|
+
});
|
|
946
|
+
|
|
947
|
+
// ../../node_modules/.pnpm/retry@0.12.0/node_modules/retry/lib/retry.js
|
|
948
|
+
var require_retry = __commonJS({
|
|
949
|
+
"../../node_modules/.pnpm/retry@0.12.0/node_modules/retry/lib/retry.js"(exports) {
|
|
950
|
+
"use strict";
|
|
951
|
+
var RetryOperation = require_retry_operation();
|
|
952
|
+
exports.operation = function(options) {
|
|
953
|
+
var timeouts = exports.timeouts(options);
|
|
954
|
+
return new RetryOperation(timeouts, {
|
|
955
|
+
forever: options && options.forever,
|
|
956
|
+
unref: options && options.unref,
|
|
957
|
+
maxRetryTime: options && options.maxRetryTime
|
|
958
|
+
});
|
|
959
|
+
};
|
|
960
|
+
exports.timeouts = function(options) {
|
|
961
|
+
if (options instanceof Array) {
|
|
962
|
+
return [].concat(options);
|
|
963
|
+
}
|
|
964
|
+
var opts = {
|
|
965
|
+
retries: 10,
|
|
966
|
+
factor: 2,
|
|
967
|
+
minTimeout: 1 * 1e3,
|
|
968
|
+
maxTimeout: Infinity,
|
|
969
|
+
randomize: false
|
|
970
|
+
};
|
|
971
|
+
for (var key in options) {
|
|
972
|
+
opts[key] = options[key];
|
|
973
|
+
}
|
|
974
|
+
if (opts.minTimeout > opts.maxTimeout) {
|
|
975
|
+
throw new Error("minTimeout is greater than maxTimeout");
|
|
976
|
+
}
|
|
977
|
+
var timeouts = [];
|
|
978
|
+
for (var i = 0; i < opts.retries; i++) {
|
|
979
|
+
timeouts.push(this.createTimeout(i, opts));
|
|
980
|
+
}
|
|
981
|
+
if (options && options.forever && !timeouts.length) {
|
|
982
|
+
timeouts.push(this.createTimeout(i, opts));
|
|
983
|
+
}
|
|
984
|
+
timeouts.sort(function(a, b) {
|
|
985
|
+
return a - b;
|
|
986
|
+
});
|
|
987
|
+
return timeouts;
|
|
988
|
+
};
|
|
989
|
+
exports.createTimeout = function(attempt, opts) {
|
|
990
|
+
var random = opts.randomize ? Math.random() + 1 : 1;
|
|
991
|
+
var timeout = Math.round(random * opts.minTimeout * Math.pow(opts.factor, attempt));
|
|
992
|
+
timeout = Math.min(timeout, opts.maxTimeout);
|
|
993
|
+
return timeout;
|
|
994
|
+
};
|
|
995
|
+
exports.wrap = function(obj, options, methods) {
|
|
996
|
+
if (options instanceof Array) {
|
|
997
|
+
methods = options;
|
|
998
|
+
options = null;
|
|
999
|
+
}
|
|
1000
|
+
if (!methods) {
|
|
1001
|
+
methods = [];
|
|
1002
|
+
for (var key in obj) {
|
|
1003
|
+
if (typeof obj[key] === "function") {
|
|
1004
|
+
methods.push(key);
|
|
1005
|
+
}
|
|
1006
|
+
}
|
|
1007
|
+
}
|
|
1008
|
+
for (var i = 0; i < methods.length; i++) {
|
|
1009
|
+
var method = methods[i];
|
|
1010
|
+
var original = obj[method];
|
|
1011
|
+
obj[method] = function retryWrapper(original2) {
|
|
1012
|
+
var op = exports.operation(options);
|
|
1013
|
+
var args = Array.prototype.slice.call(arguments, 1);
|
|
1014
|
+
var callback = args.pop();
|
|
1015
|
+
args.push(function(err) {
|
|
1016
|
+
if (op.retry(err)) {
|
|
1017
|
+
return;
|
|
1018
|
+
}
|
|
1019
|
+
if (err) {
|
|
1020
|
+
arguments[0] = op.mainError();
|
|
1021
|
+
}
|
|
1022
|
+
callback.apply(this, arguments);
|
|
1023
|
+
});
|
|
1024
|
+
op.attempt(function() {
|
|
1025
|
+
original2.apply(obj, args);
|
|
1026
|
+
});
|
|
1027
|
+
}.bind(obj, original);
|
|
1028
|
+
obj[method].options = options;
|
|
1029
|
+
}
|
|
1030
|
+
};
|
|
1031
|
+
}
|
|
1032
|
+
});
|
|
1033
|
+
|
|
1034
|
+
// ../../node_modules/.pnpm/retry@0.12.0/node_modules/retry/index.js
|
|
1035
|
+
var require_retry2 = __commonJS({
|
|
1036
|
+
"../../node_modules/.pnpm/retry@0.12.0/node_modules/retry/index.js"(exports, module) {
|
|
1037
|
+
"use strict";
|
|
1038
|
+
module.exports = require_retry();
|
|
1039
|
+
}
|
|
1040
|
+
});
|
|
1041
|
+
|
|
1042
|
+
// ../../node_modules/.pnpm/signal-exit@3.0.7/node_modules/signal-exit/signals.js
|
|
1043
|
+
var require_signals = __commonJS({
|
|
1044
|
+
"../../node_modules/.pnpm/signal-exit@3.0.7/node_modules/signal-exit/signals.js"(exports, module) {
|
|
1045
|
+
"use strict";
|
|
1046
|
+
module.exports = [
|
|
1047
|
+
"SIGABRT",
|
|
1048
|
+
"SIGALRM",
|
|
1049
|
+
"SIGHUP",
|
|
1050
|
+
"SIGINT",
|
|
1051
|
+
"SIGTERM"
|
|
1052
|
+
];
|
|
1053
|
+
if (process.platform !== "win32") {
|
|
1054
|
+
module.exports.push(
|
|
1055
|
+
"SIGVTALRM",
|
|
1056
|
+
"SIGXCPU",
|
|
1057
|
+
"SIGXFSZ",
|
|
1058
|
+
"SIGUSR2",
|
|
1059
|
+
"SIGTRAP",
|
|
1060
|
+
"SIGSYS",
|
|
1061
|
+
"SIGQUIT",
|
|
1062
|
+
"SIGIOT"
|
|
1063
|
+
// should detect profiler and enable/disable accordingly.
|
|
1064
|
+
// see #21
|
|
1065
|
+
// 'SIGPROF'
|
|
1066
|
+
);
|
|
1067
|
+
}
|
|
1068
|
+
if (process.platform === "linux") {
|
|
1069
|
+
module.exports.push(
|
|
1070
|
+
"SIGIO",
|
|
1071
|
+
"SIGPOLL",
|
|
1072
|
+
"SIGPWR",
|
|
1073
|
+
"SIGSTKFLT",
|
|
1074
|
+
"SIGUNUSED"
|
|
1075
|
+
);
|
|
1076
|
+
}
|
|
1077
|
+
}
|
|
1078
|
+
});
|
|
1079
|
+
|
|
1080
|
+
// ../../node_modules/.pnpm/signal-exit@3.0.7/node_modules/signal-exit/index.js
|
|
1081
|
+
var require_signal_exit = __commonJS({
|
|
1082
|
+
"../../node_modules/.pnpm/signal-exit@3.0.7/node_modules/signal-exit/index.js"(exports, module) {
|
|
1083
|
+
"use strict";
|
|
1084
|
+
var process4 = global.process;
|
|
1085
|
+
var processOk = function(process5) {
|
|
1086
|
+
return process5 && typeof process5 === "object" && typeof process5.removeListener === "function" && typeof process5.emit === "function" && typeof process5.reallyExit === "function" && typeof process5.listeners === "function" && typeof process5.kill === "function" && typeof process5.pid === "number" && typeof process5.on === "function";
|
|
1087
|
+
};
|
|
1088
|
+
if (!processOk(process4)) {
|
|
1089
|
+
module.exports = function() {
|
|
1090
|
+
return function() {
|
|
1091
|
+
};
|
|
1092
|
+
};
|
|
1093
|
+
} else {
|
|
1094
|
+
assert = __require("assert");
|
|
1095
|
+
signals = require_signals();
|
|
1096
|
+
isWin = /^win/i.test(process4.platform);
|
|
1097
|
+
EE = __require("events");
|
|
1098
|
+
if (typeof EE !== "function") {
|
|
1099
|
+
EE = EE.EventEmitter;
|
|
1100
|
+
}
|
|
1101
|
+
if (process4.__signal_exit_emitter__) {
|
|
1102
|
+
emitter = process4.__signal_exit_emitter__;
|
|
1103
|
+
} else {
|
|
1104
|
+
emitter = process4.__signal_exit_emitter__ = new EE();
|
|
1105
|
+
emitter.count = 0;
|
|
1106
|
+
emitter.emitted = {};
|
|
1107
|
+
}
|
|
1108
|
+
if (!emitter.infinite) {
|
|
1109
|
+
emitter.setMaxListeners(Infinity);
|
|
1110
|
+
emitter.infinite = true;
|
|
1111
|
+
}
|
|
1112
|
+
module.exports = function(cb, opts) {
|
|
1113
|
+
if (!processOk(global.process)) {
|
|
1114
|
+
return function() {
|
|
1115
|
+
};
|
|
1116
|
+
}
|
|
1117
|
+
assert.equal(typeof cb, "function", "a callback must be provided for exit handler");
|
|
1118
|
+
if (loaded === false) {
|
|
1119
|
+
load();
|
|
1120
|
+
}
|
|
1121
|
+
var ev = "exit";
|
|
1122
|
+
if (opts && opts.alwaysLast) {
|
|
1123
|
+
ev = "afterexit";
|
|
1124
|
+
}
|
|
1125
|
+
var remove = function() {
|
|
1126
|
+
emitter.removeListener(ev, cb);
|
|
1127
|
+
if (emitter.listeners("exit").length === 0 && emitter.listeners("afterexit").length === 0) {
|
|
1128
|
+
unload();
|
|
1129
|
+
}
|
|
1130
|
+
};
|
|
1131
|
+
emitter.on(ev, cb);
|
|
1132
|
+
return remove;
|
|
1133
|
+
};
|
|
1134
|
+
unload = function unload2() {
|
|
1135
|
+
if (!loaded || !processOk(global.process)) {
|
|
1136
|
+
return;
|
|
1137
|
+
}
|
|
1138
|
+
loaded = false;
|
|
1139
|
+
signals.forEach(function(sig) {
|
|
1140
|
+
try {
|
|
1141
|
+
process4.removeListener(sig, sigListeners[sig]);
|
|
1142
|
+
} catch (er) {
|
|
1143
|
+
}
|
|
1144
|
+
});
|
|
1145
|
+
process4.emit = originalProcessEmit;
|
|
1146
|
+
process4.reallyExit = originalProcessReallyExit;
|
|
1147
|
+
emitter.count -= 1;
|
|
1148
|
+
};
|
|
1149
|
+
module.exports.unload = unload;
|
|
1150
|
+
emit = function emit2(event, code, signal) {
|
|
1151
|
+
if (emitter.emitted[event]) {
|
|
1152
|
+
return;
|
|
1153
|
+
}
|
|
1154
|
+
emitter.emitted[event] = true;
|
|
1155
|
+
emitter.emit(event, code, signal);
|
|
1156
|
+
};
|
|
1157
|
+
sigListeners = {};
|
|
1158
|
+
signals.forEach(function(sig) {
|
|
1159
|
+
sigListeners[sig] = function listener() {
|
|
1160
|
+
if (!processOk(global.process)) {
|
|
1161
|
+
return;
|
|
1162
|
+
}
|
|
1163
|
+
var listeners = process4.listeners(sig);
|
|
1164
|
+
if (listeners.length === emitter.count) {
|
|
1165
|
+
unload();
|
|
1166
|
+
emit("exit", null, sig);
|
|
1167
|
+
emit("afterexit", null, sig);
|
|
1168
|
+
if (isWin && sig === "SIGHUP") {
|
|
1169
|
+
sig = "SIGINT";
|
|
1170
|
+
}
|
|
1171
|
+
process4.kill(process4.pid, sig);
|
|
1172
|
+
}
|
|
1173
|
+
};
|
|
1174
|
+
});
|
|
1175
|
+
module.exports.signals = function() {
|
|
1176
|
+
return signals;
|
|
1177
|
+
};
|
|
1178
|
+
loaded = false;
|
|
1179
|
+
load = function load2() {
|
|
1180
|
+
if (loaded || !processOk(global.process)) {
|
|
1181
|
+
return;
|
|
1182
|
+
}
|
|
1183
|
+
loaded = true;
|
|
1184
|
+
emitter.count += 1;
|
|
1185
|
+
signals = signals.filter(function(sig) {
|
|
1186
|
+
try {
|
|
1187
|
+
process4.on(sig, sigListeners[sig]);
|
|
1188
|
+
return true;
|
|
1189
|
+
} catch (er) {
|
|
1190
|
+
return false;
|
|
1191
|
+
}
|
|
1192
|
+
});
|
|
1193
|
+
process4.emit = processEmit;
|
|
1194
|
+
process4.reallyExit = processReallyExit;
|
|
1195
|
+
};
|
|
1196
|
+
module.exports.load = load;
|
|
1197
|
+
originalProcessReallyExit = process4.reallyExit;
|
|
1198
|
+
processReallyExit = function processReallyExit2(code) {
|
|
1199
|
+
if (!processOk(global.process)) {
|
|
1200
|
+
return;
|
|
1201
|
+
}
|
|
1202
|
+
process4.exitCode = code || /* istanbul ignore next */
|
|
1203
|
+
0;
|
|
1204
|
+
emit("exit", process4.exitCode, null);
|
|
1205
|
+
emit("afterexit", process4.exitCode, null);
|
|
1206
|
+
originalProcessReallyExit.call(process4, process4.exitCode);
|
|
1207
|
+
};
|
|
1208
|
+
originalProcessEmit = process4.emit;
|
|
1209
|
+
processEmit = function processEmit2(ev, arg) {
|
|
1210
|
+
if (ev === "exit" && processOk(global.process)) {
|
|
1211
|
+
if (arg !== void 0) {
|
|
1212
|
+
process4.exitCode = arg;
|
|
1213
|
+
}
|
|
1214
|
+
var ret = originalProcessEmit.apply(this, arguments);
|
|
1215
|
+
emit("exit", process4.exitCode, null);
|
|
1216
|
+
emit("afterexit", process4.exitCode, null);
|
|
1217
|
+
return ret;
|
|
1218
|
+
} else {
|
|
1219
|
+
return originalProcessEmit.apply(this, arguments);
|
|
1220
|
+
}
|
|
1221
|
+
};
|
|
1222
|
+
}
|
|
1223
|
+
var assert;
|
|
1224
|
+
var signals;
|
|
1225
|
+
var isWin;
|
|
1226
|
+
var EE;
|
|
1227
|
+
var emitter;
|
|
1228
|
+
var unload;
|
|
1229
|
+
var emit;
|
|
1230
|
+
var sigListeners;
|
|
1231
|
+
var loaded;
|
|
1232
|
+
var load;
|
|
1233
|
+
var originalProcessReallyExit;
|
|
1234
|
+
var processReallyExit;
|
|
1235
|
+
var originalProcessEmit;
|
|
1236
|
+
var processEmit;
|
|
1237
|
+
}
|
|
1238
|
+
});
|
|
1239
|
+
|
|
1240
|
+
// ../../node_modules/.pnpm/proper-lockfile@4.1.2/node_modules/proper-lockfile/lib/mtime-precision.js
|
|
1241
|
+
var require_mtime_precision = __commonJS({
|
|
1242
|
+
"../../node_modules/.pnpm/proper-lockfile@4.1.2/node_modules/proper-lockfile/lib/mtime-precision.js"(exports, module) {
|
|
1243
|
+
"use strict";
|
|
1244
|
+
var cacheSymbol = /* @__PURE__ */ Symbol();
|
|
1245
|
+
function probe(file, fs8, callback) {
|
|
1246
|
+
const cachedPrecision = fs8[cacheSymbol];
|
|
1247
|
+
if (cachedPrecision) {
|
|
1248
|
+
return fs8.stat(file, (err, stat) => {
|
|
1249
|
+
if (err) {
|
|
1250
|
+
return callback(err);
|
|
1251
|
+
}
|
|
1252
|
+
callback(null, stat.mtime, cachedPrecision);
|
|
1253
|
+
});
|
|
1254
|
+
}
|
|
1255
|
+
const mtime = new Date(Math.ceil(Date.now() / 1e3) * 1e3 + 5);
|
|
1256
|
+
fs8.utimes(file, mtime, mtime, (err) => {
|
|
1257
|
+
if (err) {
|
|
1258
|
+
return callback(err);
|
|
1259
|
+
}
|
|
1260
|
+
fs8.stat(file, (err2, stat) => {
|
|
1261
|
+
if (err2) {
|
|
1262
|
+
return callback(err2);
|
|
1263
|
+
}
|
|
1264
|
+
const precision = stat.mtime.getTime() % 1e3 === 0 ? "s" : "ms";
|
|
1265
|
+
Object.defineProperty(fs8, cacheSymbol, { value: precision });
|
|
1266
|
+
callback(null, stat.mtime, precision);
|
|
1267
|
+
});
|
|
1268
|
+
});
|
|
1269
|
+
}
|
|
1270
|
+
function getMtime(precision) {
|
|
1271
|
+
let now = Date.now();
|
|
1272
|
+
if (precision === "s") {
|
|
1273
|
+
now = Math.ceil(now / 1e3) * 1e3;
|
|
1274
|
+
}
|
|
1275
|
+
return new Date(now);
|
|
1276
|
+
}
|
|
1277
|
+
module.exports.probe = probe;
|
|
1278
|
+
module.exports.getMtime = getMtime;
|
|
1279
|
+
}
|
|
1280
|
+
});
|
|
1281
|
+
|
|
1282
|
+
// ../../node_modules/.pnpm/proper-lockfile@4.1.2/node_modules/proper-lockfile/lib/lockfile.js
|
|
1283
|
+
var require_lockfile = __commonJS({
|
|
1284
|
+
"../../node_modules/.pnpm/proper-lockfile@4.1.2/node_modules/proper-lockfile/lib/lockfile.js"(exports, module) {
|
|
1285
|
+
"use strict";
|
|
1286
|
+
var path8 = __require("path");
|
|
1287
|
+
var fs8 = require_graceful_fs();
|
|
1288
|
+
var retry = require_retry2();
|
|
1289
|
+
var onExit = require_signal_exit();
|
|
1290
|
+
var mtimePrecision = require_mtime_precision();
|
|
1291
|
+
var locks = {};
|
|
1292
|
+
function getLockFile(file, options) {
|
|
1293
|
+
return options.lockfilePath || `${file}.lock`;
|
|
1294
|
+
}
|
|
1295
|
+
function resolveCanonicalPath(file, options, callback) {
|
|
1296
|
+
if (!options.realpath) {
|
|
1297
|
+
return callback(null, path8.resolve(file));
|
|
1298
|
+
}
|
|
1299
|
+
options.fs.realpath(file, callback);
|
|
1300
|
+
}
|
|
1301
|
+
function acquireLock(file, options, callback) {
|
|
1302
|
+
const lockfilePath = getLockFile(file, options);
|
|
1303
|
+
options.fs.mkdir(lockfilePath, (err) => {
|
|
1304
|
+
if (!err) {
|
|
1305
|
+
return mtimePrecision.probe(lockfilePath, options.fs, (err2, mtime, mtimePrecision2) => {
|
|
1306
|
+
if (err2) {
|
|
1307
|
+
options.fs.rmdir(lockfilePath, () => {
|
|
1308
|
+
});
|
|
1309
|
+
return callback(err2);
|
|
1310
|
+
}
|
|
1311
|
+
callback(null, mtime, mtimePrecision2);
|
|
1312
|
+
});
|
|
1313
|
+
}
|
|
1314
|
+
if (err.code !== "EEXIST") {
|
|
1315
|
+
return callback(err);
|
|
1316
|
+
}
|
|
1317
|
+
if (options.stale <= 0) {
|
|
1318
|
+
return callback(Object.assign(new Error("Lock file is already being held"), { code: "ELOCKED", file }));
|
|
1319
|
+
}
|
|
1320
|
+
options.fs.stat(lockfilePath, (err2, stat) => {
|
|
1321
|
+
if (err2) {
|
|
1322
|
+
if (err2.code === "ENOENT") {
|
|
1323
|
+
return acquireLock(file, { ...options, stale: 0 }, callback);
|
|
1324
|
+
}
|
|
1325
|
+
return callback(err2);
|
|
1326
|
+
}
|
|
1327
|
+
if (!isLockStale(stat, options)) {
|
|
1328
|
+
return callback(Object.assign(new Error("Lock file is already being held"), { code: "ELOCKED", file }));
|
|
1329
|
+
}
|
|
1330
|
+
removeLock(file, options, (err3) => {
|
|
1331
|
+
if (err3) {
|
|
1332
|
+
return callback(err3);
|
|
1333
|
+
}
|
|
1334
|
+
acquireLock(file, { ...options, stale: 0 }, callback);
|
|
1335
|
+
});
|
|
1336
|
+
});
|
|
1337
|
+
});
|
|
1338
|
+
}
|
|
1339
|
+
function isLockStale(stat, options) {
|
|
1340
|
+
return stat.mtime.getTime() < Date.now() - options.stale;
|
|
1341
|
+
}
|
|
1342
|
+
function removeLock(file, options, callback) {
|
|
1343
|
+
options.fs.rmdir(getLockFile(file, options), (err) => {
|
|
1344
|
+
if (err && err.code !== "ENOENT") {
|
|
1345
|
+
return callback(err);
|
|
1346
|
+
}
|
|
1347
|
+
callback();
|
|
1348
|
+
});
|
|
1349
|
+
}
|
|
1350
|
+
function updateLock(file, options) {
|
|
1351
|
+
const lock3 = locks[file];
|
|
1352
|
+
if (lock3.updateTimeout) {
|
|
1353
|
+
return;
|
|
1354
|
+
}
|
|
1355
|
+
lock3.updateDelay = lock3.updateDelay || options.update;
|
|
1356
|
+
lock3.updateTimeout = setTimeout(() => {
|
|
1357
|
+
lock3.updateTimeout = null;
|
|
1358
|
+
options.fs.stat(lock3.lockfilePath, (err, stat) => {
|
|
1359
|
+
const isOverThreshold = lock3.lastUpdate + options.stale < Date.now();
|
|
1360
|
+
if (err) {
|
|
1361
|
+
if (err.code === "ENOENT" || isOverThreshold) {
|
|
1362
|
+
return setLockAsCompromised(file, lock3, Object.assign(err, { code: "ECOMPROMISED" }));
|
|
1363
|
+
}
|
|
1364
|
+
lock3.updateDelay = 1e3;
|
|
1365
|
+
return updateLock(file, options);
|
|
1366
|
+
}
|
|
1367
|
+
const isMtimeOurs = lock3.mtime.getTime() === stat.mtime.getTime();
|
|
1368
|
+
if (!isMtimeOurs) {
|
|
1369
|
+
return setLockAsCompromised(
|
|
1370
|
+
file,
|
|
1371
|
+
lock3,
|
|
1372
|
+
Object.assign(
|
|
1373
|
+
new Error("Unable to update lock within the stale threshold"),
|
|
1374
|
+
{ code: "ECOMPROMISED" }
|
|
1375
|
+
)
|
|
1376
|
+
);
|
|
1377
|
+
}
|
|
1378
|
+
const mtime = mtimePrecision.getMtime(lock3.mtimePrecision);
|
|
1379
|
+
options.fs.utimes(lock3.lockfilePath, mtime, mtime, (err2) => {
|
|
1380
|
+
const isOverThreshold2 = lock3.lastUpdate + options.stale < Date.now();
|
|
1381
|
+
if (lock3.released) {
|
|
1382
|
+
return;
|
|
1383
|
+
}
|
|
1384
|
+
if (err2) {
|
|
1385
|
+
if (err2.code === "ENOENT" || isOverThreshold2) {
|
|
1386
|
+
return setLockAsCompromised(file, lock3, Object.assign(err2, { code: "ECOMPROMISED" }));
|
|
1387
|
+
}
|
|
1388
|
+
lock3.updateDelay = 1e3;
|
|
1389
|
+
return updateLock(file, options);
|
|
1390
|
+
}
|
|
1391
|
+
lock3.mtime = mtime;
|
|
1392
|
+
lock3.lastUpdate = Date.now();
|
|
1393
|
+
lock3.updateDelay = null;
|
|
1394
|
+
updateLock(file, options);
|
|
1395
|
+
});
|
|
1396
|
+
});
|
|
1397
|
+
}, lock3.updateDelay);
|
|
1398
|
+
if (lock3.updateTimeout.unref) {
|
|
1399
|
+
lock3.updateTimeout.unref();
|
|
1400
|
+
}
|
|
1401
|
+
}
|
|
1402
|
+
function setLockAsCompromised(file, lock3, err) {
|
|
1403
|
+
lock3.released = true;
|
|
1404
|
+
if (lock3.updateTimeout) {
|
|
1405
|
+
clearTimeout(lock3.updateTimeout);
|
|
1406
|
+
}
|
|
1407
|
+
if (locks[file] === lock3) {
|
|
1408
|
+
delete locks[file];
|
|
1409
|
+
}
|
|
1410
|
+
lock3.options.onCompromised(err);
|
|
1411
|
+
}
|
|
1412
|
+
function lock2(file, options, callback) {
|
|
1413
|
+
options = {
|
|
1414
|
+
stale: 1e4,
|
|
1415
|
+
update: null,
|
|
1416
|
+
realpath: true,
|
|
1417
|
+
retries: 0,
|
|
1418
|
+
fs: fs8,
|
|
1419
|
+
onCompromised: (err) => {
|
|
1420
|
+
throw err;
|
|
1421
|
+
},
|
|
1422
|
+
...options
|
|
1423
|
+
};
|
|
1424
|
+
options.retries = options.retries || 0;
|
|
1425
|
+
options.retries = typeof options.retries === "number" ? { retries: options.retries } : options.retries;
|
|
1426
|
+
options.stale = Math.max(options.stale || 0, 2e3);
|
|
1427
|
+
options.update = options.update == null ? options.stale / 2 : options.update || 0;
|
|
1428
|
+
options.update = Math.max(Math.min(options.update, options.stale / 2), 1e3);
|
|
1429
|
+
resolveCanonicalPath(file, options, (err, file2) => {
|
|
1430
|
+
if (err) {
|
|
1431
|
+
return callback(err);
|
|
1432
|
+
}
|
|
1433
|
+
const operation = retry.operation(options.retries);
|
|
1434
|
+
operation.attempt(() => {
|
|
1435
|
+
acquireLock(file2, options, (err2, mtime, mtimePrecision2) => {
|
|
1436
|
+
if (operation.retry(err2)) {
|
|
1437
|
+
return;
|
|
1438
|
+
}
|
|
1439
|
+
if (err2) {
|
|
1440
|
+
return callback(operation.mainError());
|
|
1441
|
+
}
|
|
1442
|
+
const lock3 = locks[file2] = {
|
|
1443
|
+
lockfilePath: getLockFile(file2, options),
|
|
1444
|
+
mtime,
|
|
1445
|
+
mtimePrecision: mtimePrecision2,
|
|
1446
|
+
options,
|
|
1447
|
+
lastUpdate: Date.now()
|
|
1448
|
+
};
|
|
1449
|
+
updateLock(file2, options);
|
|
1450
|
+
callback(null, (releasedCallback) => {
|
|
1451
|
+
if (lock3.released) {
|
|
1452
|
+
return releasedCallback && releasedCallback(Object.assign(new Error("Lock is already released"), { code: "ERELEASED" }));
|
|
1453
|
+
}
|
|
1454
|
+
unlock(file2, { ...options, realpath: false }, releasedCallback);
|
|
1455
|
+
});
|
|
1456
|
+
});
|
|
1457
|
+
});
|
|
1458
|
+
});
|
|
1459
|
+
}
|
|
1460
|
+
function unlock(file, options, callback) {
|
|
1461
|
+
options = {
|
|
1462
|
+
fs: fs8,
|
|
1463
|
+
realpath: true,
|
|
1464
|
+
...options
|
|
1465
|
+
};
|
|
1466
|
+
resolveCanonicalPath(file, options, (err, file2) => {
|
|
1467
|
+
if (err) {
|
|
1468
|
+
return callback(err);
|
|
1469
|
+
}
|
|
1470
|
+
const lock3 = locks[file2];
|
|
1471
|
+
if (!lock3) {
|
|
1472
|
+
return callback(Object.assign(new Error("Lock is not acquired/owned by you"), { code: "ENOTACQUIRED" }));
|
|
1473
|
+
}
|
|
1474
|
+
lock3.updateTimeout && clearTimeout(lock3.updateTimeout);
|
|
1475
|
+
lock3.released = true;
|
|
1476
|
+
delete locks[file2];
|
|
1477
|
+
removeLock(file2, options, callback);
|
|
1478
|
+
});
|
|
1479
|
+
}
|
|
1480
|
+
function check2(file, options, callback) {
|
|
1481
|
+
options = {
|
|
1482
|
+
stale: 1e4,
|
|
1483
|
+
realpath: true,
|
|
1484
|
+
fs: fs8,
|
|
1485
|
+
...options
|
|
1486
|
+
};
|
|
1487
|
+
options.stale = Math.max(options.stale || 0, 2e3);
|
|
1488
|
+
resolveCanonicalPath(file, options, (err, file2) => {
|
|
1489
|
+
if (err) {
|
|
1490
|
+
return callback(err);
|
|
1491
|
+
}
|
|
1492
|
+
options.fs.stat(getLockFile(file2, options), (err2, stat) => {
|
|
1493
|
+
if (err2) {
|
|
1494
|
+
return err2.code === "ENOENT" ? callback(null, false) : callback(err2);
|
|
1495
|
+
}
|
|
1496
|
+
return callback(null, !isLockStale(stat, options));
|
|
1497
|
+
});
|
|
1498
|
+
});
|
|
1499
|
+
}
|
|
1500
|
+
function getLocks() {
|
|
1501
|
+
return locks;
|
|
1502
|
+
}
|
|
1503
|
+
onExit(() => {
|
|
1504
|
+
for (const file in locks) {
|
|
1505
|
+
const options = locks[file].options;
|
|
1506
|
+
try {
|
|
1507
|
+
options.fs.rmdirSync(getLockFile(file, options));
|
|
1508
|
+
} catch (e) {
|
|
1509
|
+
}
|
|
1510
|
+
}
|
|
1511
|
+
});
|
|
1512
|
+
module.exports.lock = lock2;
|
|
1513
|
+
module.exports.unlock = unlock;
|
|
1514
|
+
module.exports.check = check2;
|
|
1515
|
+
module.exports.getLocks = getLocks;
|
|
1516
|
+
}
|
|
1517
|
+
});
|
|
1518
|
+
|
|
1519
|
+
// ../../node_modules/.pnpm/proper-lockfile@4.1.2/node_modules/proper-lockfile/lib/adapter.js
|
|
1520
|
+
var require_adapter = __commonJS({
|
|
1521
|
+
"../../node_modules/.pnpm/proper-lockfile@4.1.2/node_modules/proper-lockfile/lib/adapter.js"(exports, module) {
|
|
1522
|
+
"use strict";
|
|
1523
|
+
var fs8 = require_graceful_fs();
|
|
1524
|
+
function createSyncFs(fs9) {
|
|
1525
|
+
const methods = ["mkdir", "realpath", "stat", "rmdir", "utimes"];
|
|
1526
|
+
const newFs = { ...fs9 };
|
|
1527
|
+
methods.forEach((method) => {
|
|
1528
|
+
newFs[method] = (...args) => {
|
|
1529
|
+
const callback = args.pop();
|
|
1530
|
+
let ret;
|
|
1531
|
+
try {
|
|
1532
|
+
ret = fs9[`${method}Sync`](...args);
|
|
1533
|
+
} catch (err) {
|
|
1534
|
+
return callback(err);
|
|
1535
|
+
}
|
|
1536
|
+
callback(null, ret);
|
|
1537
|
+
};
|
|
1538
|
+
});
|
|
1539
|
+
return newFs;
|
|
1540
|
+
}
|
|
1541
|
+
function toPromise(method) {
|
|
1542
|
+
return (...args) => new Promise((resolve, reject) => {
|
|
1543
|
+
args.push((err, result) => {
|
|
1544
|
+
if (err) {
|
|
1545
|
+
reject(err);
|
|
1546
|
+
} else {
|
|
1547
|
+
resolve(result);
|
|
1548
|
+
}
|
|
1549
|
+
});
|
|
1550
|
+
method(...args);
|
|
1551
|
+
});
|
|
1552
|
+
}
|
|
1553
|
+
function toSync(method) {
|
|
1554
|
+
return (...args) => {
|
|
1555
|
+
let err;
|
|
1556
|
+
let result;
|
|
1557
|
+
args.push((_err, _result) => {
|
|
1558
|
+
err = _err;
|
|
1559
|
+
result = _result;
|
|
1560
|
+
});
|
|
1561
|
+
method(...args);
|
|
1562
|
+
if (err) {
|
|
1563
|
+
throw err;
|
|
1564
|
+
}
|
|
1565
|
+
return result;
|
|
1566
|
+
};
|
|
1567
|
+
}
|
|
1568
|
+
function toSyncOptions(options) {
|
|
1569
|
+
options = { ...options };
|
|
1570
|
+
options.fs = createSyncFs(options.fs || fs8);
|
|
1571
|
+
if (typeof options.retries === "number" && options.retries > 0 || options.retries && typeof options.retries.retries === "number" && options.retries.retries > 0) {
|
|
1572
|
+
throw Object.assign(new Error("Cannot use retries with the sync api"), { code: "ESYNC" });
|
|
1573
|
+
}
|
|
1574
|
+
return options;
|
|
1575
|
+
}
|
|
1576
|
+
module.exports = {
|
|
1577
|
+
toPromise,
|
|
1578
|
+
toSync,
|
|
1579
|
+
toSyncOptions
|
|
1580
|
+
};
|
|
1581
|
+
}
|
|
1582
|
+
});
|
|
1583
|
+
|
|
1584
|
+
// ../../node_modules/.pnpm/proper-lockfile@4.1.2/node_modules/proper-lockfile/index.js
|
|
1585
|
+
var require_proper_lockfile = __commonJS({
|
|
1586
|
+
"../../node_modules/.pnpm/proper-lockfile@4.1.2/node_modules/proper-lockfile/index.js"(exports, module) {
|
|
1587
|
+
"use strict";
|
|
1588
|
+
var lockfile = require_lockfile();
|
|
1589
|
+
var { toPromise, toSync, toSyncOptions } = require_adapter();
|
|
1590
|
+
async function lock2(file, options) {
|
|
1591
|
+
const release = await toPromise(lockfile.lock)(file, options);
|
|
1592
|
+
return toPromise(release);
|
|
1593
|
+
}
|
|
1594
|
+
function lockSync(file, options) {
|
|
1595
|
+
const release = toSync(lockfile.lock)(file, toSyncOptions(options));
|
|
1596
|
+
return toSync(release);
|
|
1597
|
+
}
|
|
1598
|
+
function unlock(file, options) {
|
|
1599
|
+
return toPromise(lockfile.unlock)(file, options);
|
|
1600
|
+
}
|
|
1601
|
+
function unlockSync(file, options) {
|
|
1602
|
+
return toSync(lockfile.unlock)(file, toSyncOptions(options));
|
|
1603
|
+
}
|
|
1604
|
+
function check2(file, options) {
|
|
1605
|
+
return toPromise(lockfile.check)(file, options);
|
|
1606
|
+
}
|
|
1607
|
+
function checkSync(file, options) {
|
|
1608
|
+
return toSync(lockfile.check)(file, toSyncOptions(options));
|
|
1609
|
+
}
|
|
1610
|
+
module.exports = lock2;
|
|
1611
|
+
module.exports.lock = lock2;
|
|
1612
|
+
module.exports.unlock = unlock;
|
|
1613
|
+
module.exports.lockSync = lockSync;
|
|
1614
|
+
module.exports.unlockSync = unlockSync;
|
|
1615
|
+
module.exports.check = check2;
|
|
1616
|
+
module.exports.checkSync = checkSync;
|
|
1617
|
+
}
|
|
1618
|
+
});
|
|
1619
|
+
|
|
35
1620
|
// ../../node_modules/.pnpm/ws@8.21.3/node_modules/ws/lib/constants.js
|
|
36
1621
|
var require_constants = __commonJS({
|
|
37
1622
|
"../../node_modules/.pnpm/ws@8.21.3/node_modules/ws/lib/constants.js"(exports, module) {
|
|
@@ -5247,11 +6832,111 @@ async function goalWorkspace(args, policy = {}) {
|
|
|
5247
6832
|
}
|
|
5248
6833
|
}
|
|
5249
6834
|
|
|
6835
|
+
// src/agent-runtime.ts
|
|
6836
|
+
var import_proper_lockfile = __toESM(require_proper_lockfile(), 1);
|
|
6837
|
+
import fs5 from "fs/promises";
|
|
6838
|
+
import { appendFileSync, mkdirSync, renameSync, statSync, openSync, closeSync } from "fs";
|
|
6839
|
+
import path5 from "path";
|
|
6840
|
+
import { spawn as spawn3 } from "child_process";
|
|
6841
|
+
var AGENT_LEASE_STALE_MS = 15e3;
|
|
6842
|
+
async function agentLeaseActive(directory) {
|
|
6843
|
+
return (0, import_proper_lockfile.check)(path5.join(directory, "execution"), {
|
|
6844
|
+
realpath: false,
|
|
6845
|
+
stale: AGENT_LEASE_STALE_MS
|
|
6846
|
+
});
|
|
6847
|
+
}
|
|
6848
|
+
async function tryAgentLease(directory, role = "execution") {
|
|
6849
|
+
await fs5.mkdir(directory, { recursive: true, mode: 448 });
|
|
6850
|
+
try {
|
|
6851
|
+
return await (0, import_proper_lockfile.lock)(path5.join(directory, role), {
|
|
6852
|
+
realpath: false,
|
|
6853
|
+
stale: AGENT_LEASE_STALE_MS,
|
|
6854
|
+
update: 3e3,
|
|
6855
|
+
retries: 0
|
|
6856
|
+
});
|
|
6857
|
+
} catch (error) {
|
|
6858
|
+
if (error.code === "ELOCKED") return null;
|
|
6859
|
+
throw error;
|
|
6860
|
+
}
|
|
6861
|
+
}
|
|
6862
|
+
function appendAgentEvent(directory, line) {
|
|
6863
|
+
try {
|
|
6864
|
+
mkdirSync(directory, { recursive: true, mode: 448 });
|
|
6865
|
+
const file = path5.join(directory, "events.log");
|
|
6866
|
+
if ((statSync(file, { throwIfNoEntry: false })?.size ?? 0) > 5 * 1024 * 1024) {
|
|
6867
|
+
renameSync(file, file + ".1");
|
|
6868
|
+
}
|
|
6869
|
+
appendFileSync(file, line.replace(/\x1b\[[0-9;]*m/g, ""), { mode: 384 });
|
|
6870
|
+
} catch {
|
|
6871
|
+
}
|
|
6872
|
+
}
|
|
6873
|
+
async function readAgentEvents(directory, cursor) {
|
|
6874
|
+
const file = path5.join(directory, "events.log");
|
|
6875
|
+
let handle;
|
|
6876
|
+
try {
|
|
6877
|
+
handle = await fs5.open(file, "r");
|
|
6878
|
+
const size = (await handle.stat()).size;
|
|
6879
|
+
const start = cursor === null ? Math.max(0, size - 16384) : cursor > size ? 0 : cursor;
|
|
6880
|
+
const buffer = Buffer.alloc(Math.min(size - start, 64 * 1024));
|
|
6881
|
+
const { bytesRead } = await handle.read(buffer, 0, buffer.length, start);
|
|
6882
|
+
const content = buffer.subarray(0, bytesRead).toString("utf8");
|
|
6883
|
+
return {
|
|
6884
|
+
cursor: start + bytesRead,
|
|
6885
|
+
text: cursor === null ? content.split("\n").slice(-21).join("\n") : content
|
|
6886
|
+
};
|
|
6887
|
+
} catch {
|
|
6888
|
+
return { cursor, text: "" };
|
|
6889
|
+
} finally {
|
|
6890
|
+
await handle?.close();
|
|
6891
|
+
}
|
|
6892
|
+
}
|
|
6893
|
+
async function superviseAgent(options) {
|
|
6894
|
+
let delay = options.delayMs ?? 1e3;
|
|
6895
|
+
while (!options.signal.aborted && await options.enabled()) {
|
|
6896
|
+
const startedAt = Date.now();
|
|
6897
|
+
const child = options.start();
|
|
6898
|
+
const abort = () => child.kill();
|
|
6899
|
+
options.signal.addEventListener("abort", abort, { once: true });
|
|
6900
|
+
await new Promise((resolve) => {
|
|
6901
|
+
child.once("error", () => resolve());
|
|
6902
|
+
child.once("close", () => resolve());
|
|
6903
|
+
if (options.signal.aborted) abort();
|
|
6904
|
+
});
|
|
6905
|
+
options.signal.removeEventListener("abort", abort);
|
|
6906
|
+
if (options.signal.aborted || !await options.enabled()) break;
|
|
6907
|
+
await new Promise((resolve) => {
|
|
6908
|
+
const finish = () => {
|
|
6909
|
+
clearTimeout(timer);
|
|
6910
|
+
options.signal.removeEventListener("abort", finish);
|
|
6911
|
+
resolve();
|
|
6912
|
+
};
|
|
6913
|
+
const timer = setTimeout(finish, delay);
|
|
6914
|
+
options.signal.addEventListener("abort", finish, { once: true });
|
|
6915
|
+
if (options.signal.aborted) finish();
|
|
6916
|
+
});
|
|
6917
|
+
delay = Date.now() - startedAt > 6e4 ? options.delayMs ?? 1e3 : Math.min(delay * 2, 3e4);
|
|
6918
|
+
}
|
|
6919
|
+
}
|
|
6920
|
+
function startSupervisedAgent(node, bundle, logs) {
|
|
6921
|
+
if (!logs) return spawn3(node, [bundle, "--agent"], { stdio: "inherit", windowsHide: true });
|
|
6922
|
+
mkdirSync(logs, { recursive: true, mode: 448 });
|
|
6923
|
+
const out = openSync(path5.join(logs, "agent.log"), "a", 384);
|
|
6924
|
+
let err;
|
|
6925
|
+
try {
|
|
6926
|
+
err = openSync(path5.join(logs, "agent-error.log"), "a", 384);
|
|
6927
|
+
return spawn3(node, [bundle, "--agent"], { stdio: ["ignore", out, err], windowsHide: true });
|
|
6928
|
+
} finally {
|
|
6929
|
+
closeSync(out);
|
|
6930
|
+
if (err !== void 0) closeSync(err);
|
|
6931
|
+
}
|
|
6932
|
+
}
|
|
6933
|
+
|
|
5250
6934
|
// src/index.ts
|
|
5251
6935
|
import os4 from "os";
|
|
5252
|
-
import
|
|
5253
|
-
import
|
|
5254
|
-
import { spawn as
|
|
6936
|
+
import path7 from "path";
|
|
6937
|
+
import fs7 from "fs/promises";
|
|
6938
|
+
import { spawn as spawn5 } from "child_process";
|
|
6939
|
+
import { randomUUID } from "crypto";
|
|
5255
6940
|
import process3 from "process";
|
|
5256
6941
|
import { createInterface } from "readline/promises";
|
|
5257
6942
|
import { fileURLToPath } from "url";
|
|
@@ -5269,26 +6954,43 @@ var wrapper_default = import_websocket.default;
|
|
|
5269
6954
|
|
|
5270
6955
|
// src/background.ts
|
|
5271
6956
|
import os3 from "os";
|
|
5272
|
-
import
|
|
5273
|
-
import
|
|
5274
|
-
import { spawn as
|
|
5275
|
-
var
|
|
5276
|
-
|
|
5277
|
-
|
|
5278
|
-
|
|
5279
|
-
|
|
5280
|
-
|
|
5281
|
-
|
|
5282
|
-
|
|
5283
|
-
|
|
6957
|
+
import path6 from "path";
|
|
6958
|
+
import fs6 from "fs/promises";
|
|
6959
|
+
import { spawn as spawn4 } from "child_process";
|
|
6960
|
+
var LegacyBackgroundAgentError = class extends Error {
|
|
6961
|
+
};
|
|
6962
|
+
function parseReleaseVersion(value) {
|
|
6963
|
+
if (!value) return null;
|
|
6964
|
+
const match = value.trim().match(/^(\d+)\.(\d+)\.(\d+)$/);
|
|
6965
|
+
if (!match) return null;
|
|
6966
|
+
return [Number(match[1]), Number(match[2]), Number(match[3])];
|
|
6967
|
+
}
|
|
6968
|
+
function isOlderRelease(current, target) {
|
|
6969
|
+
const a = parseReleaseVersion(current);
|
|
6970
|
+
const b = parseReleaseVersion(target);
|
|
6971
|
+
if (!a || !b) return false;
|
|
6972
|
+
if (a[0] !== b[0]) return a[0] < b[0];
|
|
6973
|
+
if (a[1] !== b[1]) return a[1] < b[1];
|
|
6974
|
+
return a[2] < b[2];
|
|
6975
|
+
}
|
|
6976
|
+
function windowsSupervisorLaunchScript(node, bundle) {
|
|
6977
|
+
const quote = (value) => "'" + value.replaceAll("'", "''") + "'";
|
|
6978
|
+
return "Start-Process -FilePath " + quote(node) + " -ArgumentList " + quote('"' + bundle + '" --supervise') + " -WindowStyle Hidden | Out-Null";
|
|
6979
|
+
}
|
|
5284
6980
|
async function run2(command, args, options = {}) {
|
|
5285
6981
|
return new Promise((resolve, reject) => {
|
|
5286
|
-
const child =
|
|
6982
|
+
const child = spawn4(command, args, {
|
|
5287
6983
|
stdio: ["ignore", "pipe", "pipe"],
|
|
5288
6984
|
windowsHide: true
|
|
5289
6985
|
});
|
|
5290
6986
|
let stdout = "";
|
|
5291
6987
|
let stderr = "";
|
|
6988
|
+
const timer = setTimeout(() => {
|
|
6989
|
+
child.kill();
|
|
6990
|
+
const detail = `${command} timed out after 10 seconds`;
|
|
6991
|
+
if (options.ignoreFailure) resolve({ code: 124, stdout, stderr: detail });
|
|
6992
|
+
else reject(new Error(detail));
|
|
6993
|
+
}, 1e4);
|
|
5292
6994
|
child.stdout?.on("data", (chunk) => {
|
|
5293
6995
|
stdout += chunk.toString();
|
|
5294
6996
|
});
|
|
@@ -5296,6 +6998,7 @@ async function run2(command, args, options = {}) {
|
|
|
5296
6998
|
stderr += chunk.toString();
|
|
5297
6999
|
});
|
|
5298
7000
|
child.once("error", (error) => {
|
|
7001
|
+
clearTimeout(timer);
|
|
5299
7002
|
if (options.ignoreFailure) {
|
|
5300
7003
|
resolve({ code: 1, stdout, stderr: stderr || error.message });
|
|
5301
7004
|
return;
|
|
@@ -5303,6 +7006,7 @@ async function run2(command, args, options = {}) {
|
|
|
5303
7006
|
reject(error);
|
|
5304
7007
|
});
|
|
5305
7008
|
child.once("close", (code) => {
|
|
7009
|
+
clearTimeout(timer);
|
|
5306
7010
|
const result = { code: code ?? 1, stdout, stderr };
|
|
5307
7011
|
if ((code ?? 1) !== 0 && !options.ignoreFailure) {
|
|
5308
7012
|
reject(
|
|
@@ -5316,48 +7020,70 @@ async function run2(command, args, options = {}) {
|
|
|
5316
7020
|
});
|
|
5317
7021
|
});
|
|
5318
7022
|
}
|
|
5319
|
-
function
|
|
5320
|
-
|
|
5321
|
-
|
|
5322
|
-
|
|
5323
|
-
|
|
5324
|
-
|
|
5325
|
-
|
|
5326
|
-
|
|
5327
|
-
|
|
5328
|
-
|
|
5329
|
-
|
|
5330
|
-
|
|
5331
|
-
|
|
7023
|
+
function createBackgroundController(options = {}) {
|
|
7024
|
+
const platform = options.platform ?? process.platform;
|
|
7025
|
+
const home = options.home ?? os3.homedir();
|
|
7026
|
+
const nodePath = options.nodePath ?? process.execPath;
|
|
7027
|
+
const uid = options.uid ?? process.getuid?.() ?? os3.userInfo().uid;
|
|
7028
|
+
const runCommand = options.run ?? run2;
|
|
7029
|
+
const wait = options.wait ?? ((ms) => new Promise((resolve) => setTimeout(resolve, ms)));
|
|
7030
|
+
const leaseActive = options.leaseActive ?? agentLeaseActive;
|
|
7031
|
+
const CONFIG_DIR2 = path6.join(home, ".remotearc");
|
|
7032
|
+
const AGENT_DIR = path6.join(CONFIG_DIR2, "agent");
|
|
7033
|
+
const LOG_DIR = path6.join(CONFIG_DIR2, "logs");
|
|
7034
|
+
const AGENT_BUNDLE = path6.join(AGENT_DIR, "remotelink.mjs");
|
|
7035
|
+
const AGENT_VERSION_FILE = path6.join(AGENT_DIR, "version");
|
|
7036
|
+
const MAC_LABEL = "app.remotearc.agent";
|
|
7037
|
+
const WINDOWS_RUN_KEY = "HKCU\\Software\\Microsoft\\Windows\\CurrentVersion\\Run";
|
|
7038
|
+
const WINDOWS_RUN_VALUE = "Remote Arc Agent";
|
|
7039
|
+
const LINUX_UNIT = "remotearc-agent.service";
|
|
7040
|
+
function xmlEscape(value) {
|
|
7041
|
+
return value.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">");
|
|
7042
|
+
}
|
|
7043
|
+
function psQuote(value) {
|
|
7044
|
+
return "'" + value.replaceAll("'", "''") + "'";
|
|
7045
|
+
}
|
|
7046
|
+
function unitQuote(value) {
|
|
7047
|
+
return JSON.stringify(value).replaceAll("%", "%%");
|
|
7048
|
+
}
|
|
7049
|
+
async function ensureBundle(sourcePath, version) {
|
|
7050
|
+
await fs6.mkdir(AGENT_DIR, { recursive: true });
|
|
7051
|
+
await fs6.mkdir(LOG_DIR, { recursive: true });
|
|
7052
|
+
if (path6.resolve(sourcePath) !== path6.resolve(AGENT_BUNDLE)) {
|
|
7053
|
+
const staging = AGENT_BUNDLE + "." + process.pid + ".tmp";
|
|
7054
|
+
await fs6.copyFile(sourcePath, staging);
|
|
7055
|
+
await fs6.rename(staging, AGENT_BUNDLE);
|
|
7056
|
+
if (platform !== "win32") {
|
|
7057
|
+
await fs6.chmod(AGENT_BUNDLE, 448).catch(() => void 0);
|
|
7058
|
+
}
|
|
7059
|
+
}
|
|
7060
|
+
if (version) {
|
|
7061
|
+
await fs6.writeFile(AGENT_VERSION_FILE, version + "\n", { mode: 384 });
|
|
5332
7062
|
}
|
|
5333
7063
|
}
|
|
5334
|
-
|
|
5335
|
-
|
|
7064
|
+
async function backgroundBundleVersion() {
|
|
7065
|
+
return fs6.readFile(AGENT_VERSION_FILE, "utf8").then((value) => value.trim() || null).catch(() => null);
|
|
5336
7066
|
}
|
|
5337
|
-
|
|
5338
|
-
|
|
5339
|
-
|
|
5340
|
-
|
|
5341
|
-
|
|
5342
|
-
|
|
5343
|
-
|
|
5344
|
-
|
|
5345
|
-
|
|
5346
|
-
}
|
|
5347
|
-
|
|
5348
|
-
|
|
5349
|
-
|
|
5350
|
-
await fs5.mkdir(path5.dirname(plistPath), { recursive: true });
|
|
5351
|
-
const stdoutPath = path5.join(LOG_DIR, "agent.log");
|
|
5352
|
-
const stderrPath = path5.join(LOG_DIR, "agent-error.log");
|
|
5353
|
-
const plist = `<?xml version="1.0" encoding="UTF-8"?>
|
|
7067
|
+
function macPlistPath() {
|
|
7068
|
+
return path6.join(home, "Library", "LaunchAgents", MAC_LABEL + ".plist");
|
|
7069
|
+
}
|
|
7070
|
+
function linuxUnitPath() {
|
|
7071
|
+
return path6.join(home, ".config", "systemd", "user", LINUX_UNIT);
|
|
7072
|
+
}
|
|
7073
|
+
async function enableMac(sourcePath, preserveCurrent, version) {
|
|
7074
|
+
await ensureBundle(sourcePath, version);
|
|
7075
|
+
const plistPath = macPlistPath();
|
|
7076
|
+
await fs6.mkdir(path6.dirname(plistPath), { recursive: true });
|
|
7077
|
+
const stdoutPath = path6.join(LOG_DIR, "agent.log");
|
|
7078
|
+
const stderrPath = path6.join(LOG_DIR, "agent-error.log");
|
|
7079
|
+
const plist = `<?xml version="1.0" encoding="UTF-8"?>
|
|
5354
7080
|
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
|
5355
7081
|
<plist version="1.0">
|
|
5356
7082
|
<dict>
|
|
5357
7083
|
<key>Label</key><string>${MAC_LABEL}</string>
|
|
5358
7084
|
<key>ProgramArguments</key>
|
|
5359
7085
|
<array>
|
|
5360
|
-
<string>${xmlEscape(
|
|
7086
|
+
<string>${xmlEscape(nodePath)}</string>
|
|
5361
7087
|
<string>${xmlEscape(AGENT_BUNDLE)}</string>
|
|
5362
7088
|
<string>--agent</string>
|
|
5363
7089
|
</array>
|
|
@@ -5370,7 +7096,7 @@ async function enableMac(sourcePath, preserveCurrent, version) {
|
|
|
5370
7096
|
<key>EnvironmentVariables</key>
|
|
5371
7097
|
<dict>
|
|
5372
7098
|
<key>PATH</key><string>${xmlEscape(process.env.PATH || "/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin")}</string>
|
|
5373
|
-
<key>HOME</key><string>${xmlEscape(
|
|
7099
|
+
<key>HOME</key><string>${xmlEscape(home)}</string>
|
|
5374
7100
|
</dict>
|
|
5375
7101
|
<key>ThrottleInterval</key><integer>5</integer>
|
|
5376
7102
|
<key>StandardOutPath</key><string>${xmlEscape(stdoutPath)}</string>
|
|
@@ -5378,211 +7104,321 @@ async function enableMac(sourcePath, preserveCurrent, version) {
|
|
|
5378
7104
|
</dict>
|
|
5379
7105
|
</plist>
|
|
5380
7106
|
`;
|
|
5381
|
-
|
|
5382
|
-
|
|
5383
|
-
|
|
5384
|
-
|
|
5385
|
-
|
|
5386
|
-
|
|
5387
|
-
|
|
5388
|
-
|
|
5389
|
-
ignoreFailure: true
|
|
5390
|
-
});
|
|
5391
|
-
if (!(preserveCurrent && loaded.code === 0)) {
|
|
5392
|
-
await run2("launchctl", ["bootout", domain + "/" + MAC_LABEL], {
|
|
7107
|
+
await fs6.writeFile(plistPath, plist, { mode: 384 });
|
|
7108
|
+
const domain = `gui/${uid}`;
|
|
7109
|
+
const loaded = await runCommand(
|
|
7110
|
+
"launchctl",
|
|
7111
|
+
["print", domain + "/" + MAC_LABEL],
|
|
7112
|
+
{ ignoreFailure: true }
|
|
7113
|
+
);
|
|
7114
|
+
await runCommand("launchctl", ["enable", domain + "/" + MAC_LABEL], {
|
|
5393
7115
|
ignoreFailure: true
|
|
5394
7116
|
});
|
|
5395
|
-
|
|
5396
|
-
|
|
7117
|
+
if (loaded.code !== 0) {
|
|
7118
|
+
const bootstrapped = await runCommand(
|
|
7119
|
+
"launchctl",
|
|
7120
|
+
["bootstrap", domain, plistPath],
|
|
7121
|
+
{ ignoreFailure: true }
|
|
7122
|
+
);
|
|
7123
|
+
if (bootstrapped.code !== 0) {
|
|
7124
|
+
const observed = await runCommand(
|
|
7125
|
+
"launchctl",
|
|
7126
|
+
["print", domain + "/" + MAC_LABEL],
|
|
7127
|
+
{ ignoreFailure: true }
|
|
7128
|
+
);
|
|
7129
|
+
if (observed.code !== 0) {
|
|
7130
|
+
throw new Error(
|
|
7131
|
+
"launchctl bootstrap exited with " + bootstrapped.code + ": " + (bootstrapped.stderr.trim() || bootstrapped.stdout.trim()) + ". The current terminal remains connected."
|
|
7132
|
+
);
|
|
7133
|
+
}
|
|
7134
|
+
}
|
|
7135
|
+
}
|
|
7136
|
+
await runCommand("launchctl", ["kickstart", domain + "/" + MAC_LABEL], {
|
|
5397
7137
|
ignoreFailure: true
|
|
5398
7138
|
});
|
|
7139
|
+
return backgroundAgentStatus2();
|
|
5399
7140
|
}
|
|
5400
|
-
|
|
5401
|
-
|
|
5402
|
-
|
|
5403
|
-
|
|
5404
|
-
const domain = `gui/${process.getuid?.() ?? os3.userInfo().uid}`;
|
|
5405
|
-
await run2("launchctl", ["disable", domain + "/" + MAC_LABEL], {
|
|
5406
|
-
ignoreFailure: true
|
|
5407
|
-
});
|
|
5408
|
-
await fs5.rm(plistPath, { force: true });
|
|
5409
|
-
if (stopCurrent) {
|
|
5410
|
-
await run2("launchctl", ["bootout", domain + "/" + MAC_LABEL], {
|
|
7141
|
+
async function disableMac(stopCurrent) {
|
|
7142
|
+
const plistPath = macPlistPath();
|
|
7143
|
+
const domain = `gui/${uid}`;
|
|
7144
|
+
await runCommand("launchctl", ["disable", domain + "/" + MAC_LABEL], {
|
|
5411
7145
|
ignoreFailure: true
|
|
5412
7146
|
});
|
|
7147
|
+
await fs6.rm(plistPath, { force: true });
|
|
7148
|
+
if (stopCurrent) {
|
|
7149
|
+
await runCommand("launchctl", ["bootout", domain + "/" + MAC_LABEL], {
|
|
7150
|
+
ignoreFailure: true
|
|
7151
|
+
});
|
|
7152
|
+
}
|
|
7153
|
+
return backgroundAgentStatus2();
|
|
5413
7154
|
}
|
|
5414
|
-
|
|
5415
|
-
|
|
5416
|
-
|
|
5417
|
-
|
|
5418
|
-
|
|
5419
|
-
|
|
5420
|
-
|
|
5421
|
-
|
|
5422
|
-
|
|
5423
|
-
|
|
5424
|
-
|
|
5425
|
-
|
|
5426
|
-
enabled
|
|
5427
|
-
|
|
5428
|
-
|
|
5429
|
-
pid
|
|
5430
|
-
|
|
5431
|
-
|
|
5432
|
-
|
|
5433
|
-
|
|
5434
|
-
|
|
5435
|
-
|
|
5436
|
-
|
|
5437
|
-
|
|
5438
|
-
|
|
7155
|
+
async function statusMac() {
|
|
7156
|
+
const plistPath = macPlistPath();
|
|
7157
|
+
const installed = await fs6.access(plistPath).then(() => true).catch(() => false);
|
|
7158
|
+
const domain = "gui/" + uid;
|
|
7159
|
+
const result = await runCommand(
|
|
7160
|
+
"launchctl",
|
|
7161
|
+
["print", domain + "/" + MAC_LABEL],
|
|
7162
|
+
{ ignoreFailure: true }
|
|
7163
|
+
);
|
|
7164
|
+
const disabled = await runCommand("launchctl", ["print-disabled", domain], {
|
|
7165
|
+
ignoreFailure: true
|
|
7166
|
+
});
|
|
7167
|
+
const enabled = installed && !disabled.stdout.includes('"' + MAC_LABEL + '" => true');
|
|
7168
|
+
const pidMatch = result.stdout.match(/\bpid = (\d+)/);
|
|
7169
|
+
const pid = pidMatch ? Number(pidMatch[1]) : null;
|
|
7170
|
+
const active = result.code === 0 && pid !== null && /\bstate = running\b/i.test(result.stdout);
|
|
7171
|
+
return {
|
|
7172
|
+
supported: true,
|
|
7173
|
+
enabled,
|
|
7174
|
+
active,
|
|
7175
|
+
service: "launchd",
|
|
7176
|
+
pid,
|
|
7177
|
+
workerPid: pid,
|
|
7178
|
+
version: await backgroundBundleVersion(),
|
|
7179
|
+
detail: enabled && !active ? "Background connection is configured but the launchd agent is not currently running." : void 0
|
|
7180
|
+
};
|
|
7181
|
+
}
|
|
7182
|
+
async function enableLinux(sourcePath, preserveCurrent, version) {
|
|
7183
|
+
await ensureBundle(sourcePath, version);
|
|
7184
|
+
const unitPath = linuxUnitPath();
|
|
7185
|
+
await fs6.mkdir(path6.dirname(unitPath), { recursive: true });
|
|
7186
|
+
const unit = `[Unit]
|
|
5439
7187
|
Description=Remote Arc background agent
|
|
5440
7188
|
After=network-online.target
|
|
5441
7189
|
Wants=network-online.target
|
|
5442
7190
|
|
|
5443
7191
|
[Service]
|
|
5444
7192
|
Type=simple
|
|
5445
|
-
ExecStart
|
|
7193
|
+
ExecStart=:${unitQuote(nodePath)} ${unitQuote(AGENT_BUNDLE)} --agent
|
|
5446
7194
|
Restart=on-failure
|
|
5447
7195
|
RestartSec=3
|
|
5448
7196
|
Environment=NODE_ENV=production
|
|
7197
|
+
Environment=${unitQuote("PATH=" + (process.env.PATH || "/usr/local/bin:/usr/bin:/bin"))}
|
|
7198
|
+
Environment=${unitQuote("HOME=" + home)}
|
|
5449
7199
|
|
|
5450
7200
|
[Install]
|
|
5451
7201
|
WantedBy=default.target
|
|
5452
7202
|
`;
|
|
5453
|
-
|
|
5454
|
-
|
|
5455
|
-
|
|
5456
|
-
|
|
5457
|
-
preserveCurrent ? ["--user", "enable", LINUX_UNIT] : ["--user", "enable", "--now", LINUX_UNIT]
|
|
5458
|
-
);
|
|
5459
|
-
return backgroundAgentStatus();
|
|
5460
|
-
}
|
|
5461
|
-
async function disableLinux(stopCurrent) {
|
|
5462
|
-
await run2(
|
|
5463
|
-
"systemctl",
|
|
5464
|
-
stopCurrent ? ["--user", "disable", "--now", LINUX_UNIT] : ["--user", "disable", LINUX_UNIT],
|
|
5465
|
-
{ ignoreFailure: true }
|
|
5466
|
-
);
|
|
5467
|
-
await fs5.rm(linuxUnitPath(), { force: true });
|
|
5468
|
-
if (stopCurrent) {
|
|
5469
|
-
await run2("systemctl", ["--user", "daemon-reload"], {
|
|
5470
|
-
ignoreFailure: true
|
|
5471
|
-
});
|
|
7203
|
+
await fs6.writeFile(unitPath, unit, { mode: 384 });
|
|
7204
|
+
await runCommand("systemctl", ["--user", "daemon-reload"]);
|
|
7205
|
+
await runCommand("systemctl", ["--user", "enable", "--now", LINUX_UNIT]);
|
|
7206
|
+
return backgroundAgentStatus2();
|
|
5472
7207
|
}
|
|
5473
|
-
|
|
5474
|
-
|
|
5475
|
-
|
|
5476
|
-
|
|
5477
|
-
|
|
5478
|
-
const pidResult = await run2("systemctl", ["--user", "show", LINUX_UNIT, "--property", "MainPID", "--value"], { ignoreFailure: true });
|
|
5479
|
-
const supported = !enabledResult.stderr.toLowerCase().includes("failed to connect to bus");
|
|
5480
|
-
const pidValue = Number(pidResult.stdout.trim());
|
|
5481
|
-
return {
|
|
5482
|
-
supported,
|
|
5483
|
-
enabled: enabledResult.code === 0,
|
|
5484
|
-
active: activeResult.code === 0 && Number.isFinite(pidValue) && pidValue > 0,
|
|
5485
|
-
service: supported ? "systemd-user" : "unsupported",
|
|
5486
|
-
pid: Number.isFinite(pidValue) && pidValue > 0 ? pidValue : null,
|
|
5487
|
-
version: await backgroundBundleVersion(),
|
|
5488
|
-
detail: supported ? void 0 : "systemd user services are unavailable"
|
|
5489
|
-
};
|
|
5490
|
-
}
|
|
5491
|
-
async function powershell(script, ignoreFailure = false) {
|
|
5492
|
-
const utf8Script = "$OutputEncoding = [Console]::OutputEncoding = [System.Text.UTF8Encoding]::new(); " + script;
|
|
5493
|
-
return run2(
|
|
5494
|
-
"powershell.exe",
|
|
5495
|
-
["-NoProfile", "-NonInteractive", "-ExecutionPolicy", "Bypass", "-Command", utf8Script],
|
|
5496
|
-
{ ignoreFailure }
|
|
5497
|
-
);
|
|
5498
|
-
}
|
|
5499
|
-
async function windowsAgentPid() {
|
|
5500
|
-
const escapedBundle = AGENT_BUNDLE.replaceAll("'", "''");
|
|
5501
|
-
const script = "$p = Get-CimInstance Win32_Process | Where-Object { $_.Name -ieq 'node.exe' -and $_.CommandLine -like '*" + escapedBundle + "*' -and $_.CommandLine -like '*--agent*' } | Select-Object -First 1 -ExpandProperty ProcessId; if ($null -ne $p) { Write-Output $p }";
|
|
5502
|
-
const result = await powershell(script, true);
|
|
5503
|
-
const pid = Number(result.stdout.trim());
|
|
5504
|
-
return Number.isFinite(pid) && pid > 0 ? pid : null;
|
|
5505
|
-
}
|
|
5506
|
-
async function enableWindows(sourcePath, preserveCurrent, version) {
|
|
5507
|
-
await ensureBundle(sourcePath, version);
|
|
5508
|
-
const command = '"' + process.execPath + '" "' + AGENT_BUNDLE + '" --agent';
|
|
5509
|
-
await run2("reg.exe", [
|
|
5510
|
-
"add",
|
|
5511
|
-
WINDOWS_RUN_KEY,
|
|
5512
|
-
"/v",
|
|
5513
|
-
WINDOWS_RUN_VALUE,
|
|
5514
|
-
"/t",
|
|
5515
|
-
"REG_SZ",
|
|
5516
|
-
"/d",
|
|
5517
|
-
command,
|
|
5518
|
-
"/f"
|
|
5519
|
-
]);
|
|
5520
|
-
if (!preserveCurrent && !await windowsAgentPid()) {
|
|
5521
|
-
const stdoutPath = path5.join(LOG_DIR, "agent.log");
|
|
5522
|
-
const stderrPath = path5.join(LOG_DIR, "agent-error.log");
|
|
5523
|
-
await powershell(
|
|
5524
|
-
"Start-Process -FilePath " + psQuote(process.execPath) + " -ArgumentList @(" + psQuote(AGENT_BUNDLE) + ", '--agent') -WindowStyle Hidden -RedirectStandardOutput " + psQuote(stdoutPath) + " -RedirectStandardError " + psQuote(stderrPath) + " | Out-Null"
|
|
7208
|
+
async function disableLinux(stopCurrent) {
|
|
7209
|
+
await runCommand(
|
|
7210
|
+
"systemctl",
|
|
7211
|
+
stopCurrent ? ["--user", "disable", "--now", LINUX_UNIT] : ["--user", "disable", LINUX_UNIT],
|
|
7212
|
+
{ ignoreFailure: true }
|
|
5525
7213
|
);
|
|
5526
|
-
await
|
|
7214
|
+
await fs6.rm(linuxUnitPath(), { force: true });
|
|
7215
|
+
if (stopCurrent) {
|
|
7216
|
+
await runCommand("systemctl", ["--user", "daemon-reload"], {
|
|
7217
|
+
ignoreFailure: true
|
|
7218
|
+
});
|
|
7219
|
+
}
|
|
7220
|
+
return backgroundAgentStatus2();
|
|
5527
7221
|
}
|
|
5528
|
-
|
|
5529
|
-
|
|
5530
|
-
|
|
5531
|
-
|
|
5532
|
-
|
|
7222
|
+
async function statusLinux() {
|
|
7223
|
+
const enabledResult = await runCommand(
|
|
7224
|
+
"systemctl",
|
|
7225
|
+
["--user", "is-enabled", LINUX_UNIT],
|
|
7226
|
+
{ ignoreFailure: true }
|
|
7227
|
+
);
|
|
7228
|
+
const activeResult = await runCommand(
|
|
7229
|
+
"systemctl",
|
|
7230
|
+
["--user", "is-active", LINUX_UNIT],
|
|
7231
|
+
{ ignoreFailure: true }
|
|
7232
|
+
);
|
|
7233
|
+
const pidResult = await runCommand(
|
|
7234
|
+
"systemctl",
|
|
7235
|
+
["--user", "show", LINUX_UNIT, "--property", "MainPID", "--value"],
|
|
7236
|
+
{ ignoreFailure: true }
|
|
7237
|
+
);
|
|
7238
|
+
const supported = !enabledResult.stderr.toLowerCase().includes("failed to connect to bus");
|
|
7239
|
+
const pidValue = Number(pidResult.stdout.trim());
|
|
7240
|
+
return {
|
|
7241
|
+
supported,
|
|
7242
|
+
enabled: enabledResult.code === 0,
|
|
7243
|
+
active: activeResult.code === 0 && Number.isFinite(pidValue) && pidValue > 0,
|
|
7244
|
+
service: supported ? "systemd-user" : "unsupported",
|
|
7245
|
+
pid: Number.isFinite(pidValue) && pidValue > 0 ? pidValue : null,
|
|
7246
|
+
workerPid: Number.isFinite(pidValue) && pidValue > 0 ? pidValue : null,
|
|
7247
|
+
version: await backgroundBundleVersion(),
|
|
7248
|
+
detail: supported ? void 0 : "systemd user services are unavailable"
|
|
7249
|
+
};
|
|
7250
|
+
}
|
|
7251
|
+
async function powershell(script, ignoreFailure = false) {
|
|
7252
|
+
const utf8Script = "$OutputEncoding = [Console]::OutputEncoding = [System.Text.UTF8Encoding]::new(); " + script;
|
|
7253
|
+
return runCommand(
|
|
7254
|
+
"powershell.exe",
|
|
7255
|
+
[
|
|
7256
|
+
"-NoProfile",
|
|
7257
|
+
"-NonInteractive",
|
|
7258
|
+
"-ExecutionPolicy",
|
|
7259
|
+
"Bypass",
|
|
7260
|
+
"-Command",
|
|
7261
|
+
utf8Script
|
|
7262
|
+
],
|
|
7263
|
+
{ ignoreFailure }
|
|
7264
|
+
);
|
|
7265
|
+
}
|
|
7266
|
+
async function windowsAgentPid(role = "--supervise") {
|
|
7267
|
+
const script = "$p = Get-CimInstance Win32_Process | Where-Object { $_.Name -ieq 'node.exe' -and $_.ExecutablePath -ieq " + psQuote(nodePath) + ` -and $_.CommandLine -match ('^"?' + [regex]::Escape(` + psQuote(nodePath) + `) + '"?\\s+"?' + [regex]::Escape(` + psQuote(AGENT_BUNDLE) + `) + '"?\\s+` + role + "(?:\\s|$)') } | Select-Object -First 1 -ExpandProperty ProcessId; if ($null -ne $p) { Write-Output $p }";
|
|
7268
|
+
const result = await powershell(script, true);
|
|
7269
|
+
const pid = Number(result.stdout.trim());
|
|
7270
|
+
return Number.isFinite(pid) && pid > 0 ? pid : null;
|
|
7271
|
+
}
|
|
7272
|
+
async function enableWindows(sourcePath, preserveCurrent, version) {
|
|
7273
|
+
await ensureBundle(sourcePath, version);
|
|
7274
|
+
const start = windowsSupervisorLaunchScript(nodePath, AGENT_BUNDLE);
|
|
7275
|
+
const encoded = Buffer.from(start, "utf16le").toString("base64");
|
|
7276
|
+
const command = "powershell.exe -NoProfile -NonInteractive -WindowStyle Hidden -EncodedCommand " + encoded;
|
|
7277
|
+
await runCommand("reg.exe", [
|
|
7278
|
+
"add",
|
|
7279
|
+
WINDOWS_RUN_KEY,
|
|
7280
|
+
"/v",
|
|
7281
|
+
WINDOWS_RUN_VALUE,
|
|
7282
|
+
"/t",
|
|
7283
|
+
"REG_SZ",
|
|
7284
|
+
"/d",
|
|
7285
|
+
command,
|
|
7286
|
+
"/f"
|
|
7287
|
+
]);
|
|
7288
|
+
if (!await windowsAgentPid()) await powershell(start);
|
|
7289
|
+
return backgroundAgentStatus2();
|
|
7290
|
+
}
|
|
7291
|
+
async function disableWindows(stopCurrent) {
|
|
7292
|
+
await runCommand(
|
|
7293
|
+
"reg.exe",
|
|
7294
|
+
["delete", WINDOWS_RUN_KEY, "/v", WINDOWS_RUN_VALUE, "/f"],
|
|
7295
|
+
{ ignoreFailure: true }
|
|
7296
|
+
);
|
|
7297
|
+
if (stopCurrent) {
|
|
7298
|
+
for (const role of ["--agent", "--supervise"]) {
|
|
7299
|
+
const pid = await windowsAgentPid(role);
|
|
7300
|
+
if (pid && pid !== process.pid)
|
|
7301
|
+
await powershell(
|
|
7302
|
+
"Stop-Process -Id " + pid + " -Force -ErrorAction SilentlyContinue",
|
|
7303
|
+
true
|
|
7304
|
+
);
|
|
7305
|
+
}
|
|
7306
|
+
}
|
|
7307
|
+
return backgroundAgentStatus2();
|
|
7308
|
+
}
|
|
7309
|
+
async function statusWindows() {
|
|
7310
|
+
const enabledResult = await runCommand(
|
|
7311
|
+
"reg.exe",
|
|
7312
|
+
["query", WINDOWS_RUN_KEY, "/v", WINDOWS_RUN_VALUE],
|
|
7313
|
+
{ ignoreFailure: true }
|
|
7314
|
+
);
|
|
5533
7315
|
const pid = await windowsAgentPid();
|
|
5534
|
-
|
|
5535
|
-
|
|
7316
|
+
return {
|
|
7317
|
+
supported: true,
|
|
7318
|
+
enabled: enabledResult.code === 0,
|
|
7319
|
+
active: pid !== null,
|
|
7320
|
+
service: "registry-run",
|
|
7321
|
+
pid,
|
|
7322
|
+
workerPid: await windowsAgentPid("--agent"),
|
|
7323
|
+
version: await backgroundBundleVersion(),
|
|
7324
|
+
detail: enabledResult.code === 0 && pid === null ? "Login startup is configured, but its supervisor is not running; recovery is unavailable." : void 0
|
|
7325
|
+
};
|
|
7326
|
+
}
|
|
7327
|
+
async function backgroundAgentStatus2() {
|
|
7328
|
+
if (platform === "darwin") return statusMac();
|
|
7329
|
+
if (platform === "win32") return statusWindows();
|
|
7330
|
+
if (platform === "linux") return statusLinux();
|
|
7331
|
+
return {
|
|
7332
|
+
supported: false,
|
|
7333
|
+
enabled: false,
|
|
7334
|
+
active: false,
|
|
7335
|
+
service: "unsupported",
|
|
7336
|
+
detail: "unsupported operating system"
|
|
7337
|
+
};
|
|
7338
|
+
}
|
|
7339
|
+
async function enableBackgroundAgent2(sourcePath, options2 = {}) {
|
|
7340
|
+
const preserveCurrent = options2.preserveCurrent ?? false;
|
|
7341
|
+
const before = await backgroundAgentStatus2();
|
|
7342
|
+
if (before.workerPid && before.workerPid !== process.pid) {
|
|
7343
|
+
let participates = await leaseActive(AGENT_DIR);
|
|
7344
|
+
for (let attempt = 0; !participates && attempt < 6; attempt++) {
|
|
7345
|
+
await wait(500);
|
|
7346
|
+
participates = await leaseActive(AGENT_DIR);
|
|
7347
|
+
}
|
|
7348
|
+
if (!participates) {
|
|
7349
|
+
const canUpgradeLegacy = isOlderRelease(before.version, options2.version) && before.enabled;
|
|
7350
|
+
if (!canUpgradeLegacy) {
|
|
7351
|
+
throw new LegacyBackgroundAgentError(
|
|
7352
|
+
"An existing background Agent does not hold the execution lease and cannot be identified as a safe older release. Stop it locally before retrying; this launch will not create a competing executor."
|
|
7353
|
+
);
|
|
7354
|
+
}
|
|
7355
|
+
if (platform === "darwin") await disableMac(true);
|
|
7356
|
+
else if (platform === "win32") await disableWindows(true);
|
|
7357
|
+
else if (platform === "linux") await disableLinux(true);
|
|
7358
|
+
else {
|
|
7359
|
+
throw new LegacyBackgroundAgentError(
|
|
7360
|
+
"The existing background Agent is older, but automatic handoff is not supported on this operating system."
|
|
7361
|
+
);
|
|
7362
|
+
}
|
|
7363
|
+
let stopped = false;
|
|
7364
|
+
for (let attempt = 0; attempt < 40; attempt++) {
|
|
7365
|
+
const status2 = await backgroundAgentStatus2();
|
|
7366
|
+
if (!status2.workerPid) {
|
|
7367
|
+
stopped = true;
|
|
7368
|
+
break;
|
|
7369
|
+
}
|
|
7370
|
+
await wait(250);
|
|
7371
|
+
}
|
|
7372
|
+
if (!stopped) {
|
|
7373
|
+
throw new LegacyBackgroundAgentError(
|
|
7374
|
+
"The older background Agent did not stop cleanly. Automatic upgrade was aborted before installing the new executor."
|
|
7375
|
+
);
|
|
7376
|
+
}
|
|
7377
|
+
}
|
|
7378
|
+
}
|
|
7379
|
+
if (platform === "darwin")
|
|
7380
|
+
await enableMac(sourcePath, preserveCurrent, options2.version);
|
|
7381
|
+
else if (platform === "win32")
|
|
7382
|
+
await enableWindows(sourcePath, preserveCurrent, options2.version);
|
|
7383
|
+
else if (platform === "linux")
|
|
7384
|
+
await enableLinux(sourcePath, preserveCurrent, options2.version);
|
|
7385
|
+
else return backgroundAgentStatus2();
|
|
7386
|
+
for (let attempt = 0; attempt < 20; attempt++) {
|
|
7387
|
+
const status2 = await backgroundAgentStatus2();
|
|
7388
|
+
if (status2.enabled && status2.active) return status2;
|
|
7389
|
+
if (!status2.supported) return status2;
|
|
7390
|
+
await wait(200);
|
|
5536
7391
|
}
|
|
7392
|
+
const status = await backgroundAgentStatus2();
|
|
7393
|
+
throw new Error(
|
|
7394
|
+
status.detail || "Background supervisor did not start; the current terminal remains connected."
|
|
7395
|
+
);
|
|
7396
|
+
}
|
|
7397
|
+
async function disableBackgroundAgent2(options2 = {}) {
|
|
7398
|
+
const stopCurrent = options2.stopCurrent ?? true;
|
|
7399
|
+
if (platform === "darwin") return disableMac(stopCurrent);
|
|
7400
|
+
if (platform === "win32") return disableWindows(stopCurrent);
|
|
7401
|
+
if (platform === "linux") return disableLinux(stopCurrent);
|
|
7402
|
+
return backgroundAgentStatus2();
|
|
5537
7403
|
}
|
|
5538
|
-
return backgroundAgentStatus();
|
|
5539
|
-
}
|
|
5540
|
-
async function statusWindows() {
|
|
5541
|
-
const enabledResult = await run2("reg.exe", ["query", WINDOWS_RUN_KEY, "/v", WINDOWS_RUN_VALUE], { ignoreFailure: true });
|
|
5542
|
-
const pid = await windowsAgentPid();
|
|
5543
|
-
return {
|
|
5544
|
-
supported: true,
|
|
5545
|
-
enabled: enabledResult.code === 0,
|
|
5546
|
-
active: pid !== null,
|
|
5547
|
-
service: "registry-run",
|
|
5548
|
-
pid,
|
|
5549
|
-
version: await backgroundBundleVersion(),
|
|
5550
|
-
detail: enabledResult.code === 0 && pid === null ? "Background connection is configured but the user-level agent is not currently running." : void 0
|
|
5551
|
-
};
|
|
5552
|
-
}
|
|
5553
|
-
async function backgroundAgentStatus() {
|
|
5554
|
-
if (process.platform === "darwin") return statusMac();
|
|
5555
|
-
if (process.platform === "win32") return statusWindows();
|
|
5556
|
-
if (process.platform === "linux") return statusLinux();
|
|
5557
7404
|
return {
|
|
5558
|
-
|
|
5559
|
-
|
|
5560
|
-
|
|
5561
|
-
service: "unsupported",
|
|
5562
|
-
detail: "unsupported operating system"
|
|
7405
|
+
backgroundAgentStatus: backgroundAgentStatus2,
|
|
7406
|
+
enableBackgroundAgent: enableBackgroundAgent2,
|
|
7407
|
+
disableBackgroundAgent: disableBackgroundAgent2
|
|
5563
7408
|
};
|
|
5564
7409
|
}
|
|
5565
|
-
|
|
5566
|
-
|
|
5567
|
-
|
|
5568
|
-
|
|
5569
|
-
|
|
5570
|
-
return backgroundAgentStatus();
|
|
5571
|
-
}
|
|
5572
|
-
async function disableBackgroundAgent(options = {}) {
|
|
5573
|
-
const stopCurrent = options.stopCurrent ?? true;
|
|
5574
|
-
if (process.platform === "darwin") return disableMac(stopCurrent);
|
|
5575
|
-
if (process.platform === "win32") return disableWindows(stopCurrent);
|
|
5576
|
-
if (process.platform === "linux") return disableLinux(stopCurrent);
|
|
5577
|
-
return backgroundAgentStatus();
|
|
5578
|
-
}
|
|
7410
|
+
var {
|
|
7411
|
+
backgroundAgentStatus,
|
|
7412
|
+
enableBackgroundAgent,
|
|
7413
|
+
disableBackgroundAgent
|
|
7414
|
+
} = createBackgroundController();
|
|
5579
7415
|
|
|
5580
7416
|
// src/index.ts
|
|
5581
|
-
var VERSION = "0.4.
|
|
7417
|
+
var VERSION = "0.4.5";
|
|
5582
7418
|
var DEFAULT_ORIGIN = "https://mcp.remotearc.app";
|
|
5583
|
-
var
|
|
5584
|
-
var CONFIG_PATH =
|
|
5585
|
-
var LEGACY_CONFIG_PATH =
|
|
7419
|
+
var CONFIG_DIR = path7.join(os4.homedir(), ".remotearc");
|
|
7420
|
+
var CONFIG_PATH = path7.join(CONFIG_DIR, "config.json");
|
|
7421
|
+
var LEGACY_CONFIG_PATH = path7.join(os4.homedir(), ".remote-link", "config.json");
|
|
5586
7422
|
var SELF_PATH = fileURLToPath(import.meta.url);
|
|
5587
7423
|
var RevokedDeviceCredentialError = class extends Error {
|
|
5588
7424
|
constructor() {
|
|
@@ -5696,12 +7532,14 @@ function nowTime() {
|
|
|
5696
7532
|
function logLine(level, message) {
|
|
5697
7533
|
const icon = level === "success" ? green("\u2713") : level === "warn" ? yellow("!") : level === "error" ? red("\xD7") : level === "event" ? cyan("\u2192") : cyan("\u2022");
|
|
5698
7534
|
process3.stdout.write(`${dim(nowTime())} ${icon} ${message}
|
|
7535
|
+
`);
|
|
7536
|
+
appendAgentEvent(path7.join(CONFIG_DIR, "logs"), `${nowTime()} ${level} ${message}
|
|
5699
7537
|
`);
|
|
5700
7538
|
}
|
|
5701
7539
|
function banner() {
|
|
5702
7540
|
process3.stdout.write("\n");
|
|
5703
7541
|
process3.stdout.write(bold("Remote Arc") + " " + dim(`v${VERSION}`) + "\n");
|
|
5704
|
-
process3.stdout.write(dim("
|
|
7542
|
+
process3.stdout.write(dim("Persistent agent runtime for your computers") + "\n\n");
|
|
5705
7543
|
}
|
|
5706
7544
|
function argFlag(name) {
|
|
5707
7545
|
return process3.argv.includes(name);
|
|
@@ -5718,11 +7556,11 @@ function modeLabel(mode) {
|
|
|
5718
7556
|
}
|
|
5719
7557
|
async function readConfig() {
|
|
5720
7558
|
try {
|
|
5721
|
-
return JSON.parse(await
|
|
7559
|
+
return JSON.parse(await fs7.readFile(CONFIG_PATH, "utf8"));
|
|
5722
7560
|
} catch {
|
|
5723
7561
|
try {
|
|
5724
7562
|
const legacy = JSON.parse(
|
|
5725
|
-
await
|
|
7563
|
+
await fs7.readFile(LEGACY_CONFIG_PATH, "utf8")
|
|
5726
7564
|
);
|
|
5727
7565
|
await writeConfig(legacy);
|
|
5728
7566
|
logLine("success", "Migrated existing Remote Link pairing to Remote Arc.");
|
|
@@ -5733,22 +7571,26 @@ async function readConfig() {
|
|
|
5733
7571
|
}
|
|
5734
7572
|
}
|
|
5735
7573
|
async function writeConfig(config) {
|
|
5736
|
-
await
|
|
5737
|
-
|
|
5738
|
-
|
|
5739
|
-
|
|
7574
|
+
await fs7.mkdir(CONFIG_DIR, { recursive: true, mode: 448 });
|
|
7575
|
+
const staging = CONFIG_PATH + "." + randomUUID() + ".tmp";
|
|
7576
|
+
try {
|
|
7577
|
+
await fs7.writeFile(staging, JSON.stringify(config, null, 2) + "\n", { mode: 384 });
|
|
7578
|
+
await fs7.rename(staging, CONFIG_PATH);
|
|
7579
|
+
} finally {
|
|
7580
|
+
await fs7.rm(staging, { force: true });
|
|
7581
|
+
}
|
|
5740
7582
|
}
|
|
5741
7583
|
async function resetConfig() {
|
|
5742
7584
|
await Promise.all([
|
|
5743
|
-
|
|
5744
|
-
|
|
7585
|
+
fs7.rm(CONFIG_PATH, { force: true }),
|
|
7586
|
+
fs7.rm(LEGACY_CONFIG_PATH, { force: true })
|
|
5745
7587
|
]);
|
|
5746
7588
|
logLine("success", "Removed saved device credentials.");
|
|
5747
7589
|
}
|
|
5748
7590
|
function openBrowser(url) {
|
|
5749
7591
|
const command = process3.platform === "win32" ? "cmd" : process3.platform === "darwin" ? "open" : "xdg-open";
|
|
5750
7592
|
const args = process3.platform === "win32" ? ["/c", "start", "", url] : [url];
|
|
5751
|
-
const child =
|
|
7593
|
+
const child = spawn5(command, args, {
|
|
5752
7594
|
detached: true,
|
|
5753
7595
|
stdio: "ignore"
|
|
5754
7596
|
});
|
|
@@ -5855,9 +7697,13 @@ async function connectAgent(config) {
|
|
|
5855
7697
|
}
|
|
5856
7698
|
const wsUrl = new URL("/agent", config.origin.replace(/^http/, "ws"));
|
|
5857
7699
|
let stopped = false;
|
|
7700
|
+
let rePair = false;
|
|
5858
7701
|
let backoff = 1e3;
|
|
7702
|
+
let currentSocket = null;
|
|
7703
|
+
let backgroundSettings = Promise.resolve();
|
|
5859
7704
|
const shutdown = async () => {
|
|
5860
7705
|
stopped = true;
|
|
7706
|
+
currentSocket?.terminate();
|
|
5861
7707
|
keepAwake.close();
|
|
5862
7708
|
await core.close().catch(() => void 0);
|
|
5863
7709
|
};
|
|
@@ -5870,6 +7716,15 @@ async function connectAgent(config) {
|
|
|
5870
7716
|
Authorization: "Bearer " + config.deviceToken
|
|
5871
7717
|
}
|
|
5872
7718
|
});
|
|
7719
|
+
currentSocket = ws;
|
|
7720
|
+
const send = (message) => {
|
|
7721
|
+
if (ws.readyState !== wrapper_default.OPEN) return;
|
|
7722
|
+
try {
|
|
7723
|
+
ws.send(JSON.stringify(message));
|
|
7724
|
+
} catch {
|
|
7725
|
+
ws.terminate();
|
|
7726
|
+
}
|
|
7727
|
+
};
|
|
5873
7728
|
const absorbSocketError = () => void 0;
|
|
5874
7729
|
ws.on("error", absorbSocketError);
|
|
5875
7730
|
try {
|
|
@@ -5905,29 +7760,48 @@ async function connectAgent(config) {
|
|
|
5905
7760
|
ws.once("unexpected-response", onUnexpectedResponse);
|
|
5906
7761
|
});
|
|
5907
7762
|
backoff = 1e3;
|
|
5908
|
-
|
|
5909
|
-
|
|
5910
|
-
|
|
5911
|
-
|
|
5912
|
-
|
|
5913
|
-
|
|
5914
|
-
|
|
5915
|
-
|
|
5916
|
-
|
|
5917
|
-
|
|
5918
|
-
|
|
5919
|
-
|
|
5920
|
-
|
|
5921
|
-
|
|
5922
|
-
|
|
5923
|
-
|
|
5924
|
-
|
|
5925
|
-
|
|
5926
|
-
|
|
5927
|
-
|
|
5928
|
-
|
|
5929
|
-
|
|
5930
|
-
|
|
7763
|
+
const connectedAt = (/* @__PURE__ */ new Date()).toISOString();
|
|
7764
|
+
const publishPresence = async () => {
|
|
7765
|
+
const saved = await readConfig();
|
|
7766
|
+
if (!saved || saved.deviceId !== config.deviceId || saved.deviceToken !== config.deviceToken) {
|
|
7767
|
+
logLine("warn", "The local pairing changed or was removed; stopping this execution owner.");
|
|
7768
|
+
await shutdown();
|
|
7769
|
+
return;
|
|
7770
|
+
}
|
|
7771
|
+
const local = await backgroundAgentStatus().catch(() => null);
|
|
7772
|
+
const recovery = local ? { ...local, enabled: saved?.backgroundEnabled === true && local.enabled && local.active } : null;
|
|
7773
|
+
if (ws.readyState !== wrapper_default.OPEN) return;
|
|
7774
|
+
ws.send(
|
|
7775
|
+
JSON.stringify({
|
|
7776
|
+
type: "hello",
|
|
7777
|
+
device: {
|
|
7778
|
+
id: config.deviceId,
|
|
7779
|
+
name: config.deviceName,
|
|
7780
|
+
platform: process3.platform,
|
|
7781
|
+
arch: process3.arch,
|
|
7782
|
+
hostname: os4.hostname(),
|
|
7783
|
+
agentVersion: VERSION,
|
|
7784
|
+
pid: process3.pid,
|
|
7785
|
+
backgroundProcess: argFlag("--agent"),
|
|
7786
|
+
connectedAt,
|
|
7787
|
+
recoveryEnabled: recovery?.enabled ?? false,
|
|
7788
|
+
supervisorActive: recovery?.active,
|
|
7789
|
+
supervisorPid: recovery?.pid,
|
|
7790
|
+
supervisorService: recovery?.service
|
|
7791
|
+
},
|
|
7792
|
+
tools: [...tools.map((tool) => tool.name), ...internalTools],
|
|
7793
|
+
capabilities: [
|
|
7794
|
+
"native_core_v1",
|
|
7795
|
+
"device_policy_v1",
|
|
7796
|
+
"undo_history_v1",
|
|
7797
|
+
"background_agent_v1",
|
|
7798
|
+
"background_recovery_v2"
|
|
7799
|
+
]
|
|
7800
|
+
})
|
|
7801
|
+
);
|
|
7802
|
+
};
|
|
7803
|
+
await publishPresence();
|
|
7804
|
+
const presenceTimer = setInterval(() => void publishPresence().catch(() => void 0), 3e4);
|
|
5931
7805
|
logLine("success", `Relay connected \xB7 ${bold(config.deviceName)} \xB7 ${config.mode} mode`);
|
|
5932
7806
|
logLine("success", "Device presence published.");
|
|
5933
7807
|
process3.stdout.write(" " + dim(config.origin) + "\n");
|
|
@@ -5942,7 +7816,7 @@ async function connectAgent(config) {
|
|
|
5942
7816
|
"content-type": "application/json"
|
|
5943
7817
|
},
|
|
5944
7818
|
body: JSON.stringify({
|
|
5945
|
-
background_enabled: background?.enabled,
|
|
7819
|
+
background_enabled: background ? (await readConfig())?.backgroundEnabled === true && background.enabled && background.active : void 0,
|
|
5946
7820
|
background_process: argFlag("--agent"),
|
|
5947
7821
|
background_service: background?.service
|
|
5948
7822
|
})
|
|
@@ -6011,29 +7885,32 @@ async function connectAgent(config) {
|
|
|
6011
7885
|
if (typeof enabled !== "boolean") {
|
|
6012
7886
|
throw new Error("enabled must be a boolean");
|
|
6013
7887
|
}
|
|
6014
|
-
|
|
6015
|
-
|
|
6016
|
-
|
|
6017
|
-
|
|
6018
|
-
|
|
6019
|
-
...
|
|
6020
|
-
|
|
6021
|
-
|
|
6022
|
-
|
|
6023
|
-
|
|
6024
|
-
|
|
6025
|
-
|
|
6026
|
-
|
|
6027
|
-
|
|
6028
|
-
|
|
6029
|
-
|
|
6030
|
-
|
|
6031
|
-
|
|
6032
|
-
|
|
6033
|
-
|
|
6034
|
-
|
|
6035
|
-
|
|
6036
|
-
|
|
7888
|
+
const change = backgroundSettings.then(async () => {
|
|
7889
|
+
config = { ...await readConfig() || config, backgroundEnabled: enabled };
|
|
7890
|
+
await writeConfig(config);
|
|
7891
|
+
if (enabled) {
|
|
7892
|
+
const current = await backgroundAgentStatus();
|
|
7893
|
+
result = current.enabled && current.active ? { ...current, desired_enabled: true } : {
|
|
7894
|
+
...await enableBackgroundAgent(SELF_PATH, {
|
|
7895
|
+
preserveCurrent: argFlag("--agent"),
|
|
7896
|
+
version: VERSION
|
|
7897
|
+
}),
|
|
7898
|
+
desired_enabled: true
|
|
7899
|
+
};
|
|
7900
|
+
} else {
|
|
7901
|
+
const stopCurrent = message.arguments?.stop_current === true;
|
|
7902
|
+
const runningAsBackgroundAgent = argFlag("--agent");
|
|
7903
|
+
result = {
|
|
7904
|
+
...await disableBackgroundAgent({
|
|
7905
|
+
stopCurrent: stopCurrent && !runningAsBackgroundAgent
|
|
7906
|
+
}),
|
|
7907
|
+
desired_enabled: false
|
|
7908
|
+
};
|
|
7909
|
+
exitAfterResponse = stopCurrent && runningAsBackgroundAgent;
|
|
7910
|
+
}
|
|
7911
|
+
});
|
|
7912
|
+
backgroundSettings = change.catch(() => void 0);
|
|
7913
|
+
await change;
|
|
6037
7914
|
} else {
|
|
6038
7915
|
result = await core.call(
|
|
6039
7916
|
message.tool,
|
|
@@ -6042,30 +7919,31 @@ async function connectAgent(config) {
|
|
|
6042
7919
|
);
|
|
6043
7920
|
}
|
|
6044
7921
|
logLine("success", `tool.done ${message.tool} \xB7 ${Date.now() - callStarted}ms`);
|
|
6045
|
-
|
|
6046
|
-
|
|
6047
|
-
|
|
6048
|
-
|
|
6049
|
-
|
|
6050
|
-
|
|
6051
|
-
|
|
7922
|
+
send({
|
|
7923
|
+
type: "result",
|
|
7924
|
+
id: message.id,
|
|
7925
|
+
result
|
|
7926
|
+
});
|
|
7927
|
+
if (message.tool === "set_background_agent") {
|
|
7928
|
+
await publishPresence();
|
|
7929
|
+
void sendHeartbeat();
|
|
7930
|
+
}
|
|
6052
7931
|
if (exitAfterResponse) {
|
|
6053
|
-
setTimeout(() =>
|
|
7932
|
+
setTimeout(() => void shutdown(), 500);
|
|
6054
7933
|
}
|
|
6055
7934
|
} catch (error) {
|
|
6056
7935
|
logLine("error", `tool.fail ${message.tool} \xB7 ${error instanceof Error ? error.message : String(error)}`);
|
|
6057
|
-
|
|
6058
|
-
|
|
6059
|
-
|
|
6060
|
-
|
|
6061
|
-
|
|
6062
|
-
})
|
|
6063
|
-
);
|
|
7936
|
+
send({
|
|
7937
|
+
type: "result",
|
|
7938
|
+
id: message.id,
|
|
7939
|
+
error: error instanceof Error ? error.message : String(error)
|
|
7940
|
+
});
|
|
6064
7941
|
}
|
|
6065
7942
|
});
|
|
6066
7943
|
ws.once("close", resolve);
|
|
6067
7944
|
ws.once("error", resolve);
|
|
6068
7945
|
});
|
|
7946
|
+
clearInterval(presenceTimer);
|
|
6069
7947
|
clearInterval(heartbeatTimer);
|
|
6070
7948
|
clearInterval(approvalTimer);
|
|
6071
7949
|
clearInterval(livenessTimer);
|
|
@@ -6074,8 +7952,8 @@ async function connectAgent(config) {
|
|
|
6074
7952
|
logLine("warn", error.message);
|
|
6075
7953
|
await resetConfig();
|
|
6076
7954
|
logLine("event", "Starting a fresh device pairing\u2026");
|
|
6077
|
-
|
|
6078
|
-
|
|
7955
|
+
rePair = true;
|
|
7956
|
+
await shutdown();
|
|
6079
7957
|
}
|
|
6080
7958
|
logLine(
|
|
6081
7959
|
"error",
|
|
@@ -6105,8 +7983,10 @@ async function connectAgent(config) {
|
|
|
6105
7983
|
backoff = Math.min(backoff * 2, 3e4);
|
|
6106
7984
|
}
|
|
6107
7985
|
}
|
|
7986
|
+
process3.off("SIGINT", shutdown);
|
|
7987
|
+
process3.off("SIGTERM", shutdown);
|
|
6108
7988
|
await core.close().catch(() => void 0);
|
|
6109
|
-
return "stopped";
|
|
7989
|
+
return rePair ? "rePair" : "stopped";
|
|
6110
7990
|
}
|
|
6111
7991
|
async function main() {
|
|
6112
7992
|
if (argFlag("--help") || argFlag("-h")) {
|
|
@@ -6123,9 +8003,9 @@ async function main() {
|
|
|
6123
8003
|
"Options:",
|
|
6124
8004
|
" --safe Hard local read-only cap; dashboard cannot enable write tools",
|
|
6125
8005
|
" --developer Legacy alias for dashboard-managed capabilities",
|
|
6126
|
-
" --foreground
|
|
6127
|
-
" --background Enable
|
|
6128
|
-
" --no-background Disable
|
|
8006
|
+
" --foreground Stay attached without installing or repairing recovery",
|
|
8007
|
+
" --background Enable process recovery and keep this terminal attached",
|
|
8008
|
+
" --no-background Disable recovery; preserve the currently executing Agent",
|
|
6129
8009
|
" --reset Remove local pairing and background-agent registration",
|
|
6130
8010
|
" --version Print CLI version",
|
|
6131
8011
|
" --help Show this help",
|
|
@@ -6146,6 +8026,7 @@ async function main() {
|
|
|
6146
8026
|
const origin = process3.env.REMOTEARC_ORIGIN || process3.env.REMOTE_LINK_ORIGIN || process3.argv.find((value) => value.startsWith("--origin="))?.slice(9) || DEFAULT_ORIGIN;
|
|
6147
8027
|
const agentMode = argFlag("--agent");
|
|
6148
8028
|
const foregroundMode = argFlag("--foreground");
|
|
8029
|
+
const supervisorMode = argFlag("--supervise");
|
|
6149
8030
|
const disableBackground = argFlag("--no-background");
|
|
6150
8031
|
const enableBackground = argFlag("--background");
|
|
6151
8032
|
let config = await readConfig();
|
|
@@ -6156,45 +8037,67 @@ async function main() {
|
|
|
6156
8037
|
logLine("info", "Migrated relay origin to " + DEFAULT_ORIGIN);
|
|
6157
8038
|
}
|
|
6158
8039
|
if (!config) {
|
|
6159
|
-
if (agentMode) return;
|
|
8040
|
+
if (agentMode || supervisorMode) return;
|
|
6160
8041
|
config = await pair(origin, selectedMode());
|
|
6161
|
-
} else if (argFlag("--safe") || argFlag("--developer")) {
|
|
6162
|
-
config.mode = argFlag("--safe") ? "safe" : "managed";
|
|
6163
|
-
await writeConfig(config);
|
|
6164
8042
|
}
|
|
6165
8043
|
if (disableBackground) {
|
|
6166
8044
|
config.backgroundEnabled = false;
|
|
6167
8045
|
await writeConfig(config);
|
|
6168
|
-
await disableBackgroundAgent({ stopCurrent:
|
|
8046
|
+
await disableBackgroundAgent({ stopCurrent: false }).catch(() => void 0);
|
|
6169
8047
|
} else if (enableBackground) {
|
|
6170
8048
|
config.backgroundEnabled = true;
|
|
6171
8049
|
await writeConfig(config);
|
|
6172
8050
|
}
|
|
6173
8051
|
logLine("info", `Using paired device identity ${dim(config.deviceId.slice(0, 8))}\u2026`);
|
|
6174
|
-
if (
|
|
6175
|
-
|
|
6176
|
-
|
|
6177
|
-
|
|
8052
|
+
if (supervisorMode) {
|
|
8053
|
+
const release2 = await tryAgentLease(path7.join(CONFIG_DIR, "agent"), "supervisor");
|
|
8054
|
+
if (!release2) return;
|
|
8055
|
+
const abort2 = new AbortController();
|
|
8056
|
+
const stop = () => abort2.abort();
|
|
8057
|
+
process3.on("SIGINT", stop);
|
|
8058
|
+
process3.on("SIGTERM", stop);
|
|
8059
|
+
try {
|
|
8060
|
+
await superviseAgent({
|
|
8061
|
+
enabled: async () => (await readConfig())?.backgroundEnabled === true,
|
|
8062
|
+
signal: abort2.signal,
|
|
8063
|
+
start: () => startSupervisedAgent(process3.execPath, SELF_PATH, path7.join(CONFIG_DIR, "logs"))
|
|
8064
|
+
});
|
|
8065
|
+
} finally {
|
|
8066
|
+
process3.off("SIGINT", stop);
|
|
8067
|
+
process3.off("SIGTERM", stop);
|
|
8068
|
+
await release2();
|
|
8069
|
+
}
|
|
6178
8070
|
return;
|
|
6179
8071
|
}
|
|
6180
|
-
if (
|
|
8072
|
+
if (agentMode && config.backgroundEnabled !== true) return;
|
|
8073
|
+
if (!agentMode && !foregroundMode && config.backgroundEnabled === true) {
|
|
6181
8074
|
try {
|
|
8075
|
+
const existing = await backgroundAgentStatus().catch(() => null);
|
|
8076
|
+
if (existing?.active && existing.version && existing.version !== VERSION) {
|
|
8077
|
+
logLine(
|
|
8078
|
+
"info",
|
|
8079
|
+
`Background Agent v${existing.version} detected \xB7 checking safe handoff to v${VERSION}\u2026`
|
|
8080
|
+
);
|
|
8081
|
+
}
|
|
6182
8082
|
const status = await enableBackgroundAgent(SELF_PATH, { version: VERSION });
|
|
6183
|
-
if (status.supported && status.enabled) {
|
|
8083
|
+
if (status.supported && status.enabled && status.active) {
|
|
6184
8084
|
banner();
|
|
6185
|
-
logLine("success", "
|
|
8085
|
+
logLine("success", "Process recovery enabled; this terminal stays attached.");
|
|
6186
8086
|
logLine(
|
|
6187
8087
|
"info",
|
|
6188
|
-
`
|
|
8088
|
+
`Supervisor: ${status.service} \xB7 PID ${status.pid} \xB7 takes over if the executing Agent ends`
|
|
6189
8089
|
);
|
|
6190
8090
|
logLine(
|
|
6191
8091
|
"info",
|
|
6192
8092
|
"Use the Remote Arc dashboard or --no-background to disable it."
|
|
6193
8093
|
);
|
|
8094
|
+
} else logLine("warn", status.detail || "Background services are unavailable on this system.");
|
|
8095
|
+
} catch (error) {
|
|
8096
|
+
if (error instanceof LegacyBackgroundAgentError) {
|
|
8097
|
+
logLine("error", error.message);
|
|
8098
|
+
process3.exitCode = 1;
|
|
6194
8099
|
return;
|
|
6195
8100
|
}
|
|
6196
|
-
logLine("warn", status.detail || "Background services are unavailable on this system.");
|
|
6197
|
-
} catch (error) {
|
|
6198
8101
|
logLine(
|
|
6199
8102
|
"warn",
|
|
6200
8103
|
"Could not enable background mode; keeping this terminal session connected: " + (error instanceof Error ? error.message : String(error))
|
|
@@ -6207,8 +8110,56 @@ async function main() {
|
|
|
6207
8110
|
"Background connection is not configured yet \xB7 finish setup in the browser or Devices."
|
|
6208
8111
|
);
|
|
6209
8112
|
}
|
|
6210
|
-
const
|
|
6211
|
-
|
|
8113
|
+
const abort = new AbortController();
|
|
8114
|
+
const stopWaiting = () => abort.abort();
|
|
8115
|
+
process3.on("SIGINT", stopWaiting);
|
|
8116
|
+
process3.on("SIGTERM", stopWaiting);
|
|
8117
|
+
let release = null;
|
|
8118
|
+
let cursor = null;
|
|
8119
|
+
let announced = false;
|
|
8120
|
+
let lastApprovalPoll = 0;
|
|
8121
|
+
try {
|
|
8122
|
+
while (!abort.signal.aborted && !release) {
|
|
8123
|
+
if (agentMode && (await readConfig())?.backgroundEnabled !== true) return;
|
|
8124
|
+
release = await tryAgentLease(path7.join(CONFIG_DIR, "agent"));
|
|
8125
|
+
if (release) break;
|
|
8126
|
+
if (!agentMode && (argFlag("--safe") || argFlag("--developer"))) {
|
|
8127
|
+
logLine("error", "Another Agent owns execution. Stop it locally before changing the local permission profile.");
|
|
8128
|
+
process3.exitCode = 1;
|
|
8129
|
+
return;
|
|
8130
|
+
}
|
|
8131
|
+
if (!agentMode) {
|
|
8132
|
+
if (!announced) {
|
|
8133
|
+
logLine("info", "An Agent already owns execution. Following its operation log; Ctrl+C closes this viewer.");
|
|
8134
|
+
announced = true;
|
|
8135
|
+
}
|
|
8136
|
+
const events = await readAgentEvents(path7.join(CONFIG_DIR, "logs"), cursor);
|
|
8137
|
+
cursor = events.cursor;
|
|
8138
|
+
if (events.text) process3.stdout.write(events.text);
|
|
8139
|
+
if (Date.now() - lastApprovalPoll >= 4e3) {
|
|
8140
|
+
lastApprovalPoll = Date.now();
|
|
8141
|
+
void promptPendingApproval(config);
|
|
8142
|
+
}
|
|
8143
|
+
}
|
|
8144
|
+
await sleep(500);
|
|
8145
|
+
}
|
|
8146
|
+
if (!release || abort.signal.aborted) return;
|
|
8147
|
+
if (argFlag("--safe") || argFlag("--developer")) {
|
|
8148
|
+
config.mode = argFlag("--safe") ? "safe" : "managed";
|
|
8149
|
+
await writeConfig(config);
|
|
8150
|
+
}
|
|
8151
|
+
process3.off("SIGINT", stopWaiting);
|
|
8152
|
+
process3.off("SIGTERM", stopWaiting);
|
|
8153
|
+
const result = await connectAgent(config);
|
|
8154
|
+
if (result !== "rePair") {
|
|
8155
|
+
if (agentMode && (await readConfig())?.backgroundEnabled === true) process3.exitCode = 1;
|
|
8156
|
+
return;
|
|
8157
|
+
}
|
|
8158
|
+
} finally {
|
|
8159
|
+
process3.off("SIGINT", stopWaiting);
|
|
8160
|
+
process3.off("SIGTERM", stopWaiting);
|
|
8161
|
+
await release?.();
|
|
8162
|
+
}
|
|
6212
8163
|
config = null;
|
|
6213
8164
|
}
|
|
6214
8165
|
}
|