debug.js 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384
  1. 'use strict';
  2. const cp = require('child_process');
  3. const chalk = require('chalk');
  4. const InspectorProxy = require('inspector-proxy');
  5. const debug = require('debug')('egg-bin');
  6. const semver = require('semver');
  7. const Command = require('./dev');
  8. const newDebugger = semver.gte(process.version, '7.0.0');
  9. class DebugCommand extends Command {
  10. constructor(rawArgv) {
  11. super(rawArgv);
  12. this.usage = 'Usage: egg-bin debug [dir] [options]';
  13. this.options = {
  14. // set default to empty so `--inspect` will always pass to fork
  15. inspect: {
  16. description: 'V8 Inspector port',
  17. default() {
  18. /* istanbul ignore next */
  19. return newDebugger ? '' : undefined;
  20. },
  21. },
  22. 'inspect-brk': {
  23. description: 'whether break at start',
  24. },
  25. debug: {
  26. description: 'legacy debugger',
  27. default() {
  28. /* istanbul ignore next */
  29. return newDebugger ? undefined : '';
  30. },
  31. },
  32. proxy: {
  33. description: 'worker debug proxy port',
  34. default: 9999,
  35. },
  36. };
  37. process.env.EGG_DEBUG = 'true';
  38. }
  39. get description() {
  40. return 'Start server at local debug mode';
  41. }
  42. * run(context) {
  43. const proxyPort = context.argv.proxy;
  44. context.argv.proxy = undefined;
  45. const eggArgs = yield this.formatArgs(context);
  46. const options = {
  47. execArgv: context.execArgv,
  48. env: Object.assign({ NODE_ENV: 'development', EGG_DEBUG: true }, context.env),
  49. };
  50. debug('%s %j %j, %j', this.serverBin, eggArgs, options.execArgv, options.env.NODE_ENV);
  51. // start egg
  52. const child = cp.fork(this.serverBin, eggArgs, options);
  53. // start debug proxy
  54. const proxy = new InspectorProxy({ port: proxyPort });
  55. // proxy to new worker
  56. child.on('message', msg => {
  57. if (msg && msg.action === 'debug' && msg.from === 'app') {
  58. const { debugPort, pid } = msg.data;
  59. debug(`recieve new worker#${pid} debugPort: ${debugPort}`);
  60. proxy.start({ debugPort }).then(() => {
  61. // don't log within VSCode and WebStorm
  62. // TODO: don't start proxy within vscode and webstorm at next major
  63. if (!process.env.VSCODE_CLI && !process.env.NODE_DEBUG_OPTION && !process.env.JB_DEBUG_FILE) {
  64. console.log(chalk.yellow(`Debug Proxy online, now you could attach to ${proxyPort} without worry about reload.`));
  65. if (newDebugger) console.log(chalk.yellow(`DevTools → ${proxy.url}`));
  66. }
  67. });
  68. }
  69. });
  70. child.on('exit', () => proxy.end());
  71. }
  72. }
  73. module.exports = DebugCommand;