以下是“TCP SERVER”代码,当任何客户端第一次连接代码运行得很好时,但是一旦客户端断开并再次连接TCP SERVER,客户端连接成功但无法发送数据。
如何检测客户端与服务器断开连接?
import android.content.Context;
import android.net.ConnectivityManager;
import android.net.NetworkInfo;
import android.net.wifi.WifiManager;
import android.os.AsyncTask;
import android.os.CountDownTimer;
import android.os.Handler;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.util.Log;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.Inet4Address;
import java.net.Inet6Address;
import java.net.InetAddress;
import java.net.NetworkInterface;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.Enumeration;
public class MainActivity extends AppCompatActivity {
TextView tvStatus;
EditText etPort, etMsg, etTransmit;
Button btnListen, btnServerSend;
Handler UIHandler;
private int SERVERPORT1;
private InetAddress addr;
private ServerSocket serverSocket;
private Socket clientSocket = null;
private BufferedReader in;
private PrintWriter out;
// public static final int SERVERPORT = 3000;
private WifiManager wifiManager = null;
private WifiManager.WifiLock lock = null;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
wifi();
UIHandler = new Handler();
tvStatus = (TextView) findViewById(R.id.tvStatus);
etMsg = (EditText) findViewById(R.id.etMsg);
etTransmit = (EditText) findViewById(R.id.etTransmit);
etPort = (EditText) findViewById(R.id.etPort);
btnListen = (Button) findViewById(R.id.btnListen);
btnServerSend = (Button) findViewById(R.id.btnServerSend);
// ******************* Register controls end ******************************
btnListen.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
new ServerClass().execute(etPort.getText().toString());
}
});
}
public String getLocalIpAddress() throws Exception {
String resultIpv6 = "";
String resultIpv4 = "";
for (Enumeration en = NetworkInterface.getNetworkInterfaces();
en.hasMoreElements(); ) {
NetworkInterface intf = (NetworkInterface) en.nextElement();
for (Enumeration enumIpAddr = intf.getInetAddresses();
enumIpAddr.hasMoreElements(); ) {
InetAddress inetAddress = (InetAddress) enumIpAddr.nextElement();
if (!inetAddress.isLoopbackAddress()) {
if (inetAddress instanceof Inet4Address) {
resultIpv4 = inetAddress.getHostAddress().toString();
} else if (inetAddress instanceof Inet6Address) {
resultIpv6 = inetAddress.getHostAddress().toString();
}
}
}
}
return ((resultIpv4.length() > 0) ? resultIpv4 : resultIpv6);
}
private class ServerClass extends AsyncTask<String, Object, String> {
private String input;
@Override
protected String doInBackground(String... params) {
try {
SERVERPORT1 = Integer.parseInt(params[0]);
addr = InetAddress.getByName(getLocalIpAddress());
serverSocket = new ServerSocket(SERVERPORT1, 0, addr);
while (true) {
clientSocket = serverSocket.accept();
clientSocket.setTcpNoDelay(true);
MainActivity.this.runOnUiThread(new Runnable() {
@Override
public void run() {
tvStatus.setText(clientSocket.getInetAddress().toString() + " Client connected");
Toast.makeText(MainActivity.this, "Server started...", Toast.LENGTH_SHORT).show();
}
});
in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));
out = new PrintWriter(clientSocket.getOutputStream(), true);
if (!Thread.currentThread().isInterrupted()) {
input = in.readLine();
if (input != null) {
UIHandler.post(new updateUIThread1(input.toString()));
out.println("Received from client: " + input);
} else {
MainActivity.this.runOnUiThread(new Runnable() {
@Override
public void run() {
new ServerClass().execute(etPort.getText().toString());
}
});
}
}
}
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
}
private class updateUIThread1 implements Runnable {
private String input = null;
public updateUIThread1(String input) {
this.input = input;
}
@Override
public void run() {
if (input.getBytes().length != 0) {
etMsg.append("\n" + input.toString());
Toast.makeText(MainActivity.this, "Answer: " + input, Toast.LENGTH_SHORT).show();
}else {
Toast.makeText(MainActivity.this, "Empty", Toast.LENGTH_SHORT).show();
}
}
}
}
日志显示如下:
04-22 12:57:05.799 10857-10931/com.chat.admin.clientserver I/System.out: [CDS]shutdownInput in read
04-22 12:57:05.799 10857-10931/com.chat.admin.clientserver I/System.out: [CDS]shutdownInput in read
04-22 12:57:05.799 10857-10931/com.chat.admin.clientserver I/System.out: [CDS]shutdownInput in read
04-22 12:57:05.799 10857-10931/com.chat.admin.clientserver I/System.out: [CDS]shutdownInput in read
04-22 12:57:05.799 10857-10931/com.chat.admin.clientserver I/System.out: [CDS]shutdownInput in read
read: unexpected EOF!
答案 0 :(得分:1)
如果客户端断开连接,请不要创建新服务器。
相反,你应该有一个循环,这样你就可以再次调用.accept()来等待新的客户端。