i'm trying to develop a simple unit test to bind a port on my machine, test that the port is bound, then release the port and test that it is release. Currently I'm using this naive approach
class ServerTest extends FlatSpec with MustMatchers {
"Server" must "bind a tcp server to an address on our machine" in {
//if this fails this means that the port is in use before our test case is run
val port = 18333
isBound(port) must be (false)
val actor = Server()
actor ! Tcp.Bind(actor, new InetSocketAddress(port))
Thread.sleep(1000)
isBound(port) must be (true)
Thread.sleep(1000)
actor ! Tcp.Unbind
Thread.sleep(1000)
isBound(port) must be (false)
}
/**
* Tests if a specific port number is bound on our machine
* #param port
* #return
*/
def isBound(port : Int) : Boolean = {
val tryBinding : Try[Unit] = Try {
val socket = new java.net.Socket()
socket.connect(new java.net.InetSocketAddress(port),1000)
socket.close()
}
tryBinding.isSuccess
}
}
I would like to test this without using the calls to Thread.sleep since this is a blocking call. Can anyone provide me with a more idiomatic solution?
When sending TCP.Bind , you should expect a reply stating either success or failure: http://doc.akka.io/japi/akka/2.3.2/akka/io/Tcp.Bind.html
The Bind message is send to the TCP manager actor, which is obtained
via TcpExt.manager() in order to bind to a listening socket. The
manager replies either with a Tcp.CommandFailed or the actor handling
the listen socket replies with a Tcp.Bound message. If the local port
is set to 0 in the Bind message, then the Tcp.Bound message should be
inspected to find the actual port which was bound to.
You should use AkkaTestKit (http://doc.akka.io/docs/akka/snapshot/scala/testing.html) and use either ImplicitSender or a TestProbe to send the TCP.Bind, and then wait for the answer.
For example:
val probe = TestProbe()
probe.send(actor, Tcp.Bind(actor, new InetSocketAddress(port)))
probe.expectMsg(Tcp.Bound)
Your test code will either continue when the reply is received, or fail if not received within the timeout (which is configurable in the expectMsg call).
You can use
within (1000 millisends) {
...
}
see https://github.com/RayRoestenburg/AkkaExamples/blob/master/src/test/scala/unit/akka/TestKitUsageSpec.scala for more examples
Related
Suppose I've created a socket, started listen()ing on it and run accept() in a loop to process incoming connections. I.e. smth like this:
s = socket();
bind(s, ...);
listen(s, ...);
loop {
new_s = accept(s, ...);
... // do smth with new_s
}
For various reasons accept() can return an error and most of these errors say this particular connection attempt failed, please carry on. Is there any scenario when you have to close the socket and start from scratch (i.e. make new socket + bind + listen) in order to be (eventually) reachable by clients? What error (returned from accept()) tell me that? I.e. should I ever structure my logic like this:
loop {
loop {
s = socket();
bind(s, ...);
listen(s, ...);
if !error { break; }
sleep(1second); // avoid busy loop
}
loop {
new_s = accept(s, ...);
if error {
if error == ??? break; <--- which error code(s)?
continue;
}
... // do smth with new_s
}
}
Notes:
Specifically I am looking at ENETDOWN (Linux) and WSAENETDOWN (Winsock2) -- looks like these happen when someone restarts the network (interface). Will my previously created socket continue accepting connections once network is up? I doubt it, but even if it is the case -- how to properly avoid busy accept loop?
Other platforms may have other error codes -- how to write a code that will work on all of them?
You don't need to recreate the listening socket if accept() fails on that listener (at least on Windows).
If one called bind on 0.0.0.0:(some port) - then you almost never need to worry about recreating the listening socket.
If one called bind on a specific IP address, and that IP address goes away, then you definitely need to recreate the listening socket (you aren't listening to anything anymore).
From what I understand (please correct me if I am wrong), in tomcat incoming websocket messages are processed sequentially. Meaning that if you have 100 incoming messages in one websocket, they will be processed using only one thread one-by-one from message 1 to message 100.
But this does not work for me. I need to concurrently process incoming messages in a websocket in order to increase my websocket throughput. The messages coming in do not depend on each other hence do not need to be processed sequentially.
The question is how to configure tomcat such that it would assign multiple worker threads per websocket to process incoming messages concurrently?
Any hint is appreciated.
This is where in tomcat code that I think it is blocking per websocket connection (which makes sense):
/**
* Called when there is data in the ServletInputStream to process.
*
* #throws IOException if an I/O error occurs while processing the available
* data
*/
public void onDataAvailable() throws IOException {
synchronized (connectionReadLock) {
while (isOpen() && sis.isReady()) {
// Fill up the input buffer with as much data as we can
int read = sis.read(
inputBuffer, writePos, inputBuffer.length - writePos);
if (read == 0) {
return;
}
if (read == -1) {
throw new EOFException();
}
writePos += read;
processInputBuffer();
}
}
}
You can't configure Tomcat to do what you want. You need to write a message handler that consumes the message, passes it to an Executor (or similar for processing) and then returns.
I am designing a communication server in Node that handles incoming messages (sent by client1) and transfers them to someone else (client2), who answers the message and sends the answer back, via the server, to client1.
The communication happens via WebSockets, which implies an open connection from each client to the server.
Thus I implemented a ConnectionManager to which I can register any new connections when a new client comes online. Every connection gets assigned a messageQueue in which all incoming messages are cached before processing.
At the end of processing, I have a ServerTaskManager, who generates Output-Tasks for the server, telling him a message to send and a receiver to receive it.
This ServerTaskManager emits a Node-Event (inherits from EventEmitter) upon registering a new serverTask to which the server listens.
Now I would like my ConnectionManager to also listen to the event of the serverTaskManager, in order to make him push the next message in the messageQueue into processing.
Now the problem is, that I can catch the ServerTaskManager event within the ConnectionManager just fine, but, of course, the "this" within the listener is the ServerTaskManager, not the ConnectionManager. Thus calling any "this.someFunction()" functions that belong to the ConnectionManager won't work.
Here is some code:
/**
* ServerTaskManager - Constructor
* Implements Singleton pattern.
*/
function ServerTaskManager()
{
var __instance;
ServerTaskManager = function ServerTaskManager()
{
return __instance;
}
ServerTaskManager.prototype = this;
__instance = new ServerTaskManager();
__instance.constructor = ServerTaskManager;
return __instance;
}
util.inherits(ServerTaskManager, EventEmitter);
/**
* ConnectionManager - Constructor
* Also implements Singleton pattern.
*/
function ConnectionManager()
{
var __instance;
ConnectionManager = function ConnectionManager()
{
return __instance;
}
ConnectionManager.prototype = this;
__instance = new ConnectionManager();
__instance.constructor = ConnectionManager;
__instance.currentConnections = [];
// Listen for new serverInstructions on the serverTaskManager
serverTaskManager.on('newInstruction', function(messageObject, currentReceiver)
{
this.processNextMessage(currentReceiver);
});
return __instance;
}
util.inherits(ConnectionManager, EventEmitter);
Now when I run this and the "newInstructions" event is triggered by the serverTaskManager, node throws:
TypeError: Object #<ServerTaskManager> has no method 'processNextMessage'
Which is of course true. The function I want to call belongs to the ConnectionManager:
/**
* Starts processing the next message
*
* #param connectionId (int) - The ID of the connection, of which to process the next message.
*/
ConnectionManager.prototype.processNextMessage = function (connectionId)
{
// Some Code...
}
So obviously, when listening to the ServerTaskManager event, "this" within the listener is the ServerTaskManager. Now how do I call my ConnectionManager's function from within the listener?
I hope I am not completely misled by how events and listeners and/or prototypical extensions work (in Node). This project is by far the most advanced that I have worked on in JavaScript. Normally I am only coding PHP with a little bit of client side JS.
Thx in advance for any hints!
Worp
Like this.
serverTaskManager.on('newInstruction', function(messageObject, currentReceiver)
{
ConnectionManager.processNextMessage(currentReceiver);
});
Or like this.
serverTaskManager.on('newInstruction', function(messageObject, currentReceiver)
{
ConnectionManager().processNextMessage(currentReceiver);
});
PS: your question is unnecessarily long. When posting code, don't necessarily post your example. It is much easier to boil your code down to the simplest form that exhibits the behavior you are seeing. You'll get more quality responses this way.
In scala, how can I tell a thread: sleep t seconds, or until you receive a message? i.e. sleep at most t seconds, but wake up in case t is not over and you receive a certain message.
The answer depends greatly on what the message is. If you're using Actors (either the old variety or the Akka variety) then you can simply state a timeout value on receive. (React isn't really running until it gets a message, so you can't place a timeout on it.)
// Old style
receiveWithin(1000) {
case msg: Message => // whatever
case TIMEOUT => // Handle timeout
}
// Akka style
context.setTimeoutReceive(1 second)
def receive = {
case msg: Message => // whatever
case ReceiveTimeout => // handle timeout
}
Otherwise, what exactly do you mean by "message"?
One easy way to send a message is to use the Java concurrent classes made for exactly this kind of thing. For example, you can use a java.util.concurrent.SynchronousQueue to hold the message, and the receiver can call the poll method which takes a timeout:
// Common variable
val q = new java.util.concurrent.SynchronousQueue[String]
// Waiting thread
val msg = q.poll(1000)
// Sending thread will also block until receiver is ready to take it
q.offer("salmon", 1000)
An ArrayBlockingQueue is also useful in these situations (if you want the senders to be able to pack messages in a buffer).
Alternatively, you can use condition variables.
val monitor = new AnyRef
var messageReceived: Boolean = false
// The waiting thread...
def waitUntilMessageReceived(timeout: Int): Boolean = {
monitor synchronized {
// The time-out handling here is simplified for the purpose
// of exhibition. The "wait" may wake up spuriously for no
// apparent reason. So in practice, this would be more complicated,
// actually.
while (!messageReceived) monitor.wait(timeout * 1000L)
messageReceived
}
}
// The thread, which sends the message...
def sendMessage: Unit = monitor synchronized {
messageReceived = true
monitor.notifyAll
}
Check out Await. If you have some Awaitable objects then that's what you need.
Instead of making it sleep for a given time, make it only wake up on a Timeout() msg and then you can send this message prematurely if you want it to "wake up".
I'll preface this by saying I have minimal experience with both Perl and Socket programming, so I appreciate any help I can get. I have a TCP Server which needs to handle multiple Client connections simultaneously and be able to receive data from any one of the Clients at any time and also be able to send data back to the Clients based on information it's received. For example, Client1 and Client2 connect to my Server. Client2 sends "Ready", the server interprets that and sends "Go" to Client1. The following is what I have written so far:
my $sock = new IO::Socket::INET
{
LocalHost => $host, // defined earlier in code
LocalPort => $port, // defined earlier in code
Proto => 'tcp',
Listen => SOMAXCONN,
Reuse => 1,
};
die "Could not create socket $!\n" unless $sock;
while ( my ($new_sock,$c_addr) = $sock->accept() ) {
my ($client_port, $c_ip) = sockaddr_in($c_addr);
my $client_ipnum = inet_ntoa($c_ip);
my $client_host = "";
my #threads;
print "got a connection from $client_host", "[$client_ipnum]\n";
my $command;
my $data;
while ($data = <$new_sock>) {
push #threads, async \&Execute, $data;
}
}
sub Execute {
my ($command) = #_;
// if($command) = "test"
// send "go" to socket1
print "Executing command: $command\n";
system($command);
}
I know both of my while loops will be blocking and I need a way to implement my accept command as a thread, but I'm not sure the proper way of writing it.
Either fork, thread or do I/O multiplexing with select. Take a look at Net::Server and AnyEvent::Socket, too. For an example of I/O multiplexing, take a look at How can I accept multiple TCP connections in Perl?.