Pinging a Game Server for Status and Speed

Hey there,

I recently created a New Relic account to explore possibilities with monitoring all of our services in one place. So far we’ve made good use of the Synthetics system, but we want to expand upon that further. We’re a small network that manages a handful of websites, hosting servers and game servers and our main question is how do we monitor a game server that requires a specific IP and Port. I’ve tried looking into this but as I’m not as knowledgable on this I’m not sure how to set up a custom API script to Ping a game server through the IP and port which is able to return either the server status of being online/offline or the connection time in (ms), mostly the same to ICMP.

Any help would be greatly appreciated on how I can go by doing this,

Thank you :slight_smile:

Hi there @adam27 -

Thanks for your patience during the holidays and welcome to the community!

You should be able to specify the port with your request. For example, https://url.com:9001/ .

Please let me know if that does not get you what you need!

Hey there!

Thanks for the response :slight_smile:

So my only concern with using this system is 1) Would this be through the ping monitor type? And 2) Since I’m trying to ping an IPv4 would this still work? As it seems to be a HTTP ping in your suggestion.

Thanks again.

Hey there @adam27 -

Yes, a ping monitor is exactly what I am suggesting. The basic gist is, if the site can be accessed in a browser, you can use a ping monitor. So here, the test would be to just load the address you want to use in the address bar of your browser — if that works, then our ping monitor should work.

Let me know if this does not work and we’ll keep troubleshooting with you!

Hey there again,

I really do appreciate the help with this, but you have to understand that this isn’t for a HTTP ping, this IP cant be reached through the browser making this a non-browser situation as its a server.
For this to work, it needs to be a TCP Ping where it pings the specified IP and port number, and I’m asking how this can be accomplished, either through an API script or some other way.
If the IP:PORT was to be placed in the browser like that it results to “ERR_INVALID_HTTP_RESPONSE”.

Thanks,

Adam

Thanks Adam - sorry. I did not realize that you were looking for a TCP connection, but that makes complete sense.

We do have an example script for TCP in this post:

Let me know if that does not help you.

1 Like

Hey again!

Yeah I’ve managed to read over that post a few times prior, but the issue is that the TCP Example is strictly only for HTTP, as it uses the HTTP GET, so it cant be used with an ipv4.

Unless there’s something that I’m overlooking here?

Thank you, and happy new year,
Adam

The example of using the net module to test TCP ports was created with an HTTP port just to make the example easier to create. The net module can be used to connect to any non-secure (no SSL/TLS) TCP port much like was done with port 80 and the Google URL in the current example.

If you need to connect to a secure TCP port, please use the tls module instead which was added to the private minion image as of version 3.0.32 and is also available from public locations. Usage would essentially be the same as the net module in the example, but you would need to use var tls = require(‘tls’) instead and use tls.connect instead of net.connect.

2 Likes

Hey there bpeck,

Thank you for the response and clarifying some of the information on how the TCP monitor works.
So when changing over the TCP monitor you provided in the example with the tls module (Without changing anything else), the monitor fails when pinging my server IP and port: “There was an internal error processing your request”. Again, I really don’t know what I’m doing, I tried changing the script as much as possible to work but just resulted in more problems.

Here’s the script in its current state, and I’m aware that its a mess as its incorporating HTTP checks with IP checks but I’m out of ideas:

var tls = require('tls');

var client = tls.connect({
    port: 298XX,   (Last 2 digits hidden for forum page)
    host: '139.99.184.68'
    }, () => {

    console.log('connected to server!');
    client.write('GET / HTTP/1.1\r\n');
    client.write('Host: 139.99.184.68\r\n');
    client.write('User-Agent: Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1)\r\n');
    client.write('\r\n')
})

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

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

Note don’t worry about showing the IP or port, their not private addresses.

I’m not sure how your game server works, but in this example you are connecting to the port and requesting a HTTP page from the server, which doesn’t sound like what you want to do.

When you test connectivity to your game server, do you need to send anything over the connection after connecting to receive a response that indicates your server is working correctly? If so, those items would need to be included as client.write lines.

