转自:http://developer.51cto.com/art/201202/317547.htm
前面几篇博文提到了Socket中一些常用的用法,但是对于一些有安全要求的应用就需要加密传输的数据,此时就需要用到SSLSocket了。
1 package com.googlecode.garbagecan.test.socket.ssl; 2 3 public class User implements java.io.Serializable { 4 private static final long serialVersionUID = 1L; 5 private String name; 6 private String password; 7 8 public User() { 9 10 } 11 12 public User(String name, String password) { 13 this.name = name; 14 this.password = password; 15 } 16 17 public String getName() { 18 return name; 19 } 20 21 public void setName(String name) { 22 this.name = name; 23 } 24 25 public String getPassword() { 26 return password; 27 } 28 29 public void setPassword(String password) { 30 this.password = password; 31 } 32 33 }
SSL Server类,这里需要用到ServerSocketFactory类来创建SSLServerSocket类实例,然后在通过SSLServerSocket来获取SSLSocket实例,这里考虑到面向对象中的面向接口编程的理念,所以代码中并没有出现SSLServerSocket和SSLSocket,而是用了他们的父类ServerSocket和Socket。在获取到ServerSocket和Socket实例以后,剩下的代码就和不使用加密方式一样了。
1 package com.googlecode.garbagecan.test.socket.ssl; 2 3 import java.io.BufferedInputStream; 4 import java.io.IOException; 5 import java.io.ObjectInputStream; 6 import java.io.ObjectOutputStream; 7 import java.net.ServerSocket; 8 import java.net.Socket; 9 import java.util.logging.Level; 10 import java.util.logging.Logger; 11 12 import javax.net.ServerSocketFactory; 13 import javax.net.ssl.SSLServerSocketFactory; 14 15 public class MyServer { 16 17 private final static Logger logger = Logger.getLogger(MyServer.class.getName()); 18 19 public static void main(String[] args) { 20 try { 21 ServerSocketFactory factory = SSLServerSocketFactory.getDefault(); 22 ServerSocket server = factory.createServerSocket(10000); 23 24 while (true) { 25 Socket socket = server.accept(); 26 invoke(socket); 27 } 28 } catch (Exception ex) { 29 ex.printStackTrace(); 30 } 31 } 32 33 private static void invoke(final Socket socket) throws IOException { 34 new Thread(new Runnable() { 35 public void run() { 36 ObjectInputStream is = null; 37 ObjectOutputStream os = null; 38 try { 39 is = new ObjectInputStream(new BufferedInputStream(socket.getInputStream())); 40 os = new ObjectOutputStream(socket.getOutputStream()); 41 42 Object obj = is.readObject(); 43 User user = (User)obj; 44 System.out.println("user: " + user.getName() + "/" + user.getPassword()); 45 46 user.setName(user.getName() + "_new"); 47 user.setPassword(user.getPassword() + "_new"); 48 49 os.writeObject(user); 50 os.flush(); 51 } catch (IOException ex) { 52 logger.log(Level.SEVERE, null, ex); 53 } catch(ClassNotFoundException ex) { 54 logger.log(Level.SEVERE, null, ex); 55 } finally { 56 try { 57 is.close(); 58 } catch(Exception ex) {} 59 try { 60 os.close(); 61 } catch(Exception ex) {} 62 try { 63 socket.close(); 64 } catch(Exception ex) {} 65 } 66 } 67 }).start(); 68 } 69 }
SSL Client类和SSL Server类类似,只是将其中获取Socket的方式有所变化,其余的代码也和不使用加密方式一样。
1 package com.googlecode.garbagecan.test.socket.ssl; 2 3 import java.io.BufferedInputStream; 4 import java.io.IOException; 5 import java.io.ObjectInputStream; 6 import java.io.ObjectOutputStream; 7 import java.net.Socket; 8 import java.util.logging.Level; 9 import java.util.logging.Logger; 10 11 import javax.net.SocketFactory; 12 import javax.net.ssl.SSLSocketFactory; 13 14 public class MyClient { 15 16 private final static Logger logger = Logger.getLogger(MyClient.class.getName()); 17 18 public static void main(String[] args) throws Exception { 19 for (int i = 0; i < 100; i++) { 20 Socket socket = null; 21 ObjectOutputStream os = null; 22 ObjectInputStream is = null; 23 24 try { 25 SocketFactory factory = SSLSocketFactory.getDefault(); 26 socket = factory.createSocket("localhost", 10000); 27 28 os = new ObjectOutputStream(socket.getOutputStream()); 29 User user = new User("user_" + i, "password_" + i); 30 os.writeObject(user); 31 os.flush(); 32 33 is = new ObjectInputStream(new BufferedInputStream(socket.getInputStream())); 34 Object obj = is.readObject(); 35 if (obj != null) { 36 user = (User)obj; 37 System.out.println("user: " + user.getName() + "/" + user.getPassword()); 38 } 39 } catch(IOException ex) { 40 logger.log(Level.SEVERE, null, ex); 41 } finally { 42 try { 43 is.close(); 44 } catch(Exception ex) {} 45 try { 46 os.close(); 47 } catch(Exception ex) {} 48 try { 49 socket.close(); 50 } catch(Exception ex) {} 51 } 52 } 53 } 54 }
代码写完了,下面就需要产生keystore文件了,运行下面的命令
- keytool -genkey -alias mysocket -keyalg RSA -keystore mysocket.jks
在提示输入项中,密码项自己给定,其它都不改直接回车,这里我使用的密码是“mysocket”。
运行Server
- java -Djavax.net.ssl.keyStore=mysocket.jks -Djavax.net.ssl.keyStorePassword=mysocket com.googlecode.garbagecan.test.socket.ssl.MyServer
运行Client
- java -Djavax.net.ssl.trustStore=mysocket.jks -Djavax.net.ssl.trustStorePassword=mysocket com.googlecode.garbagecan.test.socket.ssl.MyClient
前面几篇博文提到了Socket中一些常用的用法,但是对于一些有安全要求的应用就需要加密传输的数据,此时就需要用到SSLSocket了。