Add mumble support

This commit is contained in:
Michael Morrison 2014-02-02 07:20:36 -06:00
parent 16ef96fccf
commit c5abf7aa07
5 changed files with 92 additions and 5 deletions

View File

@ -133,6 +133,7 @@ Supported Games
* Minecraft (minecraft) [[Additional Notes](#minecraft)]
* Monday Night Combat (mnc)
* Multi Theft Auto [[Separate Query Port - Usually port+123](#separate-query-port)]
* Mumble [[Additional Notes](#mumble)]
* Mutant Factions (mutantfactions)
* Natural Selection (ns)
* Natural Selection 2 (ns2) [[Separate Query Port - Usually port+1](#separate-query-port)]
@ -198,6 +199,12 @@ Don't see your game listed here?
Some minecraft servers may not respond to a typical status query. If this is the case, try using the
'minecraftping' server type instead, which uses a less accurate but more reliable solution.
#### Mumble
For full query results from Mumble, you must be running the
[GTmurmur plugin](http://www.gametracker.com/downloads/gtmurmurplugin.php).
If you do not wish to run the plugin, or do not require details such as channel and user lists,
you can use the 'mumbleping' server type instead, which uses a less accurate but more reliable solution
#### Nadeo (ShootMania / TrackMania / etc)
The server must have xmlrpc enabled, and you must pass the xmlrpc port to GameDig, not the connection port.
You must have a user account on the server with access level User or higher.

46
games/mumble.js Normal file
View File

@ -0,0 +1,46 @@
var async = require('async');
module.exports = require('./protocols/core').extend({
init: function() {
this._super();
this.pretty = 'Mumble';
this.options.port = 27800;
this.options.tcpTimeout = 5000;
},
run: function(state) {
var self = this;
this.tcpSend('\x6A\x73\x6F\x6E', function(buffer) {
if(buffer.length < 10) return;
var str = buffer.toString();
var json;
try {
json = JSON.parse(str);
} catch(e) {
// probably not all here yet
return;
}
state.raw = json;
state.name = json.name;
var channelStack = [state.raw.root];
while(channelStack.length) {
var channel = channelStack.shift();
channel.description = self.cleanComment(channel.description);
channelStack = channelStack.concat(channel.channels);
for(var i = 0; i < channel.users.length; i++) {
var user = channel.users[i];
user.comment = self.cleanComment(user.comment);
state.players.push(user);
}
}
self.finish(state);
return true;
});
},
cleanComment: function(str) {
return str.replace(/<.*>/g,'');
}
});

31
games/mumbleping.js Normal file
View File

@ -0,0 +1,31 @@
var async = require('async');
module.exports = require('./protocols/core').extend({
init: function() {
this._super();
this.pretty = 'Mumble';
this.options.port = 64738;
this.byteorder = 'be';
},
run: function(state) {
var self = this;
this.udpSend('\x00\x00\x00\x00\x01\x02\x03\x04\x05\x06\x07\x08', function(buffer) {
if(buffer.length < 24) return;
var reader = self.reader(buffer);
reader.skip(1);
state.raw.versionMajor = reader.uint(1);
state.raw.versionMinor = reader.uint(1);
state.raw.versionPatch = reader.uint(1);
reader.skip(8);
state.raw.numplayers = reader.uint(4);
state.maxplayers = reader.uint(4);
state.raw.allowedbandwidth = reader.uint(4);
for(var i = 0; i < state.raw.numplayers; i++) {
state.players.push({});
}
self.finish(state);
return true;
});
}
});

View File

@ -8,7 +8,10 @@ var EventEmitter = require('events').EventEmitter,
module.exports = Class.extend(EventEmitter,{
init: function() {
this._super();
this.options = {};
this.options = {
tcpTimeout: 1000,
udpTimeout: 1000
};
this.maxAttempts = 1;
this.attempt = 1;
this.finished = false;
@ -207,6 +210,7 @@ module.exports = Class.extend(EventEmitter,{
var socket = this.tcpSocket = net.connect(port,address,function() {
if(self.debug) console.log(address+':'+port+" TCPCONNECTED");
connected = true;
c(socket);
});
socket.setTimeout(10000);
@ -242,14 +246,13 @@ module.exports = Class.extend(EventEmitter,{
if(self.tcpCallback) return self.fatal('Attempted to send TCP packet while still waiting on a managed response');
self._tcpConnect(function(socket) {
socket.write(buffer);
if(self.debug) console.log(socket.remoteAddress+':'+socket.remotePort+" TCP--> "+buffer.toString('hex'));
});
if(!ondata) return;
self.tcpTimeoutTimer = self.setTimeout(function() {
self.tcpCallback = false;
self.fatal('TCP Watchdog Timeout');
},1000);
},self.options.tcpTimeout);
self.tcpCallback = ondata;
});
},
@ -268,7 +271,7 @@ module.exports = Class.extend(EventEmitter,{
var timeout = false;
if(!ontimeout || ontimeout() !== true) timeout = true;
if(timeout) self.fatal('UDP Watchdog Timeout');
},1000);
},self.options.udpTimeout);
self.udpCallback = onpacket;
});
},

View File

@ -3,7 +3,7 @@ var async = require('async');
module.exports = require('./protocols/core').extend({
init: function() {
this._super();
this.pretty = 'Teamspeak 2';
this.pretty = 'Teamspeak 3';
this.options.port = 9987;
this.options.master_port = 10011;
},