Java Socket入门实例
基于测试驱动的Socket入门实例(代码的具体功能可以看我的程序中的注释,不理解的可以短信我)
先看Server的代码:
package socketStudy;
import java.io.BufferedReader; import java.io.IOException; import java.io.InputStreamReader; import java.net.ServerSocket; import java.net.Socket; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.util.List; import org.apache.log4j.Logger; /** * 类ServerSocket.java的实现描述: */ public class Server { private static final Logger log = Logger.getLogger("actionLog"); private ServerSocket server; private List<String> list = new ArrayList<String>(); public Server(int port) throws IOException{ server = new ServerSocket(port); } /** * 启动server的监听程序,当server关闭的时候停止监听 * * @throws IOException */ public void listen() throws IOException { Socket client; String temp; BufferedReader br = null; //如果当前server已经手动关闭,则终止监听 while (!server.isClosed()) { // 每当检测到套接字,就获得一个socket链接 // 这个方法在连接传入之前,一直阻塞 client = server.accept(); //注意这里只需要获取一次client的输入流即可 br = new BufferedReader(new InputStreamReader(client.getInputStream())); temp = br.readLine(); while (temp != null) { list.add(temp); temp = br.readLine(); } //这里立即关闭了client,事实上可以建立个timeOut时间 if(client.isClosed()){ client.close(); } br.close(); } } /** * 每次都返回当前的套接字的传入内容<br/> * 在返回后清空当前的list * * @return List<String> */ public synchronized List<String> getList() { List<String> newArrayList=new ArrayList<String>(Arrays.asList(new String[list.size()])); Collections.copy(newArrayList, list); list.clear(); return newArrayList; } /** * 返回当前server是否成功绑定上指定接口<br/> * true表示成功绑定,false则表示没有绑定 * * @return boolean */ public boolean isBound() { return server.isBound(); } /** * 关闭当前server */ public void close() { if (server != null) { try { server.close(); } catch (IOException e) { log.error(e.getMessage(), e); } } } @Override public String toString() { return this.server.toString(); } }
再看client的程序示例;
package socketStudy;
import java.io.IOException; import java.io.PrintWriter; import java.net.Socket; import java.net.UnknownHostException; import org.apache.log4j.Logger; /** * 类Client.java的实现描述: */ public class Client { private static final Logger log = Logger.getLogger("actionLog"); private Socket client; private PrintWriter out; public Client(String serverIp, int port) throws UnknownHostException, IOException{ client = new Socket(serverIp, port); out = new PrintWriter(client.getOutputStream(), true); } /** * 向server发送消息 * * @param message */ public void send(String message) { out.println(message); } /** * 关闭当前client */ public void close() { if (client != null) { try { client.close(); } catch (IOException e) { log.error(e.getMessage(), e); } } if (out != null) { out.close(); } } }
最后看我们的测试代码(基于testng)
package test;
import java.io.IOException; import java.util.Arrays; import java.util.List; import org.testng.Assert; import org.testng.annotations.Test; import socketStudy.Client; import socketStudy.Server; /** * 类TestSocket.java的实现描述: */ public class TestSocket { private Server server; private static final int port=8733; @SuppressWarnings("static-access") @Test public void testSocket() throws IOException,InterruptedException{ //这里需要单独起个线程来在client发送消息前启动server的监听程序 Thread serverThread=new Thread() { @Override public void run() { try{ server = new Server(port); server.listen(); }catch(IOException e){ throw new RuntimeException(e); } } }; serverThread.start(); //这里通过线程不断的睡眠来等待server的监听程序启动成功 while(true){ if(server==null||!server.isBound()){ Thread.currentThread().sleep(1000); }else{ break; } } Client client = new Client("127.0.0.1", port); client.send("test"); client.send("joking"); client.close(); server.close(); //获取当前client发送的消息 List<String> actualList = server.getList(); List<String> expectedList = Arrays.asList("test", "joking"); Assert.assertEquals(actualList, expectedList); } }