Ping vs HTTP HEAD - java

I'm writing a Java app which has a feature to check whether it's connected to the internet by periodically trying to access a server. My first idea was to Ping the server - but turned out to be complicated to achieve in Java. So I remade it to send HTTP HEAD requests and check for the HTTP response code instead. I have two questions:
1) Are HTTP HEAD requests "as reliable" as pings? Ping would be my first natural choice to check if something is available. Maybe just because it's so easy to run on the command line.
2) If I send HTTP HEAD requests to a third-party website to check if it is accessible, is there some standard frequency at which these should be sent? Eg if I send them every second, would that be discouraged or even get me blocked from those services?

An HTTP HEAD is generally more reliable than a ping, as ICMP connections are often blocked and HTTP is usually open. Checking for a connectivity every second sounds pretty excessive, but it really depends on your use case what third party site you are trying to "ping".

I can't comment on whether its more effective to use HEAD or trying to do something like drop to the system and do a ping; but I don't think either of them is the solution you should be doing. IMHO, it isn't necessary to poll your connection. There are a lot of situations where a connection could be dropped and I don't think polling will provide much in the way of mitigating the problem. Also, the user might be annoyed. I know that if I were using an application, and then started doing something else, and all of a sudden I got a "connection lost to 3rd party error" from an application I wasn't even paying attention to; I would be very annoyed.
If your application depends on a connection being present, then I think its fair to handle this with exception handlers. I'm willing to be bet that whatever API you're using throws some kind of exception whenever you attempt a network action and you aren't able to establish a connection. So, what I would do is in whatever class you're initializing the network action, I would follow this paradigm:
try {
performNetworkAction();
} catch (NoConnectionFoundException e) {
// handle the situation here
}
Your application shouldn't be able to determine when a connection was lost, just how to react when you attempt a network action and no connection is found.
That being said - you still may disagree with me. If that is the case then the frequency of polling allowed/recommended might be documented in the API for the service you're using. Also, if the resource from the 3rd party is static, you should cache it as opposed to getting it over and over again.

I wanted to expand #Dave's answer, and a comment would not suffice.
When you lose internet connectivity, a java.io.IOException is thrown. Look at the sub-classes of IOException - UnknownHostException, SocketException and ProtocolException are the ones that usually smell of "No Internet Connection"
Create a central place for handling exceptions (this is good practice in itself). If you get any of the IOException's I mentioned above, set isInternetAvailable to false.
Instead of polling for internet connection, switch to retrying the operation you want to perform. You achieve the same thing
Use a backoff strategy - exponential backoff works great. For example, after it fails the first time, you wait for 5s. After the second failure, you wait for 25s and so on. Gmail webapp uses this strategy. Twitter commons has utility classes for backoff.

Related

How to stop UnknownHostException in android

Let me tell you a bit about my app, when the app is in the background, I send some session data to my session_endpoint first, and if sending is failed, I get the exception that the host is unknown from try/catch and send it to same host, which is for sending exceptions exception_endpoint.
So my question is, how is it possible that I can send data to my exception_endpoint and cannot send to session_endpoint, is it about resolving domain ? sending methods are the same by the way. I lose my precious session data. How can I overcome this issue ?
I get java.net.UnknownHostException: Unable to resolve host.
There are several options how you can handle that exception. The simplest way is to cache the requests and fire them on the next app start.
You could also use the alarm manager to try it later or maybe even better use the JobScheduler, there you can define that you require network connectivity. If you need to support older platforms try the nice lib Android-Job. There you can define for much more platforms the scheduling.

SocketTimeoutException occurring non-stop after app has run for a while, but are instantly-solved by restarting it

