java socket demo

来源:互联网 发布:linux系统调用过程 编辑:程序博客网 时间:2024/06/06 09:23

项目要做一个adb工厂测试的方法,需要用adb命令行发命令给apk,apk接收命令并执行相应的方法返回结果。此时apk相当于一个server,adb端相当于client。
在apk上建立一个server监听端口,当有消息到达时,启动新的线程处理socket:

//开启线程监听端口try {    serverSocket = new ServerSocket(10086);} catch (SocketException se) {    LogUtils.e(TAG, "SocketException: " + se.getMessage());} catch (IOException e) {    LogUtils.e(TAG, "Exception: ftpsocket " + e.getMessage());}if (serverSocket != null) {    while (true) {        Socket sock = null;        try {            LogUtils.d(TAG, "Waiting for connection...");            //接收命令            sock = serverSocket.accept();            LogUtils.d(TAG, "Got socket:" + sock);            if (sock != null) {                //开启新的线程处理命令                startDealSocket(sock);            } else {                return;  // socket shutdown?            }        } catch (IOException e) {            LogUtils.e(TAG, "Exception: ftpsocket " + e.getMessage());            break;        }    }}//每当有一个新的命令通过socket传递过来时,开启新的线程处理该socketprivate void startDealSocket(final Socket socket) {    new Thread(new Runnable() {        @Override        public void run() {            PrintWriter printWriter = null;            BufferedReader reader = null;            try {                reader = new BufferedReader(new InputStreamReader(socket.getInputStream()));                printWriter = new PrintWriter(socket.getOutputStream());                String readLine = reader.readLine();                while(readLine != null){                    LogUtils.d("landon","服务器接收到来自客户端的信息:" + readLine);                    readLine = reader.readLine();                }                String response = "服务器返回的信息";                printWriter.write(response + "\n");                printWriter.flush();            } catch (IOException ex) {                ex.printStackTrace();            }            finally {                if(printWriter != null)                    printWriter.close();                try {                    if(reader != null)                        reader.close();                    if(socket != null)                        socket.close();                }catch (IOException ex){                    ex.printStackTrace();                }            }        }    }).start();}

为了测试服务端,简单编写了client端的测试代码:

/** * 发送命令给服务端 * @param cmd 要发送的命令 * @param handler 通知返回handler */public void sendCMD(final String cmd, final Handler handler){    new Thread(new Runnable() {        @Override        public void run() {            Socket socket = connect();            Writer writer = null ;            BufferedReader reader = null;            if(socket != null){                try {                    writer = new OutputStreamWriter(socket.getOutputStream());                    reader = new BufferedReader(new InputStreamReader(socket.getInputStream()));                    writer.write(cmd + "\n");                    writer.flush();                    socket.shutdownOutput();                    String readLine = reader.readLine();                    while(readLine != null){                        LogUtils.d("landon","收到服务器返回:" + readLine);                        Message msg = handler.obtainMessage();                        msg.obj = readLine;                        msg.sendToTarget();                        readLine = reader.readLine();                    }                } catch (IOException e) {                    e.printStackTrace();                }finally {                    try {                        if(writer != null){                            writer.close();                        }                        if(reader != null){                            reader.close();                        }                        socket.close();                    } catch (IOException e) {                        e.printStackTrace();                    }                }            }        }    }).start();}/** - 获取socket连接 - @return socket */private Socket connect(){    Socket socket = null;    try {        socket = new Socket("127.0.0.1",10086);    } catch (IOException e) {        e.printStackTrace();    }    if(socket != null)        return socket;    return null;}
  • 如果用的是BufferedReader,那么需要注意发送的消息每一条都必须跟上“\n”,否则BufferedReader还认为没有读完一行,就一直阻塞执行reader.readLine()这句;
  • 服务端默认一直读取知道结束,那么如果客户端发送完消息后不进行close或者shutdownOutput操作的话,服务端会一直在while中阻塞执行reader.readLine(),而客户端此时也在等待服务端的回应,就进入了死循环。当close或者shutdownOutput后,reader.readLine这句会返回null,就可以跳出while循环。
0 0
原创粉丝点击