* SSH semi functional
This commit is contained in:
parent
3833f9910e
commit
0f1fe31fe5
|
@ -184,7 +184,7 @@ function startListening() {
|
||||||
|
|
||||||
// :TODO: handle maxConnections, e.g. conf.maxConnections
|
// :TODO: handle maxConnections, e.g. conf.maxConnections
|
||||||
|
|
||||||
server.on('client', function onClient(client) {
|
server.on('client', function newClient(client, clientSock) {
|
||||||
//
|
//
|
||||||
// Start tracking the client. We'll assign it an ID which is
|
// Start tracking the client. We'll assign it an ID which is
|
||||||
// just the index in our connections array.
|
// just the index in our connections array.
|
||||||
|
@ -193,7 +193,7 @@ function startListening() {
|
||||||
client.session = {};
|
client.session = {};
|
||||||
}
|
}
|
||||||
|
|
||||||
clientConns.addNewClient(client);
|
clientConns.addNewClient(client, clientSock);
|
||||||
|
|
||||||
client.on('ready', function onClientReady() {
|
client.on('ready', function onClientReady() {
|
||||||
|
|
||||||
|
|
|
@ -5,8 +5,9 @@
|
||||||
Portions of this code for key handling heavily inspired from the following:
|
Portions of this code for key handling heavily inspired from the following:
|
||||||
https://github.com/chjj/blessed/blob/master/lib/keys.js
|
https://github.com/chjj/blessed/blob/master/lib/keys.js
|
||||||
|
|
||||||
MIT license is as follows:
|
chji's blessed is MIT licensed:
|
||||||
--------------------------
|
|
||||||
|
----/snip/----------------------
|
||||||
The MIT License (MIT)
|
The MIT License (MIT)
|
||||||
|
|
||||||
Copyright (c) <year> <copyright holders>
|
Copyright (c) <year> <copyright holders>
|
||||||
|
@ -28,7 +29,7 @@
|
||||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||||
THE SOFTWARE.
|
THE SOFTWARE.
|
||||||
--------------------------
|
----/snip/----------------------
|
||||||
*/
|
*/
|
||||||
var term = require('./client_term.js');
|
var term = require('./client_term.js');
|
||||||
var miscUtil = require('./misc_util.js');
|
var miscUtil = require('./misc_util.js');
|
||||||
|
@ -86,9 +87,9 @@ function Client(input, output) {
|
||||||
|
|
||||||
var self = this;
|
var self = this;
|
||||||
|
|
||||||
this.input = input;
|
//this.input = input;
|
||||||
this.output = output;
|
//this.output = output;
|
||||||
this.term = new term.ClientTerminal(this.output);
|
//this.term = new term.ClientTerminal(this.output);
|
||||||
this.user = new user.User();
|
this.user = new user.User();
|
||||||
this.currentTheme = { info : { name : 'N/A', description : 'None' } };
|
this.currentTheme = { info : { name : 'N/A', description : 'None' } };
|
||||||
this.lastKeyPressMs = Date.now();
|
this.lastKeyPressMs = Date.now();
|
||||||
|
@ -110,6 +111,8 @@ function Client(input, output) {
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
//
|
//
|
||||||
// Peek at incoming |data| and emit events for any special
|
// Peek at incoming |data| and emit events for any special
|
||||||
// handling that may include:
|
// handling that may include:
|
||||||
|
@ -398,6 +401,13 @@ function Client(input, output) {
|
||||||
|
|
||||||
require('util').inherits(Client, stream);
|
require('util').inherits(Client, stream);
|
||||||
|
|
||||||
|
Client.prototype.setInputOutput = function(input, output) {
|
||||||
|
this.input = input;
|
||||||
|
this.output = output;
|
||||||
|
|
||||||
|
this.term = new term.ClientTerminal(this.output);
|
||||||
|
};
|
||||||
|
|
||||||
Client.prototype.end = function () {
|
Client.prototype.end = function () {
|
||||||
this.detachCurrentMenuModule();
|
this.detachCurrentMenuModule();
|
||||||
|
|
||||||
|
|
|
@ -14,17 +14,17 @@ function getActiveConnections() {
|
||||||
return clientConnections.length;
|
return clientConnections.length;
|
||||||
}
|
}
|
||||||
|
|
||||||
function addNewClient(client) {
|
function addNewClient(client, clientSock) {
|
||||||
var id = client.session.id = clientConnections.push(client) - 1;
|
var id = client.session.id = clientConnections.push(client) - 1;
|
||||||
|
|
||||||
// Create a client specific logger
|
// Create a client specific logger
|
||||||
client.log = logger.log.child( { clientId : id } );
|
client.log = logger.log.child( { clientId : id } );
|
||||||
|
|
||||||
var connInfo = { ip : client.input.remoteAddress };
|
var connInfo = { ip : clientSock.remoteAddress };
|
||||||
|
|
||||||
if(client.log.debug()) {
|
if(client.log.debug()) {
|
||||||
connInfo.port = client.input.localPort;
|
connInfo.port = clientSock.localPort;
|
||||||
connInfo.family = client.input.localFamily;
|
connInfo.family = clientSock.localFamily;
|
||||||
}
|
}
|
||||||
|
|
||||||
client.log.info(connInfo, 'Client connected');
|
client.log.info(connInfo, 'Client connected');
|
||||||
|
|
|
@ -7,11 +7,7 @@ var baseClient = require('../client.js');
|
||||||
var Log = require('../logger.js').log;
|
var Log = require('../logger.js').log;
|
||||||
var ServerModule = require('../server_module.js').ServerModule;
|
var ServerModule = require('../server_module.js').ServerModule;
|
||||||
var userLogin = require('../user_login.js').userLogin;
|
var userLogin = require('../user_login.js').userLogin;
|
||||||
|
var enigVersion = require('../../package.json').version;
|
||||||
// :TODO: remove this - currently an experimental hack:
|
|
||||||
var term = require('../client_term.js');
|
|
||||||
|
|
||||||
var packageJson = require('../../package.json');
|
|
||||||
|
|
||||||
var ssh2 = require('ssh2');
|
var ssh2 = require('ssh2');
|
||||||
var fs = require('fs');
|
var fs = require('fs');
|
||||||
|
@ -26,6 +22,26 @@ exports.moduleInfo = {
|
||||||
|
|
||||||
exports.getModule = SSHServerModule;
|
exports.getModule = SSHServerModule;
|
||||||
|
|
||||||
|
/*
|
||||||
|
Hello,
|
||||||
|
|
||||||
|
If you follow the first server example in the `ssh2` readme and substitute the `session.once('exec', ...)` with `session.once('shell', ...)`
|
||||||
|
you should be fine. Just about all ssh clients default to an interactive shell session so that is what you will want to look for. As the
|
||||||
|
documentation notes, the `shell` event handler is just passed `accept, reject` with `accept()` returning a duplex stream representing
|
||||||
|
stdin/stdout. You can write to stderr by using the `stderr` property of the duplex stream object.
|
||||||
|
|
||||||
|
You will probably also want to handle the `pty` event on the session, since most clients (by default) will request a pseudo-TTY before
|
||||||
|
requesting an interactive shell. I believe this event may be especially useful in your case because the ssh client can send certain terminal
|
||||||
|
modes which can have relevance with your telnet usage. The event info also contains window dimensions which may help in determining layout
|
||||||
|
of your display (there is also a `window-change` event that contains these same dimensions whenever the client's screen/window dimensions
|
||||||
|
change).
|
||||||
|
|
||||||
|
If you are still having problems after making these changes, post your code somewhere and I will see if there is anything out of place.
|
||||||
|
Additionally, you can set `debug: console.log` in the server config object to show debug output which may be useful to see what is or isn't
|
||||||
|
being sent/received ssh protocol-wise.
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
function SSHClient(clientConn) {
|
function SSHClient(clientConn) {
|
||||||
baseClient.Client.apply(this, arguments);
|
baseClient.Client.apply(this, arguments);
|
||||||
|
|
||||||
|
@ -106,7 +122,7 @@ function SSHClient(clientConn) {
|
||||||
|
|
||||||
var session = accept();
|
var session = accept();
|
||||||
|
|
||||||
session.on('pty-req', function pty(accept, reject, info) {
|
session.on('pty', function pty(accept, reject, info) {
|
||||||
console.log(info);
|
console.log(info);
|
||||||
var channel = accept();
|
var channel = accept();
|
||||||
console.log(channel)
|
console.log(channel)
|
||||||
|
@ -116,13 +132,7 @@ function SSHClient(clientConn) {
|
||||||
session.on('shell', function shell(accept, reject) {
|
session.on('shell', function shell(accept, reject) {
|
||||||
var channel = accept();
|
var channel = accept();
|
||||||
|
|
||||||
channel._write('Hello, world!')
|
self.setInputOutput(channel.stdin, channel.stdout);
|
||||||
|
|
||||||
self.input = channel._client._sock;
|
|
||||||
self.output = channel._client._sock;
|
|
||||||
|
|
||||||
|
|
||||||
self.term = new term.ClientTerminal(self.output);
|
|
||||||
|
|
||||||
self.emit('ready')
|
self.emit('ready')
|
||||||
});
|
});
|
||||||
|
@ -146,14 +156,13 @@ util.inherits(SSHServerModule, ServerModule);
|
||||||
SSHServerModule.prototype.createServer = function() {
|
SSHServerModule.prototype.createServer = function() {
|
||||||
SSHServerModule.super_.prototype.createServer.call(this);
|
SSHServerModule.super_.prototype.createServer.call(this);
|
||||||
|
|
||||||
// :TODO: setup all options here. What should the banner, etc. really be????
|
|
||||||
var serverConf = {
|
var serverConf = {
|
||||||
privateKey : fs.readFileSync(conf.config.servers.ssh.rsaPrivateKey),
|
privateKey : fs.readFileSync(conf.config.servers.ssh.rsaPrivateKey),
|
||||||
banner : 'ENiGMA½ BBS ' + packageJson.version + ' SSH Server',
|
banner : 'ENiGMA½ BBS ' + enigVersion + ' SSH Server',
|
||||||
ident : 'enigma-bbs-' + packageJson.version + '-srv',
|
ident : 'enigma-bbs-' + enigVersion + '-srv',
|
||||||
debug : function debugSsh(dbgLine) {
|
debug : function debugSsh(dbgLine) {
|
||||||
if(true === conf.config.servers.ssh.debugConnections) {
|
if(true === conf.config.servers.ssh.debugConnections) {
|
||||||
self.log.trace('SSH: ' + dbgLine);
|
Log.trace('SSH: ' + dbgLine);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
@ -163,7 +172,8 @@ SSHServerModule.prototype.createServer = function() {
|
||||||
Log.info(info, 'New SSH connection');
|
Log.info(info, 'New SSH connection');
|
||||||
|
|
||||||
var client = new SSHClient(conn);
|
var client = new SSHClient(conn);
|
||||||
this.emit('client', client);
|
|
||||||
|
this.emit('client', client, conn._sock);
|
||||||
});
|
});
|
||||||
|
|
||||||
return server;
|
return server;
|
||||||
|
|
|
@ -430,6 +430,8 @@ function TelnetClient(input, output) {
|
||||||
var readyFired = false;
|
var readyFired = false;
|
||||||
var encodingSet = false;
|
var encodingSet = false;
|
||||||
|
|
||||||
|
this.setInputOutput(input, output);
|
||||||
|
|
||||||
this.negotiationsComplete = false; // are we in the 'negotiation' phase?
|
this.negotiationsComplete = false; // are we in the 'negotiation' phase?
|
||||||
this.didReady = false; // have we emit the 'ready' event?
|
this.didReady = false; // have we emit the 'ready' event?
|
||||||
|
|
||||||
|
@ -761,21 +763,6 @@ Object.keys(OPTIONS).forEach(function(name) {
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
/*
|
|
||||||
function createServer() {
|
|
||||||
var server = net.createServer(function onConnection(sock) {
|
|
||||||
var self = this;
|
|
||||||
var client = new TelnetClient(sock, sock);
|
|
||||||
|
|
||||||
client.banner();
|
|
||||||
|
|
||||||
self.emit('client', client);
|
|
||||||
});
|
|
||||||
|
|
||||||
return server;
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
|
|
||||||
function TelnetServerModule() {
|
function TelnetServerModule() {
|
||||||
ServerModule.call(this);
|
ServerModule.call(this);
|
||||||
}
|
}
|
||||||
|
@ -791,7 +778,7 @@ TelnetServerModule.prototype.createServer = function() {
|
||||||
|
|
||||||
client.banner();
|
client.banner();
|
||||||
|
|
||||||
self.emit('client', client);
|
self.emit('client', client, sock);
|
||||||
});
|
});
|
||||||
|
|
||||||
return server;
|
return server;
|
||||||
|
|
Loading…
Reference in New Issue