Skip to content

Commit

Permalink
Actually added files.
Browse files Browse the repository at this point in the history
  • Loading branch information
bcoe committed Feb 11, 2012
1 parent 4e3f32c commit a398ea4
Show file tree
Hide file tree
Showing 5 changed files with 130 additions and 0 deletions.
11 changes: 11 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
TCPLock
=======

It's happened to everyone, you want to connect on a TCP/IP socket, but you need a mutex in front of it!

Luckily, TCPLock is here for you. TCPLock is a TCP/IP proxy that only allows a single connection through at a time.

Usage
-----

_tcplock -l [port to listen to] -p [port to proxy to] -h [host to proxy to] -n [number of connections to allow]_
11 changes: 11 additions & 0 deletions bin/tcplock.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
#!/usr/bin/env node
var TCPLock = require('tcplock').TCPLock,
args = require('argsparser').parse(),
puts = require('util').puts;

if (!args['-l'] || !args['-p']) {
puts('Options:\n\t-l listen port\n\t-p proxy port\n\t-h proxy host\n\t-n number of connections allowed')
} else {
var lock = new TCPLock(args['-l'], args['-p'], args['-h'], args['-n']);
lock.start();
}
1 change: 1 addition & 0 deletions lib/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
exports.TCPLock = require('./tcplock').TCPLock;
82 changes: 82 additions & 0 deletions lib/tcplock.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
var net = require('net'),
puts = require('util').puts;

exports.TCPLock = function(listenPort, proxyPort, proxyHost, totalConnections) {
this.connectionQueue = [];
this.currentConnections = [];
this.listenPort = listenPort;
this.proxyPort = proxyPort;
this.proxyHost = proxyHost || 'localhost';
this.proxyConnections = {};
this.totalConnections = totalConnections;
this.activeConnectionCount = 0;
}

exports.TCPLock.prototype = {

start: function() {
var _this = this;

this.server = net.createServer(function (connection) {

connection.on('connect', function () {
_this._enqueueConnection(connection);
});

connection.on('data', function (data) {
_this.proxyConnections[connection.remotePort].write(data);
});

connection.on('end', function () {
_this._endConnection(connection);
});

connection.on('error', function () {
_this._endConnection(connection);
});
});

this.server.listen(this.listenPort, 'localhost');
},

_endConnection: function(connection) {
var idx = this.currentConnections.indexOf(connection);
if (idx != -1) {
this.activeConnectionCount--;
this.currentConnections.splice(idx, 1);
this.proxyConnections[connection.remotePort].end();
delete this.proxyConnections[connection.remotePort];
this._activateConnections();
}
},

_enqueueConnection: function(connection) {
connection.pause();
this.connectionQueue.push(connection);
this._activateConnections();
},

_activateConnections: function() {
while (this.activeConnectionCount < this.totalConnections && this.connectionQueue.length) {
var connection = this.connectionQueue.shift();
this.currentConnections.push(connection);
this._createProxyConnection(connection);
connection.resume();
this.activeConnectionCount += 1;
}
},

_createProxyConnection: function(connection) {
var _this = this,
proxyConnection = net.createConnection(this.proxyPort, this.proxyHost);
this.proxyConnections[connection.remotePort] = proxyConnection;

proxyConnection.on('data', function (data) {
connection.write(data);
});

proxyConnection.on('error', function (data) {
_this._endConnection(connection);
});
}
};
25 changes: 25 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
{
"name": "tcplock",
"directories": {
"lib": "./lib",
"bin": "./bin"
},
"main": "./lib/index.js",
"bin": "./bin/tcplock.js",
"version": "0.1.2",
"author": "Ben Coe <bencoe@gmail.com>, Joshua Hull <joshbuddy@gmail.com>",
"engines": [
"node"
],
"description": "A proxy that only allows one connection through on a given port at a time.",
"keywords": [
"tcp",
"lock"
],
"repository": {
"type": "git",
"url": "git://github.com/joshbuddy/tcplock.git"
},
"dependencies": {"argsparser": ">= 0.0.0"},
"devDependencies": {}
}

0 comments on commit a398ea4

Please sign in to comment.