120 lines
2.7 KiB
JavaScript
120 lines
2.7 KiB
JavaScript
|
var os = require('os');
|
||
|
var ip = require('ip');
|
||
|
var Promise = require('pinkie-promise');
|
||
|
var createServer = require('net').createServer;
|
||
|
|
||
|
function createServerOnFreePort () {
|
||
|
return new Promise(function (resolve) {
|
||
|
var server = createServer();
|
||
|
|
||
|
server.once('listening', function () {
|
||
|
resolve(server);
|
||
|
});
|
||
|
|
||
|
server.listen(0);
|
||
|
});
|
||
|
}
|
||
|
|
||
|
function closeServers (servers) {
|
||
|
return Promise.all(servers.map(function (server) {
|
||
|
return new Promise(function (resolve) {
|
||
|
server.once('close', resolve);
|
||
|
server.close();
|
||
|
});
|
||
|
}));
|
||
|
}
|
||
|
|
||
|
function checkAvailability (port, hostname) {
|
||
|
return new Promise(function (resolve) {
|
||
|
var server = createServer();
|
||
|
|
||
|
server.once('error', function () {
|
||
|
resolve(false);
|
||
|
});
|
||
|
|
||
|
server.once('listening', function () {
|
||
|
server.once('close', function () {
|
||
|
resolve(true);
|
||
|
});
|
||
|
|
||
|
server.close();
|
||
|
});
|
||
|
|
||
|
server.listen(port, hostname);
|
||
|
});
|
||
|
}
|
||
|
|
||
|
function isFreePort (port) {
|
||
|
return checkAvailability(port);
|
||
|
}
|
||
|
|
||
|
function getFreePort () {
|
||
|
return getFreePorts(1).then(function (ports) {
|
||
|
return ports[0];
|
||
|
});
|
||
|
}
|
||
|
|
||
|
function getFreePorts (count) {
|
||
|
var serverPromises = [];
|
||
|
var ports = null;
|
||
|
|
||
|
// NOTE: Sequentially collect listening
|
||
|
// servers to avoid interference.
|
||
|
for (var i = 0; i < count; i++)
|
||
|
serverPromises.push(createServerOnFreePort());
|
||
|
|
||
|
return Promise.all(serverPromises)
|
||
|
.then(function (servers) {
|
||
|
ports = servers.map(function (server) {
|
||
|
return server.address().port;
|
||
|
});
|
||
|
|
||
|
return servers
|
||
|
})
|
||
|
.then(closeServers)
|
||
|
.then(function () {
|
||
|
return ports;
|
||
|
});
|
||
|
}
|
||
|
|
||
|
function isMyHostname (hostname) {
|
||
|
return getFreePort()
|
||
|
.then(function (port) {
|
||
|
return checkAvailability(port, hostname);
|
||
|
});
|
||
|
}
|
||
|
|
||
|
function getMyHostname () {
|
||
|
var hostname = os.hostname();
|
||
|
|
||
|
return isMyHostname(hostname)
|
||
|
.then(function (mine) {
|
||
|
if (mine)
|
||
|
return hostname;
|
||
|
|
||
|
if (os.platform() === 'mac') {
|
||
|
hostname += '.local';
|
||
|
|
||
|
return isMyHostname(hostname)
|
||
|
.then(function (mine) {
|
||
|
return mine ? hostname : ip.address();
|
||
|
});
|
||
|
}
|
||
|
|
||
|
return ip.address();
|
||
|
});
|
||
|
}
|
||
|
|
||
|
function getIPAddress () {
|
||
|
return ip.address();
|
||
|
}
|
||
|
|
||
|
module.exports = {
|
||
|
isFreePort: isFreePort,
|
||
|
getFreePort: getFreePort,
|
||
|
getFreePorts: getFreePorts,
|
||
|
isMyHostname: isMyHostname,
|
||
|
getMyHostname: getMyHostname,
|
||
|
getIPAddress: getIPAddress
|
||
|
};
|