I am new to Android programming and I have been facing problems that didn't exist in native Java. When I run this code in my computer, it runs correctly. But, when I run it in my device.I get nothing, I even tried to post the message to UI and there's no logcat for this. I am not sure what is wrong.
try{
Socket socket = new Socket(serverAddr, SERVER_PORT);
Log.i("TAG","Socket connected");
}catch(IOException e){
Log.i("TAG","Socket not connected");
}
Update 1: I just changed the code..nothing much and realized that after 2 minutes or so it does what it was supposed to do?? Is is anything to do with keep alive flags? Or is there anyway that I can run the code just for a second or two and stop it. Please understand that the code below the socket creation line executes only after 2 minutes if the server is dead. Here below is my code:
try{
InetAddress serverAddr = InetAddress.getByName(serverIP);
//Line below executes with no delay
postToUI("Trying to connect to standalone server" + "\n\n");
socket = new Socket(serverAddr, SERVER_PORT);
//Line below executes after 2 minutes
postToUI("Successfully connected to standalone server" + "\n\n");
}catch(ConnectException e){
postToUI("Socket not connected");
}catch(IOException e){
postToUI("Socket not connected");
}
I have done very few Andrioid development so don't bite me smiley.
Possible reasons why the host might not communicate with the client
Host has firewall which might be closing the connection (unlikely)
Host might have unexpectly shutdown e.g power failure (unlikely)
Host might not properly port forwared (possibly)
Your andriod app doesn't have the proper manifest that allows the use of sockets.
Your andrioid device you are testing on might have its internet disabled which can enabled easily.
Host's address could have changed if it is dynamic.
For logcat, I think that logcat only displays log messages for the main thread. But I am unsure.
Related
I am creating a chat application, which runs as a service. I connect to the chat server using a socket, and I declared a timeout using setSoTimeout.
When a connection is idle, (for example when I am at home and connected to WiFi) I never face issues. When I go outside, and my WiFi connection is lost, my phone switches to 3G. The problem is that the socket stays connected without receiving any data. (So the timeout exception isn't called.) < sometimes it connects after 30 mins, but this need to be reduced to at least a few seconds.
I also tried to add a CONNECTIVITY_CHANGE broadcast detector in my AndroidManifest.xml, this also didn't work.
See my socket connection below:
socket = new Socket(proxy);
SocketAddress socketAddress = new InetSocketAddress(HOST,
PORT);
socket.connect(socketAddress);
if (socket.isConnected()) {
socket.setSoTimeout(1020000); //Even when setting to 10000 makes no sense
return true;
} else {
Log.w("WARNING", "Failed to connect to the server");
return false;
}
In the background there are also some loops running which checks the server for chatmessages, these loops triggers a reconnect when no data is received, but this didn't work too. (During reconnect, I set the socket to socket.close() and socket = null before connecting again.)
So are there any ideas, maybe I need to use a different socket? Or some other code to resolve this problem? Thanks.
In such unexpected(as per application's perspective) network disconnection, the socket won't know it was disconnected. If this situation occurs, the only way is to try writing some data to the socket. When the socket is disconnected, writing data would throw IOExcpetion with message like Connection reset.
You'd better implement a heartbeat method to detect the disconnection. A packet sent to server every 5~10 seconds would detect network disconnection speedy enough.
I'm trying to create one simple app. I want to my cell phone be a server socket and I'm trying to send messages from my pc, my pc is the client is this case.
When they are in the same network it works fine but when I connect my cell phone in a 3G network I receive the error "Connection timed out" in my PC.
I'm using a host from no-ip (in both situation). When I do 'telnet mycellphonehost.org 8080' for example I have no problem, it is able to connect. I think the no-ip host is working fine because is give me the correct external IP.
I also use one app called FIREBIND for test if the port is open or not. The result is: "Firebind was successfully able to both transmit and receive data over this port using the TCP protocol."
I already read a lot questions about this subject, similar problems... but nothing help me solve this issue. I hope someone can help me. Thanks in advance!
Follow the codes:
Android Server
try{
ServerSocket server = new ServerSocket(port);
Socket s = server.accept();
BufferedReader input = new BufferedReader(new InputStreamReader(s.getInputStream()));
System.out.println(input.readLine());
input.close();
s.close();
server.close();
}
catch(IOException e){
System.out.println("ERROR: " + e.getMessage());
}
PC Client
try{
Socket s = new Socket("myhostfromno-ip.org",port);
PrintStream output = new PrintStream(s.getOutputStream());
output.println("TEST MESSAGE");
output.flush();
s.close();
}
catch(IOException e){
System.out.println("ERROR: " + e.getMessage());
}
PS: They have to be in different network
I would recommend using GCM for the cell
Notification and afterwards making a server pull. It certainly is much faster and you could use a simple REST server for serving data.
You need to make your PC the server and your droid the client.
I need to build an application which can receive data from over a network and use this data to do some unrelevant things with.
Here's a piece of code to make clear what I'm doing.
On the server side:
static Socket client = null;
static ServerSocket ss = null;
if (ss != null) {
ss.close();
}
ss = new ServerSocket(5513);
isrunning = true;
System.out.println("Waiting for client...");
client = ss.accept();
System.out.println("Client accepted.");
BufferedReader in = new BufferedReader(new InputStreamReader(client.getInputStream()));
And the client side:
Socket client = null;
PrintWriter out = null;
try {
client = new Socket("hostname", 5513);
out = new PrintWriter(client.getOutputStream(), true);
}
Please note that this is just a piece of the code. There are no errors in the code.
After running the server-sided piece of code, it correctly waits for the client to connect.
Now here comes the problem. As soon as I try to connect from the client side, I'm getting a "connection refused"-error.
HOWEVER, I found something on the internet whoch told me to try telnetting from the client side. For example, let the server-sided IP be 192.168.1.1. So, after using this command:
telnet 192.168.1.1 5513
I actually get a connection with the server. The command will launch an empty screen, and everything I manually type in the command line will be sent to the server-side after pressing enter (checked with debugging).
So, I can manually connect to the server-side and send some data, but my code refuses to connect.
Anyone who knows what I am doing wrong?
Is this the code you're actually using?
client = new Socket("hostname", 5513);
Try changing it to:
client = new Socket("192.168.1.1", 5513);
client = new Socket("hostname", 5513);
Hostname needs to represent the IP Address you're connecting to. If you're trying to connect to yourself, it would be "localhost"
Also, the server is not listening for the client AT ALL TIMES, there must be a while loop so the server listens and accepts connections.
while (true) {
client = ss.accept();
out = new PrintWriter(client.getOutputStream(), true);
//You should probably assign it to a seperate thread to handle stuff for this client
}
And I should explain on why you're getting that particular error. When something says that the connection is refused, it usually means that the IP Address you want to connect to knows your sending a connection and is blocking it because it was not listening for that connection. Basically, when the server closed, you stopped listening for the client, so anything that came in on that port would be blocked. Of course, the other case could be that Java was blocked on your firewall and an exception should be made for it. Although this is rarely the case if what you're trying to accomplish is over a LAN.
You're not actually using "hostname" in your Socket object in the client are you?
It should the 192.168.1.1.
Are you on Windows? and If so have you added java.exe and javaw.exe to Firewall with inbound and outbound enabled? and have you added a rule for 5513 to your Firewall?
If yes Windows but no Firewall settings, that's your answer, open up your Firewall.
I am trying to connect to server using a Java socket. I am trying to connect from port 80 to 90
int port;
Socket clientsocket;
String hostname = "www.google.com";
for(port = 80;port<=90; port++){
try{
clientsocket = new Socket(hostname,port);
System.out.println("Connection at port " + port + "\t" + clientsocket.isConnected());
clientsocket.close();
}
catch(Exception e){
System.out.println(e.getMessage());
}
}
When I try to connect to any website like google.com or w3schools.com my program hangs on the socket() call for port numbers except 80.
Since those websites are not serving on ports 81-90 it should raise exception but instead it gets blocked. For port 80 it works fine.
When I try to connect to the apache server installed on my machine, it doesn't block for any port number and gives me Connection refused error which is the obvious behavior.
So why is it happening. Thanks in advance.
When I try to connect to any website like google.com or w3schools.com my program hangs on the socket() call for port numbers except 80. Since those websites are not serving on ports 81-90 it should raise exception but instead it gets blocked.
This is almost certainly not Java's doing.
When you invoke the Socket(String, int) constructor, the JVM asks the OS to attempt to establish a connection to the IP address corresponding to the supplied name, using the supplied port number. Assuming that we're talking TCP/IP, the OS sends off a TCP 'SYN' message, and waits for a response:
If the response is a 'SYN-ACK', it proceeds to establish the connection as per the protocol; see http://en.wikipedia.org/wiki/Transmission_Control_Protocol#Connection_establishment.
If the response is an 'RST' (reset), the connect fails and this results in a Java "connection refused" exception. (This is typically what happens if the 'SYN' makes it to the remote server, only to discover that there is no application "listening" on the port you tried to connect on.)
If the response is an ICMP message of some kind (e.g. ICMP destination unreachable), this typically results in an immediate failure of the connection request, and a Java exception.
If there is no response, the OS tries again, and again, and again. Depending on the Java default connect timeout (or the explicit timeout), this process could continue for a long time.
So what is most likely happening is that something is filtering the 'SYN' messages on funky ports, and simply throwing them away. It could be the local firewall software on your PC, firewall software in your gateway, or your ISP's network, or software in the remote system you are attempting to talk to. Or this could be happening to the 'SYN-ACK' message coming back.
Either way, the blocking / timeout behavior is inherent to TCP/IP networking, and it is impossible to accurately diagnose at either the OS or Java levels. You simply need to adjust your expectations. (Or set a shorter connect timeout ...)
For this case, and any case:
/**
* Create end point and initialize connection with custom timeout for refused or server offline
*/
try{
InetSocketAddress endPoint = new InetSocketAddress(serverAddress, portNumber);
Socket socket = new Socket();
socket.connect(endPoint, 10000);
} catch(Exception e){
//... Handle connection error
}
I hope you can help. Im fairly new to progamming and Im playing around with java Sockets.
The problem is the code below. for some reason commSocket = new Socket(hostName, portNumber); is returning true even when it has not connected with the server (server not implemented yet!). Any ideas regarding this situation?
For hostName Im passing my local machine IP and for port a manually selected port.
public void networkConnect(String hostName, int portNumber){
try {
networkConnected = false;
netMessage = "Attempting Connection";
NetworkMessage networkMessage = new NetworkMessage(networkConnected, netMessage);
commSocket = new Socket(hostName, portNumber);
// this returns true!!
System.out.println(commSocket.isConnected());
networkConnected = true;
netMessage = "Connected: ";
System.out.println("hellooo");
} catch (UnknownHostException e){
System.out.println(e.getMessage());
} catch (IOException e){
System.out.println(e.getMessage());
}
}
Many thanks.
EDIT: new Socket(.., ..); is blocking isnt it? i thought in that case if that was processed without exceptions then we have a true connection?
EDIT: I played around with anti virus and now it is working!
Had that exact same situation a few days ago on a corporate computer, and searched for it for hours.
Check your antivirus, some antivirus (like E*** N**32) use live TCP scanning that make a connection succeed even if nothing is listening on the target port but will reset it later when you try to read/write from the socket.
Add this to your code:
commSocket.getOutputStream().write(0);
commSocket.getInputStream().read();
If you get a SocketException now, you should really consider to change your antivirus.
Alternatively, set a breakpoint in your application right after creating the socket, and then use netstat -ano (on Windows) to check which process id is associated with the other endpoint of your socket (which should be on your machine if you connect to localhost).
I would suggest you to disable your antivirus, but in some cases even that does not help to unload their broken live TCP scanning driver...
The Socket constructor connects right away and will throw an IOException if it doesn't succeed. So apparently you have connected successfully to a server (this could be one you didn't make yourself).