Nodejs - getting client socket to retry after 5 seconds

Just start programming and writing a tcp socket client in node.js.

I want the client to connect to the server. If the server is not available (i.e. the server does not exist on the negotiated port), then I want the client to timeout and reconnect after timeout.

I have this code but it hangs in the second client.connect. What's wrong?

var net = require('net');
var HOST = '127.0.0.1';
var PORT = 9000;
var client = new net.Socket();

client.connect(PORT, HOST, function(){
    console.log('CONNECTED TO: ' + HOST + ':' + PORT);
    client.write('I am Superman!');
});

client.on('error', function(e) {
    while (e.code == 'ECONNREFUSED') {
        console.log('Is the server running at ' + PORT + '?');`

        socket.setTimeout(1000, function() {
            console.log('Timeout for 5 seconds before trying port:' + PORT + ' again');
        }

        client.connect(PORT, HOST, function(){
            console.log('CONNECTED TO: ' + HOST + ':' + PORT);
            client.write('I am the inner superman');
        });
    }); 
});

      

Updated code:

var net = require('net');
var HOST = '127.0.0.1';
var PORT = 9000;
var client = new net.Socket();

client.connect(PORT, HOST, function(){
    console.log('CONNECTED TO: ' + HOST + ':' + PORT);
    client.write('I am Superman');
});

client.on('error', function(e) {

    while (e.code == 'ECONNREFUSED') {
        console.log('Is the server running at ' + PORT + '?');

        client.setTimeout(4000, function() {

            client.connect(PORT, HOST, function() {
                console.log('CONNECTED TO: ' + HOST + ':' + PORT);
                client.write('I am inner Superman');
            });         

            console.log('Timeout for 5 seconds before trying port:' + PORT + ' again');
        });
    }
});

client.on('data', function(data) {
    console.log('DATA: ' + data);
    client.destroy();
});

client.on('close', function() {
    console.log('Connection closed');
});

      

With updated code, the timeout does not take effect. When I run this client without a matching server, the result is shown below without waiting for 4 seconds.

Is the server running at 9000?
Is the server running at 9000?
Is the server running at 9000?
Is the server running at 9000?


      

Update (painting the wrong tree?)

I went back to look at the socket.on ('error') event and saw that the close event is fired right after the error. This way the code will close tcpclient without waiting 4 seconds. Any better ideas?

+2


source to share


2 answers


The timeout is canceled.

It should look like:

var net = require('net');
var HOST = '127.0.0.1';
var PORT = 9000;
var client = new net.Socket();

client.connect(PORT, HOST, function(){
    console.log('CONNECTED TO: ' + HOST + ':' + PORT);
    client.write('I am Superman!');
});

client.on('error', function(e) {
    if(e.code == 'ECONNREFUSED') {
        console.log('Is the server running at ' + PORT + '?');

        client.setTimeout(4000, function() {
            client.connect(PORT, HOST, function(){
                console.log('CONNECTED TO: ' + HOST + ':' + PORT);
                client.write('I am the inner superman');
            });
        });

        console.log('Timeout for 5 seconds before trying port:' + PORT + ' again');

    }   
});
client.on('data', function(data) {
    console.log('DATA: ' + data);
    client.destroy();
});
client.on('close', function() {
    console.log('Connection closed');
});

      



The function you want to run after timeout is the callback. This is the one waiting to be executed.

Also, change while

to if

, this condition will not change during a single error event. And your pairings and braces are incompatible.

+6


source


per my comment on the accepted answer, I discovered the problem using callback .connect

vs listener 'connect'

. Every time you call .connect it will issue a callback (add a listener) even if the connection fails. So when it finally connects, all calls are made. Therefore, if you use .once('connect'..

, then this will not happen. Following are the entries from my project client code that led me to this observation.

ENOENT
timeout
ENOENT
timeout
ENOENT
timeout
ENOENT
timeout
ENOENT
timeout
ENOENT
timeout
ENOENT
timeout
ENOENT
timeout
ENOENT
timeout
(node:21061) MaxListenersExceededWarning: Possible EventEmitter memory leak detected. 11 connect listeners added. Use emitter.setMaxListeners() to increase limit  
^=== if you timeout and try .connect again eventually you hit this limit
ENOENT
timeout    <==== here is where the connection finally happens
connecting  <====  now all those listener callbacks fire.
connecting
connecting
connecting
connecting
connecting
connecting
connecting
connecting
connecting
connecting

      



try this version below.

const net = require('net')
const HOST = '127.0.0.1'
const PORT = 9000
const client = new net.Socket()

const connect = () => {client.connect(PORT, HOST)}

client.once('connect', function(){
  console.log('CONNECTED TO: ' + HOST + ':' + PORT)
  client.write('I am Superman!')
})

client.on('error', function(e) {
  if(e.code == 'ECONNREFUSED') {
    console.log('Is the server running at ' + PORT + '?')
    console.log('Waiting for 5 seconds before trying port:' + PORT + ' again')
    setTimeout(connect,5000)
  }
})

connect()

client.on('data', function(data) {
  console.log('DATA: ' + data)
  client.destroy()
})
client.on('close', function() {
  console.log('Connection closed')
})

      

+2


source







All Articles