What does the server send in the response? To validate data received, you would add logic to the client.on(‘data’) section. What in the response tells you that your server is working correctly? Does simply being able to connect provide this validation?

You mentioned that you received an internal error when executing your monitor. Are you running this from one of our public locations or have you created a Docker or K8S based private location for this test?

Okay this might make it better to understand my madness,
So all I’m trying to achieve is the port check tool that Pingdom has, you enter the IP and the port and it will periodically ping the service to check if its online. This is all I’m wanting to do, is a check that’s able to identify whether the port is OPEN, or CLOSED. When it reports back it will fail if its closed and will continue functional when it’s open.

(We’re also just using public locations, built into synthetics)

This website below is pretty much the whole idea, you enter the IP and port and it checks the status of the port, now how possible will it be to do this in New Relic Synthetics?
https://www.yougetsignal.com/tools/open-ports/

Ok, I understand what you are trying to do now. Since you are only validating that you were able to connect to the port, you can change the script to look something like this:

var tls = require('tls');

var client = tls.connect({
port: 298XX,   (Last 2 digits hidden for forum page)
host: '139.99.184.68'
}, () => {

console.log('connected to server!');
client.destroy();
})

If the script is able to connect to the port, it will log out that it connected to the server and then end the connection. If the port connection fails or times out, the script will fail. I tested this by attempting to connect to Google on a port that is not open (8080). You should see the same behavior on your server.

If you would also like to time how long it is taking to connect to your server and fail after X milliseconds, you can use this example instead.

var assert = require('assert');

var tls = require('tls');

const timerstart = Date.now();

var client = tls.connect({
  port: 443,
  host: 'www.google.com'
}, () => {
  console.log('connected to server!');
  client.destroy();
  const connectTime = Date.now() - timerstart;
  console.log('Connected in: ' + connectTime + ' ms');
  $util.insights.set("connectTime", connectTime);
  assert.ok(connectTime < 2000, "ERROR - took longer than 2 seconds to connect. Connect time: " + connectTime);
})

This example uses the $util.insights.set function to add an additional attribute to your SyntheticCheck events for this monitor execution. This allows you to trend the connection time with a NRQL query (replace the monitorName value with your monitor name):

SELECT average(custom.connectTime) FROM SyntheticCheck WHERE monitorName = 'Port Connection Timer' TIMESERIES

Hey again, this is looking really good! However, when validating/executing the script it fails with the following error:

Error: 139833476867904:error:1408F10B:SSL routines:ssl3_get_record:wrong version number:…/deps/openssl/openssl/ssl/record/ssl3_record.c:252:

This error appears to appear on both of the scripts you provided so I’m not sure if it’s with the SSL of the destination server, or New Relics open SSL files.

It is possible based on that error that you don’t need to use TLS / SSL to connect to the port on your game server. Do you get connected correctly if you use the net module instead of tls? I tried to update the example script to use net and the IP/port details you shared above.

var assert = require('assert');

var net = require('net');

const timerstart = Date.now();

var client = net.connect({
  port: 298XX,
  host: '139.99.184.68'
}, () => {
  console.log('connected to server!');
  client.destroy();
  const connectTime = Date.now() - timerstart;
  console.log('Connected in: ' + connectTime + ' ms');
  $util.insights.set("connectTime", connectTime);
  assert.ok(connectTime < 2000, "ERROR - took longer than 2 seconds to connect. Connect time: " + connectTime);
})

If this doesn’t work, it is also possible that a secure connection is required but a protocol that is not supported in the tls module in this version of Node is being used (SSLv3, TLS 1.3 for example). Do you have any of these details about the connection requirements for this port that can be shared here?

1 Like

Hey Brian,

Wow, Legand. You are seriously a life saver, I think I was overthinking the situation a lot.
Everythings working with that no SSL script, it solved my problem and most likely a few others.

Even though it would be nice to have an official function for this built into New Relic alongside ping for a port monitor, it works perfectly.

Thank you!

2 Likes