handle destroy methods better: stop all polling on the event loop.
This commit is contained in:
parent
1628e7d629
commit
debbc864e4
|
@ -443,12 +443,35 @@ Program.prototype._listenOutput = function() {
|
|||
|
||||
Program.prototype.destroy = function() {
|
||||
var index = Program.instances.indexOf(this);
|
||||
|
||||
if (~index) {
|
||||
Program.instances.splice(index, 1);
|
||||
Program.total--;
|
||||
|
||||
this.flush();
|
||||
this._exiting = true;
|
||||
|
||||
if (Program.total === 0) {
|
||||
Program.global = null;
|
||||
|
||||
process.removeAllListeners('exit');
|
||||
|
||||
this.input.removeAllListeners('keypress');
|
||||
this.input.removeAllListeners('data');
|
||||
this.input.removeAllListeners('newListener');
|
||||
this.output.removeAllListeners('resize');
|
||||
|
||||
if (this.input.setRawMode) {
|
||||
if (this.input.isRaw) {
|
||||
this.input.setRawMode(false);
|
||||
}
|
||||
if (!this.input.destroyed) {
|
||||
this.input.pause();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
this.destroyed = true;
|
||||
this.emit('destroy');
|
||||
}
|
||||
};
|
||||
|
|
|
@ -305,12 +305,6 @@ Element.prototype.free = function() {
|
|||
delete this._slisteners;
|
||||
};
|
||||
|
||||
Element.prototype.destroy = function() {
|
||||
this.detach();
|
||||
this.free();
|
||||
this.emit('destroy');
|
||||
};
|
||||
|
||||
Element.prototype.hide = function() {
|
||||
if (this.hidden) return;
|
||||
this.clearPos();
|
||||
|
|
|
@ -135,6 +135,19 @@ Node.prototype.detach = function() {
|
|||
if (this.parent) this.parent.remove(this);
|
||||
};
|
||||
|
||||
Node.prototype.free = function() {
|
||||
return;
|
||||
};
|
||||
|
||||
Node.prototype.destroy = function() {
|
||||
this.detach();
|
||||
this.forDescendants(function(el) {
|
||||
el.free();
|
||||
el.destroyed = true;
|
||||
el.emit('destroy');
|
||||
}, this);
|
||||
};
|
||||
|
||||
Node.prototype.forDescendants = function(iter, s) {
|
||||
if (s) iter(this);
|
||||
this.children.forEach(function emit(el) {
|
||||
|
|
|
@ -35,7 +35,7 @@ function Screen(options) {
|
|||
return new Screen(options);
|
||||
}
|
||||
|
||||
Screen.bind(this);
|
||||
Screen.bind(this, options || {});
|
||||
|
||||
options = options || {};
|
||||
if (options.rsety && options.listen) {
|
||||
|
@ -195,9 +195,12 @@ Screen.instances = [];
|
|||
|
||||
Screen.signals = true;
|
||||
|
||||
Screen.bind = function(screen) {
|
||||
Screen.bind = function(screen, options) {
|
||||
if (!Screen.global) {
|
||||
Screen.global = screen;
|
||||
if (options.signals === false) {
|
||||
Screen.signals = false;
|
||||
}
|
||||
}
|
||||
|
||||
if (!~Screen.instances.indexOf(screen)) {
|
||||
|
@ -209,7 +212,7 @@ Screen.bind = function(screen) {
|
|||
Screen._bound = true;
|
||||
|
||||
process.on('uncaughtException', function(err) {
|
||||
if (process.listeners('uncaughtException').length > Screen.total) {
|
||||
if (process.listeners('uncaughtException').length > 1) {
|
||||
return;
|
||||
}
|
||||
Screen.instances.slice().forEach(function(screen) {
|
||||
|
@ -217,6 +220,9 @@ Screen.bind = function(screen) {
|
|||
});
|
||||
err = err || new Error('Uncaught Exception.');
|
||||
console.error(err.stack ? err.stack + '' : err + '');
|
||||
if (Screen.total === 0) {
|
||||
return process.exit(1);
|
||||
}
|
||||
nextTick(function() {
|
||||
process.exit(1);
|
||||
});
|
||||
|
@ -227,9 +233,12 @@ Screen.bind = function(screen) {
|
|||
if (Screen.signals) {
|
||||
['SIGTERM', 'SIGINT', 'SIGQUIT'].forEach(function(signal) {
|
||||
process.on(signal, function() {
|
||||
if (process.listeners(signal).length > Screen.total) {
|
||||
if (process.listeners(signal).length > 1) {
|
||||
return;
|
||||
}
|
||||
if (Screen.total === 0) {
|
||||
return process.exit(0);
|
||||
}
|
||||
nextTick(function() {
|
||||
process.exit(0);
|
||||
});
|
||||
|
@ -383,6 +392,7 @@ Screen.prototype.postEnter = function() {
|
|||
}
|
||||
};
|
||||
|
||||
Screen.prototype._destroy = Screen.prototype.destroy;
|
||||
Screen.prototype.destroy = function() {
|
||||
this.leave();
|
||||
|
||||
|
@ -390,10 +400,16 @@ Screen.prototype.destroy = function() {
|
|||
if (~index) {
|
||||
Screen.instances.splice(index, 1);
|
||||
Screen.total--;
|
||||
|
||||
if (Screen.total === 0) {
|
||||
Screen.global = null;
|
||||
|
||||
process.removeAllListeners('uncaughtException');
|
||||
}
|
||||
|
||||
this.destroyed = true;
|
||||
this.emit('destroy');
|
||||
this._destroy();
|
||||
}
|
||||
|
||||
this.program.destroy();
|
||||
|
|
|
@ -209,6 +209,7 @@ Terminal.prototype.bootstrap = function() {
|
|||
|
||||
this.on('destroy', function() {
|
||||
self.kill();
|
||||
self.screen.program.removeListener('data', self._onData);
|
||||
});
|
||||
|
||||
if (this.handler) {
|
||||
|
@ -252,11 +253,6 @@ Terminal.prototype.bootstrap = function() {
|
|||
});
|
||||
|
||||
this.screen._listenKeys(this);
|
||||
|
||||
this.on('destroy', function() {
|
||||
self.screen.program.removeListener('data', self._onData);
|
||||
self.pty.destroy();
|
||||
});
|
||||
};
|
||||
|
||||
Terminal.prototype.write = function(data) {
|
||||
|
|
Loading…
Reference in New Issue