java项目使用ssl对socket通信加密

一 使用java生成相关证书文件

1. 进入java安装目录的bin文件夹中 cd /java/bin

2. 创建一个客户端keystore文件,秘钥: clientkeys

keytool -genkey -alias clientkeys -keystore clientkeys

3. 将客户端keystore文件导出成证书格式,秘钥: clientkeys

keytool -export -alias clientkeys -keystore clientkeys -file clientkeys.cer

4. 创建一个服务器端keystore文件,秘钥: serverkeys

keytool -genkey -alias serverkeys -keystore serverkeys

5. 将服务器端keystore文件导出成证书格式,秘钥: serverkeys

keytool -export -alias serverkeys -keystore serverkeys -file serverkeys.cer

6. 将客户端证书导入到服务器端受信任的keystore中,秘钥: servertrust

 keytool -import -alias clientkeys -keystore servertrust -file clientkeys.cer 

7. 将服务器端证书导入到客户端受信任的 keystore 中,秘钥: clienttrust

 keytool -import -alias serverkeys -keystore clienttrust -file serverkeys.cer 

二 将上述生成的文件导入项目的src目录下

三 实现ssl的方式

第一种:服务端代码如下:

package demo1;

import java.io.*; 
import javax.net.ssl.SSLServerSocket; 
import javax.net.ssl.SSLServerSocketFactory; 
import javax.net.ssl.SSLSocket; 

public class SSLServer { 

	private SSLServerSocket serverSocket = null; 

	public SSLServer() throws Exception { 
		System.setProperty("javax.net.ssl.keyStore","src/serverkeys" );
		System.setProperty("javax.net.ssl.keyStorePassword","serverkeys" );
		System.setProperty("javax.net.ssl.trustStore","src/servertrust");     
		System.setProperty("javax.net.ssl.trustStorePassword","servertrust"); 
		// 通过套接字工厂,获取一个服务器端套接字
		SSLServerSocketFactory socketFactory = (SSLServerSocketFactory)SSLServerSocketFactory.getDefault(); 
		serverSocket = (SSLServerSocket)socketFactory.createServerSocket(8080); 
	} 

	private void runServer() { 
		while (true) { 
			try { 
				System.out.println("服务端启动成功,等待连接。。。"); 
				// 服务器端套接字进入阻塞状态,等待来自客户端的连接请求
				SSLSocket socket = (SSLSocket) serverSocket.accept(); 

				// 获取服务器端套接字输入流
				BufferedReader input = new BufferedReader(new InputStreamReader(socket.getInputStream())); 
				// 从输入流中读取客户端用户名和密码
				String str = input.readLine(); 
				System.out.println("服务器接收到的信息:"+str);

				// 获取服务器端套接字输出流
				PrintWriter output = new PrintWriter(new OutputStreamWriter(socket.getOutputStream())); 

				// ssl连接成功
				output.println("ssl验证成功"); 
				
				// 关闭流资源和套接字资源
				output.close(); 
				input.close(); 
				socket.close(); 

			} catch (IOException ioException) { 
				ioException.printStackTrace(); 
			} 
		} 
	} 

	public static void main(String args[]) throws Exception { 
		SSLServer server = new SSLServer(); 
		server.runServer(); 
	} 
} 

客户端代码如下:

package demo1;

import java.io.*; 
import javax.net.ssl.SSLSocket; 
import javax.net.ssl.SSLSocketFactory; 

public class SSLClient { 

	private SSLSocket socket = null; 

	public SSLClient() throws IOException { 
		System.setProperty("javax.net.ssl.keyStore","src/clientkeys" );
		System.setProperty("javax.net.ssl.keyStorePassword","clientkeys" );
		System.setProperty("javax.net.ssl.trustStore","src/clienttrust");     
		System.setProperty("javax.net.ssl.trustStorePassword","clienttrust"); 

		// 通过套接字工厂,获取一个客户端套接字
		SSLSocketFactory socketFactory = (SSLSocketFactory)SSLSocketFactory.getDefault(); 
		socket = (SSLSocket) socketFactory.createSocket("localhost", 8080); 
	} 

	public void connect() { 
		try { 
			// 获取客户端套接字输出流
			PrintWriter output = new PrintWriter(new OutputStreamWriter(socket.getOutputStream())); 
			// 通过输出流发送到服务器端
			output.println("hello,server"); 
			output.flush(); 

			// 获取客户端套接字输入流
			BufferedReader input = new BufferedReader(new InputStreamReader(socket.getInputStream())); 
			// 从输入流中读取服务器端传送的数据内容,并打印出来
			String response = input.readLine(); 
			System.out.println(response); 

			// 关闭流资源和套接字资源
			output.close(); 
			input.close(); 
			socket.close(); 
		} catch (IOException ioException) { 
			ioException.printStackTrace(); 
		} finally { 
			System.exit(0); 
		} 
	} 

	public static void main(String args[]) throws IOException { 
		new SSLClient().connect(); 
	} 
}

第二种方式:服务端代码如下:

package demo2;

import java.io.BufferedInputStream;  
import java.io.BufferedOutputStream;  
import java.io.FileInputStream;  
import java.io.InputStream;  
import java.io.OutputStream;  
import java.net.Socket;  
import java.security.KeyStore;  

