Java Socket 发送数据给ServerSocket失败
需求
通过 adb forward tcp:localport tcp:remoteport
进行端口转发,实现 PC(客户端)
与 Android(服务端)
进行 Socket
通信
PC端PC端
使用的是JavaFX
编写的界面,在其Controller
中的代码是:
public class ImageController {
public void onButtonClicked(ActionEvent event) {
try {
Runtime.getRuntime().exec("adb forward tcp:10000 tcp:20000");
Socket client = new Socket(InetAddress.getByName("127.0.0.1"), 10000);
// 向服务端发送消息: hello
OutputStream out = client.getOutputStream();
out.write("hello".getBytes());
out.flush();
} catch (IOException e) {
e.printStackTrace();
}
}
}
Android服务端
/**
接收客户端
*/
public class PCService extends Service {
private static final int SERVER_PORT = 20000;
@Override
public void onCreate() {
super.onCreate();
new Thread(() -> doListening()).start();
}
private void doListening() {
try {
ServerSocket server = new ServerSocket(SERVER_PORT);
Log.i(TAG, "服务器监听中....");
Socket client = server.accept();
new Thread(new SocketIO(client)).start();
} catch (IOException e) {
e.printStackTrace();
}
}
}
SocketIO 客户端连接成功后,进行处理的类,继承Runnable
class SocketIO implements Runnable {
private Socket mClient;
public SocketIO(Socket client) {
mClient = client;
}
@Override
public void run() {
if (mClient.isConnected()) {
try {
// 接收客户端发来的消息
InputStream in = mClient.getInputStream();
Scanner scan = new Scanner(in);
scan.useDelimiter("\\A");
String msg = scan.hasNext() ? scan.next() : "暂无";
System.out.println("接收到的数据: " + msg);
switch (msg) {
case "hello":
// TODO: doSomething();
break;
}
} catch (IOException e) {
e.printStackTrace();
}
} else {
Log.i(TAG, "客户端未连接");
}
}
}
问题
- PC端,
out.flush()
之后不写任何东西是,点击按钮,Android服务端没有任何显示,当关闭PC端应用程序时, Android服务端显示 -> 接收到数据: hello - 当
out.flush()
之后添加client.shutdownOutputStream()
后, Android服务端显示 -> 接收到数据: 暂无 (意思就是没有收到PC端发来的消息)
想要得到的帮助
- 如何解决上面的通信问题? PC端发送一条消息给Android端, Android根据消息内容作出响应返回给PC端?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
你想写一个通讯程序,可以先试在在普通java工程中写好,再移植到android工程上。
这是官方指导文档
https://docs.oracle.com/javas...
也可以看看别的代码参考下。如http://cs.lmu.edu/~ray/notes/...
你这段代码的主要问题在你使用的
Scanner
,Sacnner在读取流的时候不会主动刷新。客户端发过来的数据,始终在缓冲区中,当tcp链接异常关闭时才会被刷新。
如果服务段相关读取数据替换成下面这样,可以正常显示客户端发过来的数据。
问题1与问题2,因为调用
client.shutdownOutputStream()
后,tcp会出送rst包。收到rst包的服务器端,会丢弃缓冲区的数据。如果不调用,tcp会发送fin包,服务器收到fin包,知道要结束了,于是主动刷新Scanner,准备退出。