I have a crawler Java application which is supposed to connect to some HTTP servers, download the HTML content of their pages, then move on to other HTTP servers. For this task, I've used the Apache HTTP library.
At the first few hours of the run, things seem to work rather smoothly (there are some connection-related exceptions thrown around from time to time, but that's to be expected).
Yet after a while, it seems like I keep getting SocketTimeoutException on every request I send out. The exception does not occur on the HttpClient class's "execute" method, but rather when I try to get the content of the Entity (which I retrieve from the HttpResponse object), or when I try to write that content to a file.
Then, if I stop the application, and start it over again, things seem to go back to working fine - even though it picks up from where it stopped at, meaning it's interacting with the same servers which I received the SocketTimeoutException when trying to interact with before.
I tried looking for all kinds of possible clean-ups that I might be missing and might be essential when using this library, but couldn't find anything.
Any help would be greatly appreciated.
Thanks.
This sounds like the kind of thing which could be caused by connection pools where you're not closing things when you're done with them, if the timeout occurs while the client library waits to retrieve a pooled connection. Are you sure you're closing everything properly (in finally statements)?
If you run Wireshark to monitor your traffic, what network traffic occurs while it's "broken"?
Make sure that you're not using a lot of http requests at the same time. For example, send 5 http requests, and wait for first response. Then you can make another request etc. Looks like your http requests opens too much sockets.

Play framework longpolling in online game

I'm working on a browser game with the play framework, and I definitely need longpolling, but I don't quite understand how to use it. WebSockets would be perfect for this, but it's not supported by that many browsers yet.
Here's what I want to do: When the user logs in, and navigates to the play game controller, I want to start a connection, and keep it open. I want to do this for all users that are online, so I can show a list of them on the site, so they can play with each other. I've looked at the documentation, but I don't understand how I could implement it in my case. Because there simply isn't anything I want to calculate (in the example they're generating a pdf) I just want the connection to stay open.
What I'm also wondering is, how I should keep track of all these open connections? Right now, I just have an online column in my users table in the database, which I update. SO everytime someone connects I have to update the database. Are there better ways to do this, or is this fine?
And lastly, assuming all of the above works. When player A, selects player B to play with: how do I notify player B of this? Do I just send some JSON code, and change the page with javascript, on player B's side, or do I send him to a totally different page? I'm not sure how to communicate when the two connections are established and the game has started.
Firstly, I think you need to appreciate the difference between Websockets and Long Polling.
Websockets creates a connection and keeps it open until the browser terminates the session, via some javascript or the user moving on from the page. This would give you the desired nature of what you are requesting. Looking at the Chat example in the Play download will show you how an entire Chat application is handled using Websockets.
Further to Pere's answer regarding Play's statelessness. The Play creators have suggested that a single Websocket connection, regardless of how long it is open for and how many requests are sent back and forther, is considered to be a single transaction. Therefore, saving to the database in between each Websocket request is not needed (again, you can see that nothing is saved in the Chat example). Using this method, you would be expected to save the details when the Websocket is finally closed, or indeed all Websockets, depending on your use-case.
Long Polling on the other hand opens a connection to the server, and the server simply waits until there is something to send back to the client. If you need to push any data to the server, you would do this as a separate AJAX request, so you would effectively have two requests open at once. You don't necessarily know when a user logs off, unless you send a request just as they leave the page, to let the server know they have gone, but this is not always successful. Long Polling can work, but it is not as neat a solution as Websockets, but as you say, this is not widely supported yet.
My suggestion would be to study the Chat example (as it has a Long Polling and Websockets version). This will be the most effective way to get up and running with your requirements.
As for your final query regarding how to notify the other player. In Long Polling, you would simply respond to the suspended request with some JSON. With websockets, you would send an event back to the client. Again, both approaches can be pretty clearly figured out from the Chat example.
I have also written a Blog post on Websockets, which may help you understand this process a little better.
On the Websocket part, as you can see here (1st answer) the support is not so bad, and you have a Javascript fallback if there is some problem with the browser. This would simplify your scenario, as long polling may be more complicated to manage.
On the issue of keeping track, as Play is stateless you have to store the flag in the database and remove it when they close the connection. Otherwise you are breaking the statelessness.
About the notification, you have to send some message to B, but don't move them to another page as it may be confusing and cause bad user experience. Use Json to pop some message (in a div) alerting them of the game starting or the request to play.
I'm not using the "play" framework.
But I've been lately researching and tinkering with http-based long polling. Websockets, if available, is much more appropriate for realtime messages!
As for long-polling, I found that using a "cargo truck" analogy helped me reason about long-polling quite effectively. Here's a little note I wrote on the subject:
http://dvb.omino.com/blog/2011/http-comet-realtime-messages/
Perhaps you or future greppers may find it useful.
You might also want to take a look at the Juggernaut project which is based on node.js and Redis and gives you a "realtime connection between your servers and your client browsers". When using a Java Redis client like Jedis, you should easily be able to integrate the whole thing with the Play framework!

server push or client push is better?

I am developing a chat website using jsp/servlet.I will be hosting my website on gooogle appengine .Now i have some doubts regarding whether to use server push or client pull technology
1)If i use server push and if i dont close the response of servlet will it cause the server to go slow?How many simultanious connection can a tyicall tomcat server can handle if i keep the socket open for the entire chat session between 2 clinets??
2)Will server push or clinet push be better??
If you are using a servlet (prior to 3.0), then I guess you'll have to go with pull because of the programming model of servlet. However, there ARE advantages in using a push model. Primarily, wasted load on server and the limitation in latency. That's why there are technologies such as comet. Servlet 3.0 also supports push model. These are commonly used in ajax based apps.
In fact I believe a push model is more suited for a chatting app. because of the fast response time (=better user experience) it can provide.
If you use a nio based implementation for push-model, you can support thousands or even more than 10k concurrent connections (obviously, your millage varies).
If you use a conventional IO based implementation, it will be likely in the range of hundreds of concurrent connections (don't take this estimation too seriously though. I'm just giving these numbers to give a very, very rough feeling).
As for tomcat, last time I checked, people were saying that it won't have a good push-model support until version 7.0. But I'm not following the current status so I'm not sure (Sorry, perhaps somebody else can help you on this). If that is the case, you might want to check out comet support of jetty.
grizzly and netty are also good NIO based network frameworks, but if you want to use JSP, and find that tomcat is not sufficient, I guess jetty would be the best bet.
edit: (some additional info)
In this "push models", it's not like the server opens a connection to the client. The connection will be kept alive, and the server will push messages as it sees fit.
Also, it's not like there are only "push" and "pull" models. You can have a hybrid, like long polling.
I don't know how are you thinking of achieving server push here. As far as I can see, server needs a request to respond over HTTP. So, when there is a request, server will respond to that.
If i use server push and if i dont close the response of servlet will it cause the server to go slow?
App Engine will not let you do that. You have to finish your response within thirty seconds, or it will be killed. The thirty seconds is also an edge case, most calculations they do (for quota and such) are based on a 75 millisecond response time.
How many simultanious connection can a tyicall tomcat server
Tomcat? I thought you are planning to use App Engine?
Pull. Always pull.
I know it's a manufacturing-oriented book but the advice from Lean Thinking (Womack & Jones) is invaluable in any context (roughly, from memory):
Start by defining value,
line up the activities that create value in the value-stream,
create flow across the value-stream,
let customers pull value from the value-stream,
compete against perfection rather than other organizations
If I misquoted them, I apologize. Anyway, all of those principles can easily be applied in the development of any software product just as they could in the production of any physical product but the one that matters for you is pull.
Letting consumers of a service pull rather than pushing to them not only makes your programming model easier, it aligns activity with demand. You can still use queuing to load-level over time, if you have to, just the way you could with push but, this way, you have complete visibility into what, exactly happens in any given transaction.
I don't quite get your first question but the answer is still pull.
The answer to your query depends on what underlying protocol you wish to use.
Since you have mentioned JSP/servlets, your app will be implemented over the HTTP protocol.
HTTP is a protocol over TCP. TCP is connection oriented and remains alive, until the connection is ended. However, HTTP connections are persistent, only for the duration of a single request-response cycle. The TCP connection is broken after every request-response cycle. So that should answer your doubt with regards to how many socket connections a typical TOMCAT server will be able to handle. The connections will not be persistent, at all. They will only last the duration of a HTTP request-response cycle.
Given this basic idea, I would suggest , you use a client pull strategy, to implement your app.
Even with server push, over HTTP, even though the name says "server push", it is always the web client that polls the server at regular intervals, which just gives an illusion of "server-push". HTTP specification mandates that the client makes a request to which the server responds.
I have considerable experience in developing chat applications (both mobile and web).
Let me know , if you need any assistance. I will be more that willing to help.

