watch-cli.js 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452
  1. /*
  2. @license
  3. Rollup.js v2.40.0
  4. Fri, 26 Feb 2021 14:39:44 GMT - commit 0a0958ff926554abe9916178f56762ba71301ddd
  5. https://github.com/rollup/rollup
  6. Released under the MIT License.
  7. */
  8. 'use strict';
  9. var index = require('./index.js');
  10. var loadConfigFile_js = require('./loadConfigFile.js');
  11. var fs = require('fs');
  12. var cli = require('../bin/rollup');
  13. var require$$0 = require('assert');
  14. var require$$0$1 = require('events');
  15. var rollup = require('./rollup.js');
  16. require('path');
  17. require('util');
  18. require('stream');
  19. require('os');
  20. require('url');
  21. require('./mergeOptions.js');
  22. require('module');
  23. require('crypto');
  24. var dateTime$2 = {exports: {}};
  25. var timeZone$1 = date => {
  26. const offset = (date || new Date()).getTimezoneOffset();
  27. const absOffset = Math.abs(offset);
  28. const hours = Math.floor(absOffset / 60);
  29. const minutes = absOffset % 60;
  30. const minutesOut = minutes > 0 ? ':' + ('0' + minutes).slice(-2) : '';
  31. return (offset < 0 ? '+' : '-') + hours + minutesOut;
  32. };
  33. const timeZone = timeZone$1;
  34. const dateTime = options => {
  35. options = Object.assign({
  36. date: new Date(),
  37. local: true,
  38. showTimeZone: false,
  39. showMilliseconds: false
  40. }, options);
  41. let {date} = options;
  42. if (options.local) {
  43. // Offset the date so it will return the correct value when getting the ISO string
  44. date = new Date(date.getTime() - (date.getTimezoneOffset() * 60000));
  45. }
  46. let end = '';
  47. if (options.showTimeZone) {
  48. end = ' UTC' + (options.local ? timeZone(date) : '');
  49. }
  50. if (options.showMilliseconds && date.getUTCMilliseconds() > 0) {
  51. end = ` ${date.getUTCMilliseconds()}ms${end}`;
  52. }
  53. return date
  54. .toISOString()
  55. .replace(/T/, ' ')
  56. .replace(/\..+/, end);
  57. };
  58. dateTime$2.exports = dateTime;
  59. // TODO: Remove this for the next major release
  60. dateTime$2.exports.default = dateTime;
  61. var dateTime$1 = dateTime$2.exports;
  62. var signalExit = {exports: {}};
  63. var signals$1 = {exports: {}};
  64. (function (module) {
  65. // This is not the set of all possible signals.
  66. //
  67. // It IS, however, the set of all signals that trigger
  68. // an exit on either Linux or BSD systems. Linux is a
  69. // superset of the signal names supported on BSD, and
  70. // the unknown signals just fail to register, so we can
  71. // catch that easily enough.
  72. //
  73. // Don't bother with SIGKILL. It's uncatchable, which
  74. // means that we can't fire any callbacks anyway.
  75. //
  76. // If a user does happen to register a handler on a non-
  77. // fatal signal like SIGWINCH or something, and then
  78. // exit, it'll end up firing `process.emit('exit')`, so
  79. // the handler will be fired anyway.
  80. //
  81. // SIGBUS, SIGFPE, SIGSEGV and SIGILL, when not raised
  82. // artificially, inherently leave the process in a
  83. // state from which it is not safe to try and enter JS
  84. // listeners.
  85. module.exports = [
  86. 'SIGABRT',
  87. 'SIGALRM',
  88. 'SIGHUP',
  89. 'SIGINT',
  90. 'SIGTERM'
  91. ];
  92. if (process.platform !== 'win32') {
  93. module.exports.push(
  94. 'SIGVTALRM',
  95. 'SIGXCPU',
  96. 'SIGXFSZ',
  97. 'SIGUSR2',
  98. 'SIGTRAP',
  99. 'SIGSYS',
  100. 'SIGQUIT',
  101. 'SIGIOT'
  102. // should detect profiler and enable/disable accordingly.
  103. // see #21
  104. // 'SIGPROF'
  105. );
  106. }
  107. if (process.platform === 'linux') {
  108. module.exports.push(
  109. 'SIGIO',
  110. 'SIGPOLL',
  111. 'SIGPWR',
  112. 'SIGSTKFLT',
  113. 'SIGUNUSED'
  114. );
  115. }
  116. }(signals$1));
  117. // Note: since nyc uses this module to output coverage, any lines
  118. // that are in the direct sync flow of nyc's outputCoverage are
  119. // ignored, since we can never get coverage for them.
  120. var assert = require$$0;
  121. var signals = signals$1.exports;
  122. var isWin = /^win/i.test(process.platform);
  123. var EE = require$$0$1;
  124. /* istanbul ignore if */
  125. if (typeof EE !== 'function') {
  126. EE = EE.EventEmitter;
  127. }
  128. var emitter;
  129. if (process.__signal_exit_emitter__) {
  130. emitter = process.__signal_exit_emitter__;
  131. } else {
  132. emitter = process.__signal_exit_emitter__ = new EE();
  133. emitter.count = 0;
  134. emitter.emitted = {};
  135. }
  136. // Because this emitter is a global, we have to check to see if a
  137. // previous version of this library failed to enable infinite listeners.
  138. // I know what you're about to say. But literally everything about
  139. // signal-exit is a compromise with evil. Get used to it.
  140. if (!emitter.infinite) {
  141. emitter.setMaxListeners(Infinity);
  142. emitter.infinite = true;
  143. }
  144. signalExit.exports = function (cb, opts) {
  145. assert.equal(typeof cb, 'function', 'a callback must be provided for exit handler');
  146. if (loaded === false) {
  147. load();
  148. }
  149. var ev = 'exit';
  150. if (opts && opts.alwaysLast) {
  151. ev = 'afterexit';
  152. }
  153. var remove = function () {
  154. emitter.removeListener(ev, cb);
  155. if (emitter.listeners('exit').length === 0 &&
  156. emitter.listeners('afterexit').length === 0) {
  157. unload();
  158. }
  159. };
  160. emitter.on(ev, cb);
  161. return remove
  162. };
  163. signalExit.exports.unload = unload;
  164. function unload () {
  165. if (!loaded) {
  166. return
  167. }
  168. loaded = false;
  169. signals.forEach(function (sig) {
  170. try {
  171. process.removeListener(sig, sigListeners[sig]);
  172. } catch (er) {}
  173. });
  174. process.emit = originalProcessEmit;
  175. process.reallyExit = originalProcessReallyExit;
  176. emitter.count -= 1;
  177. }
  178. function emit (event, code, signal) {
  179. if (emitter.emitted[event]) {
  180. return
  181. }
  182. emitter.emitted[event] = true;
  183. emitter.emit(event, code, signal);
  184. }
  185. // { <signal>: <listener fn>, ... }
  186. var sigListeners = {};
  187. signals.forEach(function (sig) {
  188. sigListeners[sig] = function listener () {
  189. // If there are no other listeners, an exit is coming!
  190. // Simplest way: remove us and then re-send the signal.
  191. // We know that this will kill the process, so we can
  192. // safely emit now.
  193. var listeners = process.listeners(sig);
  194. if (listeners.length === emitter.count) {
  195. unload();
  196. emit('exit', null, sig);
  197. /* istanbul ignore next */
  198. emit('afterexit', null, sig);
  199. /* istanbul ignore next */
  200. if (isWin && sig === 'SIGHUP') {
  201. // "SIGHUP" throws an `ENOSYS` error on Windows,
  202. // so use a supported signal instead
  203. sig = 'SIGINT';
  204. }
  205. process.kill(process.pid, sig);
  206. }
  207. };
  208. });
  209. signalExit.exports.signals = function () {
  210. return signals
  211. };
  212. signalExit.exports.load = load;
  213. var loaded = false;
  214. function load () {
  215. if (loaded) {
  216. return
  217. }
  218. loaded = true;
  219. // This is the number of onSignalExit's that are in play.
  220. // It's important so that we can count the correct number of
  221. // listeners on signals, and don't wait for the other one to
  222. // handle it instead of us.
  223. emitter.count += 1;
  224. signals = signals.filter(function (sig) {
  225. try {
  226. process.on(sig, sigListeners[sig]);
  227. return true
  228. } catch (er) {
  229. return false
  230. }
  231. });
  232. process.emit = processEmit;
  233. process.reallyExit = processReallyExit;
  234. }
  235. var originalProcessReallyExit = process.reallyExit;
  236. function processReallyExit (code) {
  237. process.exitCode = code || 0;
  238. emit('exit', process.exitCode, null);
  239. /* istanbul ignore next */
  240. emit('afterexit', process.exitCode, null);
  241. /* istanbul ignore next */
  242. originalProcessReallyExit.call(process, process.exitCode);
  243. }
  244. var originalProcessEmit = process.emit;
  245. function processEmit (ev, arg) {
  246. if (ev === 'exit') {
  247. if (arg !== undefined) {
  248. process.exitCode = arg;
  249. }
  250. var ret = originalProcessEmit.apply(this, arguments);
  251. emit('exit', process.exitCode, null);
  252. /* istanbul ignore next */
  253. emit('afterexit', process.exitCode, null);
  254. return ret
  255. } else {
  256. return originalProcessEmit.apply(this, arguments)
  257. }
  258. }
  259. var onExit = signalExit.exports;
  260. const CLEAR_SCREEN = '\u001Bc';
  261. function getResetScreen(configs, allowClearScreen) {
  262. let clearScreen = allowClearScreen;
  263. for (const config of configs) {
  264. if (config.watch && config.watch.clearScreen === false) {
  265. clearScreen = false;
  266. }
  267. }
  268. if (clearScreen) {
  269. return (heading) => loadConfigFile_js.stderr(CLEAR_SCREEN + heading);
  270. }
  271. let firstRun = true;
  272. return (heading) => {
  273. if (firstRun) {
  274. loadConfigFile_js.stderr(heading);
  275. firstRun = false;
  276. }
  277. };
  278. }
  279. async function watch(command) {
  280. process.env.ROLLUP_WATCH = 'true';
  281. const isTTY = process.stderr.isTTY;
  282. const silent = command.silent;
  283. let configs;
  284. let warnings;
  285. let watcher;
  286. let configWatcher;
  287. const configFile = command.config ? cli.getConfigPath(command.config) : null;
  288. onExit(close);
  289. process.on('uncaughtException', close);
  290. if (!process.stdin.isTTY) {
  291. process.stdin.on('end', close);
  292. process.stdin.resume();
  293. }
  294. if (configFile) {
  295. let reloadingConfig = false;
  296. let aborted = false;
  297. let configFileData = null;
  298. configWatcher = index.chokidar.watch(configFile).on('change', () => reloadConfigFile());
  299. await reloadConfigFile();
  300. async function reloadConfigFile() {
  301. try {
  302. const newConfigFileData = fs.readFileSync(configFile, 'utf-8');
  303. if (newConfigFileData === configFileData) {
  304. return;
  305. }
  306. if (reloadingConfig) {
  307. aborted = true;
  308. return;
  309. }
  310. if (configFileData) {
  311. loadConfigFile_js.stderr(`\nReloading updated config...`);
  312. }
  313. configFileData = newConfigFileData;
  314. reloadingConfig = true;
  315. ({ options: configs, warnings } = await loadConfigFile_js.loadAndParseConfigFile(configFile, command));
  316. reloadingConfig = false;
  317. if (aborted) {
  318. aborted = false;
  319. reloadConfigFile();
  320. }
  321. else {
  322. if (watcher) {
  323. watcher.close();
  324. }
  325. start(configs);
  326. }
  327. }
  328. catch (err) {
  329. configs = [];
  330. reloadingConfig = false;
  331. loadConfigFile_js.handleError(err, true);
  332. }
  333. }
  334. }
  335. else {
  336. ({ options: configs, warnings } = await cli.loadConfigFromCommand(command));
  337. start(configs);
  338. }
  339. // tslint:disable-next-line:no-unnecessary-type-assertion
  340. const resetScreen = getResetScreen(configs, isTTY);
  341. function start(configs) {
  342. try {
  343. watcher = rollup.watch(configs);
  344. }
  345. catch (err) {
  346. return loadConfigFile_js.handleError(err);
  347. }
  348. watcher.on('event', event => {
  349. switch (event.code) {
  350. case 'ERROR':
  351. warnings.flush();
  352. loadConfigFile_js.handleError(event.error, true);
  353. break;
  354. case 'START':
  355. if (!silent) {
  356. resetScreen(loadConfigFile_js.underline(`rollup v${rollup.version}`));
  357. }
  358. break;
  359. case 'BUNDLE_START':
  360. if (!silent) {
  361. let input = event.input;
  362. if (typeof input !== 'string') {
  363. input = Array.isArray(input)
  364. ? input.join(', ')
  365. : Object.keys(input)
  366. .map(key => input[key])
  367. .join(', ');
  368. }
  369. loadConfigFile_js.stderr(loadConfigFile_js.cyan(`bundles ${loadConfigFile_js.bold(input)} → ${loadConfigFile_js.bold(event.output.map(rollup.relativeId).join(', '))}...`));
  370. }
  371. break;
  372. case 'BUNDLE_END':
  373. warnings.flush();
  374. if (!silent)
  375. loadConfigFile_js.stderr(loadConfigFile_js.green(`created ${loadConfigFile_js.bold(event.output.map(rollup.relativeId).join(', '))} in ${loadConfigFile_js.bold(cli.prettyMs(event.duration))}`));
  376. if (event.result && event.result.getTimings) {
  377. cli.printTimings(event.result.getTimings());
  378. }
  379. break;
  380. case 'END':
  381. if (!silent && isTTY) {
  382. loadConfigFile_js.stderr(`\n[${dateTime$1()}] waiting for changes...`);
  383. }
  384. }
  385. if ('result' in event && event.result) {
  386. event.result.close().catch(error => loadConfigFile_js.handleError(error, true));
  387. }
  388. });
  389. }
  390. function close(code) {
  391. process.removeListener('uncaughtException', close);
  392. // removing a non-existent listener is a no-op
  393. process.stdin.removeListener('end', close);
  394. if (watcher)
  395. watcher.close();
  396. if (configWatcher)
  397. configWatcher.close();
  398. if (code) {
  399. process.exit(code);
  400. }
  401. }
  402. }
  403. exports.watch = watch;
  404. //# sourceMappingURL=watch-cli.js.map