Thank everyone to see my problem.
I'd like to explain my problem on Socket with java.
Using socket ,one for server to waiting for connection from client, the other for client to connect with server. THERE ARE TWO PROBLEM~~
(1)
+++After they all connect with each other, the two side can exchange messages to each other. I'have already finished the two Application code with server and client with each own main THREAD,but I can't let them communicate with each other. I use windows command to run this two file .class. I run server first ,and then I run client. They can't communicate with each other. I Want to know whether this is a problem about congestion.If I establish a another thread ,this problem could be solved??
(2) I attempt to run this two application on two eclipse,in other words each eclipse run one application. Why this problem can be solved??
(3)HERE is my code for client:
import java.util.*;
import java.io.*;
import java.net.*;
public class CC {
public static void main(String args[]){
Socket client=null;
DataInputStream in=null;
DataOutputStream out=null;
try{
client=new Socket("127.0.0.1",2060);
in=new DataInputStream(client.getInputStream());
out=new DataOutputStream(client.getOutputStream());
System.out.println("You are a client,you send message to server");
Scanner cin=new Scanner(System.in);
while(true){
String send=null,receive=null;
System.out.println("Please input Client message sending to server!");
send=cin.nextLine();
out.writeUTF(send);
receive=in.readUTF();
System.out.println("Message from Server is:"+receive);
Thread.sleep(500);
}
}
catch(Exception e){
System.out.println("break!"+e);
}
}
}
Here is my code for server
import java.util.*;
import java.io.*;
import java.net.*;
public class SS {
public static void main(String args[]){
ServerSocket socketServer=null;
DataInputStream in=null;
DataOutputStream out=null;
Socket server;
try{
socketServer=new ServerSocket(2060);
}
catch(Exception e1){
System.out.println("can't estblish socketServer "+e1);
}
try{
Scanner cin=new Scanner(System.in);
System.out.println("you are server ,please send message to client");
server=socketServer.accept();
in=new DataInputStream(server.getInputStream());
out=new DataOutputStream(server.getOutputStream());
while(true){
String send=null,receive=null;
receive=in.readUTF();
System.out.println("get message from client is "+receive);
System.out.println("send message from client");
send=cin.nextLine();
out.writeUTF(send);
}
}
catch(Exception e){
System.out.println("break! "+e);
}
}
}
The server and client code deadlocks.
In the client code you have written send=cin.nextLine();, which blocks until more input is available. In the server code you have written receive=in.readUTF(); which too blocks until input is available.
That is, immediately after a connection is established, both the server and the client expects the other to send something which results in a deadlock and both of them wait indefinitely.
You have to make sure that either the server or the client first sends some output before waiting to accept input.
thank you,I have solve this problem under my friends.Because I have run this application before,the port has been occupied.Then I run this application for the second time,this result these two application can not transfer message. These two Application is totally right.
Related
So I'm trying to communicate via client/server using sockets between a raspberry pi and a laptop. I've been able to send basic strings over using a simple python script on my pi to get the basic idea of how it worked. Now I got a little more advanced and started using OpenCV along with a usb camera to make a little security system that detects motion in the frame of the camera. I have the python script with the security system connect with the server and it is supposed to print out "Occupied" or "Unoccupied" in the console on my laptop in real time (eventually supposed to open a pop-up menu alerting that motion is detected) but it only prints out a long huge string of either "Occupied" or "Unoccupied" once I close the connection with my Pi. Why isn't it printing out in real time? Here is the java code on my laptop, unforunately my Pi is in school at the moment and I can't access the python code but I will post it tomorrow.
public class PyComms {
public static void main(String[] args) {
try{
ServerSocket server = new ServerSocket(4444);
System.out.println("Waiting for client on port 4444");
while(true){
Socket connected = server.accept();
System.out.println("CONNECTED WITH CLIENT");
BufferedReader inFromPi = new BufferedReader(new InputStreamReader(connected.getInputStream()));
while(true){
String fromclient = inFromPi.readLine();
if(fromclient.equalsIgnoreCase("Occupied")){
System.out.println("Client responded with "+fromclient + "\n");
}
else{
System.out.println("Client responded with "+fromclient + "\n");
connected.close();
}
}
}
}
catch(Exception e){
System.out.println(e);
}
}
}
The answer was exactly what #jtahlborn said. All I had to do was include a new line after each message was sent in the python code. I achieved this by doing something similar to client_socket.send(text+'\n')
I studied the Client-Server chapter of a Java book and I copied the code examples for a easy Client-Server interaction.
The server:
package knowledge;
import java.io.*;
import java.net.*;
public class DateTimeServer {
public static void main(String[] args) {
try {
int port = Integer.parseInt(args[0]);
ServerSocket server = new ServerSocket(port);
System.out.println("DateTimeServer laeuft");
Socket s = server.accept();
new DateTimeProtokoll(s).transact();
} catch (ArrayIndexOutOfBoundsException ae) {
System.out.println("Aufruf: java DateTimeServer <Port-Nr>");
} catch (IOException e) {
e.printStackTrace();
}
}
}
Protocol:
package knowledge;
import java.io.*;
import java.net.*;
import java.util.*;
import java.text.*;
public class DateTimeProtokoll {
static SimpleDateFormat time = new SimpleDateFormat(
"´Es ist gerade´H´.´mm´ Uhr.´");
static SimpleDateFormat date = new SimpleDateFormat(
"´Heute ist´EEEE´, der ´dd.MM.yy´");
Socket s;
BufferedReader vomClient;
PrintWriter zumClient;
public DateTimeProtokoll(Socket s) {
try {
this.s = s;
vomClient = new BufferedReader(new InputStreamReader(
s.getInputStream()));
zumClient = new PrintWriter(s.getOutputStream(), true);
} catch (IOException e) {
System.out.println("IO-Error");
e.printStackTrace();
}
}
public void transact() {
System.out.println("Protokoll gestartet");
try {
zumClient.println("Geben Sie DATE oder TIME ein");
String wunsch = vomClient.readLine();
Date jetzt = new Date();
if (wunsch.equalsIgnoreCase("date"))
zumClient.print(date.format(jetzt));
else if (wunsch.equalsIgnoreCase("time"))
zumClient.println(time.format(jetzt));
else
zumClient.println(wunsch + "ist als Kommando unzulaessig!");
s.close();
} catch (IOException e) {
System.out.println("IO-Error");
}
System.out.println("Protokoll beendet");
}
}
The Client:
package knowledge;
import java.net.*;
import java.io.*;
public class DateTimeClient {
public static void main(String[] args) {
String hostName="";
int port;
Socket c=null;
try{
hostName=args[0];
port= Integer.parseInt(args[1]);
c=new Socket(hostName,port);
BufferedReader vomServer=new BufferedReader(
new InputStreamReader(c.getInputStream()));
PrintWriter zumServer=new PrintWriter(c.getOutputStream(),true);
BufferedReader vonTastatur=new BufferedReader(
new InputStreamReader(System.in));
System.out.println("Server "+ hostName+":"+port+ "sagt:");
String text=vomServer.readLine();
System.out.println(text);
text=vonTastatur.readLine();
zumServer.println(text);
text=vomServer.readLine();
System.out.println(text);
c.close();
}
catch(ArrayIndexOutOfBoundsException ae){
System.out.println("Aufruf:");
System.out.println("java DateTimeClient <HostName><PortNr>");
}
catch(UnknownHostException ue){
System.out.println("Kein DNS-Eintrag fuer: "+hostName);
}
catch(IOException e){
System.out.println("IO-Error");
}
}
}
Here are some notes of my approach and my beliefs. Please disagree on wrong statements stated below:
1)I believe it is no problem to run Client as well as Server on the same (my) computer.
2)I use Eclipse, so I run Eclipse two times in two different workspaces.
3)My input for server program is (run configuration->arguments): 2222
4)My input for the client program is: 2223 my_ip
(my_ip is for example 127.0.0.1 I choosed to write my_ip instead because I am not sure if it is dangerous to reaveal my ip in public)
4b) also: "2223" "my_ip"
4c) and: {"2223","my_ip"}
5) also 2222 my_ip
(although the figure in my book suggests that the port numbers of client and server should be different, but you never know)
Also I get this very often this error message:
Address already in use sounds like client and server port numbers should be different. But I dont know and thats why I ask. Thank you for your help
(The page did not like my code so I took screenshots :/)
I replaced the images with code. Sorry for the inconvenience.
Restarting first the server with input 2222 and then the client with input 127.0.0.1 2222. After a while the client posts "IO-Error". Its the exception from the clien class (not from protocol class) right? Why is the exception triggered? Is the code working for someone? Thank you
1) Correct. Client and server can be on the same computer, no problem there.
2) Not required, but ok.
3) This will make the server listen on port 2222
4) 127.0.0.1 is just another way of saying "this computer". It is the same as "localhost". Your actual ip is irrelevant to the question anyway, 127.0.0.1 will suffice.
5) Your server is asking on which port to listen (the SOURCE port), your client is asking to which port to connect to (the TARGET port of the client). Of course that should be the SAME port, otherwise the client will try to send a message to port X while the server will listen on port Y.
Imagine the ip as a house address, for example "Mainstreet 12, MyCity". The port would be the appartment number then. Your server occupies appartment 2222, so of course the client needs to try to connect to appartment 2222, otherwise it will not reach any server.
The error is most likely just because you don't actually stop your old server program. Stop it (big red button in eclipse), otherwise it will "occupy" the given port (which will prevent any other program from listing at that port, thus you cannot have two servers running which are both listening on the same port). If we reuse my crude analogy: An appartment cannot contain two servers at the same time, so if one is already in appartment 2222, a second one trying to live there will fail.
I don't know exactly why, but usually server binds host as 127.0.0.1 or localhost or your IP like 192.168.1.100 but if one of that are not listed, than it might be failed to call. See more with netstat.exe on Windows.
The "Address already in use" exception is only because the last Java session still running, could not terminate for some reason, and if you use IDE like Eclipse, it will often happen. :)
Make sure that all java thread is terminated (with task manager in Windows). Note that Eclipse is a Java thread too! You would better run the server in console mode..
In real world, native sockets are rarely used, because there some higher level protocol and technology like HTTP, SOAP, WebService, microService, SOA etc. If native socket is not necessary, for example you communicate with microcontroller, you should use these technologies, because these are more robust and others can easily communicate with your interface.
I am building a client/server application, for some socket programming exercise.
Below is construction + run method of my server class. The server awaits a respond from the client, which in this case is just a string.
The problem is that it seems to make two connections when the client respond. From my print statements i can see that all the code in the run method is run twice, and then the first line once again.
Why would dateServer.accept(); accept a connection for only one client request?
public Server() throws Exception {
dateServer = new ServerSocket(3001);
System.out.println("Server lytter på port 3000.");
this.start();
}
public void run() {
while (true) {
try {
System.out.println("waiting for client to request");
Socket client = dateServer.accept();
System.out.println("connection established");
Connect c = new Connect(client);
clients.add(c);
this.sleep(5000);
} catch (Exception e) {
}
}
}
--EDIT--
Client code that talks to server (Message is a simple "wrapper" class"):
System.out.println("Write to server:");
String name = scanner.nextLine();
Message message = new Message(name, null);
oos.writeObject(message);
oos.flush();
If all the prints happen twice there must have been two connections. The first line prints again after that because you're in a loop.
NB:
Never ignore exceptions: especially IOExceptions.
The sleep is completely pointless. accept() will block while there are no incoming connections. You are literally wasting time here.
Server program :
import java.io.*;
import java.net.*;
public class server
{
public static void main(String args[])
{
try
{
ServerSocket ss=new ServerSocket(2000);
Socket s=ss.accept();
BufferedReader br=new BufferedReader(new InputStreamReader(s.getInputStream()));
String str;
while((str=br.readLine())!=null)
{
System.out.println(str);
}
}
catch(Exception e)
{
System.out.println(e);
}
}
}
Client program :
import java.net.*;
import java.io.*;
public class client
{
public static void main(String args[])
{
try
{
Socket s=new Socket("127.0.0.1",2000);
String str;
BufferedWriter br=new BufferedWriter(new OutputStreamWriter(s.getOutputStream()));
br.write("\nHello World\n");
}
catch(Exception e)
{
System.out.println(e);
}
}
}
The issues that I am facing are:
No output.
No Exception/Error is indicated.
Please explain me if am doing anything wrong. The problem might be the client has not written anything while the server is reading.
Close the stream after writing to stream in client program
br.close();
After Writing to stream it is compulsory to close the stream or flush the stream(br.flush()) because when stream is closed then only that stream can be read.
I/O operations can not be performed on same stream simultaneously.
Two sockets are connected by same stream so I/O operations can not be performed simultaneously on that stream.
Please add some debug statement to check
(1) is client able to make the connection with running server or not. so in server part add
Socket s=ss.accept();
System.out.println("one new connection");
(2) also in client program add flush() after the br.write line
br.write("\nHello World\n");
br.flush()
// use the below statement as well at last (if you no longer want to use the output stream)
br.close();
Please note you are just write one time here.... for continuous reading and writing you will have to run this in loop....
OR
to run multiple clients simultaneously ... you will have to execute each socket connection (after accepting it) into different thread at server end
I attempted to create a PHP script which determines if the server (the computer which hosts the java program listed below) is running or not, If it is, the php funciton should return true, if not it returns false.
Here is the server:
package darestium.minecraft.server;
import java.io.BufferedReader;
import java.net.*;
import java.io.*;
public class Server {
private static ServerSocket socket;
private static Socket connection;
private static String command = new String();
private static String responseStr = new String();;
private static int port = 4343;
public static void main(String args[]) {
System.out.println("Signal Server is running.");
try {
socket = new ServerSocket(port);
while (true) {
connection = socket.accept();
InputStreamReader inputStream = new InputStreamReader(connection.getInputStream());
DataOutputStream response = new DataOutputStream(connection.getOutputStream());
BufferedReader input = new BufferedReader(inputStream);
command = input.readLine();
response.writeBytes(responseStr);
response.flush();
//response.close();
System.out.println("Running");
}
} catch (IOException e) {
System.out.println("Fail!: " + e.toString());
}
System.out.println("Closing...");
}
}
And here is the client:
<?
function isRunning() {
$address = 'darestium.dyndns-free.com';
$port = 4343;
$socket = socket_create(AF_INET, SOCK_STREAM, getprotobyname('tcp'));
$message = 'loolololol';
try {
socket_connect($socket, $address, $port);
$status = socket_sendto($socket, $message, strlen($message), MSG_EOF, $address, $port);
if ($status != false) {
return true;
}
return false;
} catch (Exception $e) {
return false;
}
}
?>
The following are the error messages that show up on the php page that echos out the result of the function like so:
include('server.php');
echo isRunning();
Then the error messages:
Warning: socket_connect() [function.socket-connect]: unable to connect [0]: No connection could be made because the target machine actively refused it. in C:\Users\darestium\Documents\Portables\xampp\htdocs\darestium\minecraftserver.php on line 9
Notice: Use of undefined constant MSG_EOF - assumed 'MSG_EOF' in C:\Users\darestium\Documents\Portables\xampp\htdocs\darestium\minecraftserver.php on line 11
Warning: socket_sendto() expects parameter 4 to be long, string given in C:\Users\darestium\Documents\Portables\xampp\htdocs\darestium\minecraftserver.php on line 11
I was wondering how I could fix this issue. Also, I would like to be able to send messages to the server, any ideas how I could do this? I am basing this off Simple Java TCP Server and PHP Client Problems
Note: that I am very new to Sockets, and Server/Client communication.
Edit:
#VideanuAdrian OK, just port forwarded the port 4343 and it no longer shows up with the first error, but the function always seems to return false, and the last two errors still show.
You should not close the DataOutputStream object in your server.
Just comment the line response.close(); in your server and the program should work.
When running a Client/Server you need to know if the user that runs the app has access to the port. Ports to 1024 are reserved by the system know apps/services. That´s point 1.
Point 2: One of the best ways is to run the server inside a connection-thread approach. Running in this way, when a new client request arrives, the server can delegate the request handle to the connection thread.
Point 3: The message is related to the protocol. If you are using a built protocol like HTTP or FTP, you must use the protocol rules. If not, you could built your own rules for the message request/response.
I recomend you to read the Java Networking Tutorial before continue. Run all Java examples. Later, you could mix with PHP. The more information about sockets and protocols you have, the better your programm will be.
http://docs.oracle.com/javase/tutorial/networking/
Hope this can help you.