import javax.net.ssl.KeyManagerFactory;  
import javax.net.ssl.SSLContext;  
import javax.net.ssl.SSLServerSocket;  
import javax.net.ssl.TrustManagerFactory;  


public class SSLServer {  

	private SSLServerSocket serverSocket;  

	/** 
	 * 启动程序 
	 *  
	 * @param args 
	 */  
	public static void main(String[] args) {  
		SSLServer server = new SSLServer();  
		server.init();  
		server.start();  
	}  

	/** 
	 * SSL Server Socket 
	 */  
	public void start() {  
		if (serverSocket == null) {  
			System.out.println("socket初始化错误");  
			return;  
		}  
		System.out.println("服务端已启动");
		while (true) {  
			try {  
				Socket s = serverSocket.accept();  
				System.out.println("连接成功...");
				InputStream input = s.getInputStream();  
				OutputStream output = s.getOutputStream();  

				BufferedInputStream bis = new BufferedInputStream(input);  
				BufferedOutputStream bos = new BufferedOutputStream(output);  

				byte[] buffer = new byte[20];  
				bis.read(buffer);  
				System.out.println(new String(buffer));  

				bos.write("hello client".getBytes());  
				bos.flush();  

				s.close();  
			} catch (Exception e) {  
				System.out.println(e);  
			}  
		}  
	}  

	/** 
	 *  
	 * 初始化SSLServerSocket 
	 * 导入服务端私钥KeyStore,导入服务端受信任的KeyStore(客户端的证书)
	 *  
	 */  
	public void init() {  
		try {  
			SSLContext ctx = SSLContext.getInstance("SSL");  

			KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509");  
			TrustManagerFactory tmf = TrustManagerFactory.getInstance("SunX509");  

			KeyStore ks = KeyStore.getInstance("JKS");  
			ks.load(new FileInputStream("src/serverkeys"), "serverkeys".toCharArray());  

			KeyStore tks = KeyStore.getInstance("JKS");  
			tks.load(new FileInputStream("src/servertrust"), "servertrust".toCharArray());  

			kmf.init(ks, "serverkeys".toCharArray());  
			tmf.init(tks);  

			ctx.init(kmf.getKeyManagers(), tmf.getTrustManagers(), null);  

			serverSocket = (SSLServerSocket) ctx.getServerSocketFactory().createServerSocket(8888);  
			serverSocket.setNeedClientAuth(true);   
		} catch (Exception e) {  
			e.printStackTrace();  
		}  
	}  
}  

客户端如下:

package demo2;

import java.io.BufferedInputStream;  
import java.io.BufferedOutputStream;  
import java.io.FileInputStream;  
import java.io.IOException;  
import java.io.InputStream;  
import java.io.OutputStream;  
import java.security.KeyStore;  

import javax.net.ssl.KeyManagerFactory;  
import javax.net.ssl.SSLContext;  
import javax.net.ssl.SSLSocket;  
import javax.net.ssl.TrustManagerFactory;  

/** 
 * SSL Client 
 *  
 */  
public class SSLClient{  

	private SSLSocket           sslSocket;  

	/** 
	 * 启动客户端程序 
	 * @param args 
	 */  
	public static void main(String[] args) {  
		SSLClient client = new SSLClient();  
		client.init();  
		client.process();  
	}  

	/** 
	 * 通过ssl socket与服务端进行连接,并且发送一个消息 
	 */  
	public void process() {  
		if (sslSocket == null) {  
			System.out.println("socket初始化错误");  
			return;  
		}  
		try {  
			InputStream input = sslSocket.getInputStream();  
			OutputStream output = sslSocket.getOutputStream();  

			BufferedInputStream bis = new BufferedInputStream(input);  
			BufferedOutputStream bos = new BufferedOutputStream(output);  

			bos.write("hello server".getBytes());  
			bos.flush();  

			byte[] buffer = new byte[20];  
			bis.read(buffer);  
			System.out.println(new String(buffer));  

			sslSocket.close();  
		} catch (IOException e) {  
			System.out.println(e);  
		}  
	}  

	/** 
	 * 初始化SSLSocket
	 * 导入客户端私钥KeyStore,导入客户端受信任的KeyStore(服务端的证书)
	 */  
	public void init() {  
		try {  
			SSLContext ctx = SSLContext.getInstance("SSL");  

			KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509");  
			TrustManagerFactory tmf = TrustManagerFactory.getInstance("SunX509");  

			KeyStore ks = KeyStore.getInstance("JKS");  
			KeyStore tks = KeyStore.getInstance("JKS");  

			ks.load(new FileInputStream("src/clientkeys"), "clientkeys".toCharArray());  
			tks.load(new FileInputStream("src/clienttrust "), "clienttrust".toCharArray());  

			kmf.init(ks, "clientkeys".toCharArray());  
			tmf.init(tks);  

			ctx.init(kmf.getKeyManagers(), tmf.getTrustManagers(), null);  

			sslSocket = (SSLSocket) ctx.getSocketFactory().createSocket("127.0.0.1", 8888);  
		} catch (Exception e) {  
			System.out.println(e);  
		}  
	}  

}  

注:SSLContext.getInstance("SSL"),其中SSL为数据协议类型,也可以使用TLSv1(报错的话可能是版本太低,使用TLSv1.2试试)

 

  • 1
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值