How do I test the availability of the internet in Java?

I don't want to tell the hard way that the internet is unavailable when I catch an exception from url.openStream().
Is there a simple way to tell if the computer is connected to the internet in Java?
In this scenario, "connected to the internet" means being able to download data from a specific url.
If I try to download from it and it is not available, then the program hangs for a bit. I dont want that hanging. Therefore, i need a fast way of querying whether the website is available or not.
The problem you are trying to avoid is waiting for for your http connection to determine that the URL you are trying to access is really unavailable. In order to achieve this you need to stop using url.openStream() which is a shortcut for openConnection().getInputStream() and get some finer control over your connection.
URLConnection conn = url.openConnection();
conn.setConnectTimeout(timeoutMs);
conn.setReadTimeout(timeoutMs);
in = conn.getInputStream();
This code will allow you to timeout the connection attempt if either the connection or the read exceeds the time you provide in the timeoutMs paramater.
Use
Process p1 = java.lang.Runtime.getRuntime().exec("ping www.google.com");
System.out.println(p1.waitFor());
// return code for p1 will be 0 if internet is connected, else it will be 1
There is no such thing as "Internet availability".
Imagine that your HTTP request go through a transparent HTTP proxy, you are trying to access a blacklisted site and you get a HTTP response from the proxy server telling you about access denied. Is Internet available in this scenario or not?
I think you shall be more specific about your problem.
You might be able to tell if a compouter is connected to a network but even if it is there's no guarantee the networking is working or that it's connected to the internet.
This is one of those "suck it and see" problems.
What's wrong with trying to connect? And why are you concerned whether or not they're connected to the internet?
If the criteria is whether you can access a given web server the only way to find out, is to access that web server.
You can, however, do it in a background thread at start up so the application is not delayed by it. Then the "yes/no" answer is available when the actual downloading is desired. Put a message in the status line so the user knows what is going on and is not suprised about uninitiated "connect to network" if s/he is not connected when your program is started.
I don't know much about the low level HTTP plumbing available in Java, but you could always issue an http HEAD request for the url in advance. This causes the server to send back only the headers and not the data. With a 1-3 second timeout, you should be able to avoid any lengthy delays.
If you program is hanging while waiting to download then you are probably using the GUI thread to do the download. If you use a background thread, your program won't hang even if it take a long time to timeout/download.
You could send an ICMP message to a very well known host...
You can check for a NTP server if your firewall does not forbids.
Any way I think the best option is to try to open an URL as you try to avoid, because is the service most commonly to be opened.
You can check for one or two dynamic URL that change constantly. For instace, some web that shows time. For instance this one i found googleing. More than one because the sites can be down ;-)

Categories