实现技术:

JSSE(Java Security Socket Extension)

是Sun为了解决在Internet上的实现安全信息传输的解决方案。它实现了SSL和TSL(传输层安全)协议。在JSSE中包含了数据加密,服务器验证,消息完整性和客户端验证等技术。通过使用JSSE,可以在Client和Server之间通过TCP/IP协议安全地传输数据。

为了实现消息认证。

Server需要:

1)KeyStore: 其中保存服务端的私钥

2)Trust KeyStore:其中保存客户端的授权证书

Client需要:

1)KeyStore:其中保存客户端的私钥

2)Trust KeyStore:其中保存服务端的授权证书

使用Java自带的keytool命令,去生成这样信息文件:

1)生成服务端私钥,并且导入到服务端KeyStore文件中

2)根据私钥,导出服务端证书

3)将服务端证书,导入到客户端的Trust KeyStore中

采用同样的方法,生成客户端的私钥,客户端的证书,并且导入到服务端的Trust KeyStore中

1)keytool -genkey -alias clientkey -keystore kclient.keystore

2)keytool -export -alias clientkey -keystore kclient.keystore -file client.crt

3)keytool -import -alias clientkey -file client.crt -keystore tserver.keystore

Server:

package ssl;

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;

/**

*

* @author Leo

*/

public class Server implements Runnable{

private static final int DEFAULT_PORT = 7777;

private static final String SERVER_KEY_STORE_PASSWORD = "123456";

private static final String SERVER_TRUST_KEY_STORE_PASSWORD = "123456";

private SSLServerSocket serverSocket;

/**

* 启动程序

*

* @param args

*/

public static void main(String[] args) {

Server server = new Server();

server.init();

Thread thread = new Thread(server);

thread.start();

}

public synchronized void start() {

if (serverSocket == null) {

System.out.println("ERROR");

return;

}

while (true) {

try {

Socket s = serverSocket.accept();

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("------receive:--------"+new String(buffer).toString());

bos.write("yes".getBytes());

bos.flush();

s.close();

} catch (Exception e) {

System.out.println(e);

}

}

}

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/ssl/kserver.keystore"), SERVER_KEY_STORE_PASSWORD.toCharArray());

tks.load(new FileInputStream("src/ssl/tserver.keystore"), SERVER_TRUST_KEY_STORE_PASSWORD.toCharArray());

kmf.init(ks, SERVER_KEY_STORE_PASSWORD.toCharArray());

tmf.init(tks);

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

serverSocket = (SSLServerSocket) ctx.getServerSocketFactory().createServerSocket(DEFAULT_PORT);

serverSocket.setNeedClientAuth(true);

} catch (Exception e) {

System.out.println(e);

}

}

public void run() {

// TODO Auto-generated method stub

start();

}

}

Client:

package ssl;

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

*

* @author Leo

*/

public class Client {

private static final String DEFAULT_HOST = "127.0.0.1";

private static final int DEFAULT_PORT = 7777;

private static final String CLIENT_KEY_STORE_PASSWORD = "123456";

private static final String CLIENT_TRUST_KEY_STORE_PASSWORD = "123456";

private SSLSocket sslSocket;

/**

* 启动客户端程序

*

* @param args

*/

public static void main(String[] args) {

Client client = new Client();

client.init();

client.process();

}

public void process() {

if (sslSocket == null) {

System.out.println("ERROR");

return;

}

try {

InputStream input = sslSocket.getInputStream();

OutputStream output = sslSocket.getOutputStream();

BufferedInputStream bis = new BufferedInputStream(input);

BufferedOutputStream bos = new BufferedOutputStream(output);

bos.write("1234567890".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);

}

}

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/ssl/kclient.keystore"), CLIENT_KEY_STORE_PASSWORD.toCharArray());

tks.load(new FileInputStream("src/ssl/tclient.keystore"), CLIENT_TRUST_KEY_STORE_PASSWORD.toCharArray());

kmf.init(ks, CLIENT_KEY_STORE_PASSWORD.toCharArray());

tmf.init(tks);

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

sslSocket = (SSLSocket) ctx.getSocketFactory().createSocket(DEFAULT_HOST, DEFAULT_PORT);

} catch (Exception e) {

System.out.println(e);

}

}

}

启动Server

启动Client,发送信息。

Server接收如下:正确解密

返回Client信息,如下:

如此,就完成了服务端和客户端之间的基于身份认证的交互。

client采用kclient.keystore中的clientkey私钥进行数据加密,发送给server。

server采用tserver.keystore中的client.crt证书(包含了clientkey的公钥)对数据解密,如果解密成功,证明消息来自client,进行逻辑处理。

server采用kserver.keystore中的serverkey私钥进行数据加密,发送给client。

client采用tclient.keystore中的server.crt证书(包含了serverkey的公钥)对数据解密,如果解密成功,证明消息来自server,进行逻辑处理。

如果过程中,解密失败,那么证明消息来源错误。不进行逻辑处理。这样就完成了双向的身份认证。

分享到:

2008-11-24 16:36

浏览 30693

评论

5 楼

ahong520

2013-03-07

我在Keystore.getInstance("JKS") 报错:

java.security.KeyStoreException: java.security.NoSuchAlgorithmException: KeyStore jks implementation not found

楼主 你的jdk是什么版本阿。需要做其他设置吗?

4 楼

sjp524617477

2012-05-22

mark

3 楼

rmn190

2011-11-29

能不能解释下, 一般浏览器中的证书起什么用?浏览器中的证书是怎么回事?它的构成是怎样的?

2 楼

雨过天晴0521

2011-08-03

cnlf 写道

我修改了Server端的信任证书库src/ssl/tserver.keystore为无效的证书库,比如src/ssl/kserver.keystore,根据SSl双向认证原理,client端连接server端应该失败,可是程序执行的结果恰恰相反,不知何故,请指点。

这个其实是单向的.

1 楼

cnlf

2008-12-19

我修改了Server端的信任证书库src/ssl/tserver.keystore为无效的证书库,比如src/ssl/kserver.keystore,根据SSl双向认证原理,client端连接server端应该失败,可是程序执行的结果恰恰相反,不知何故,请指点。

java ssl 双向认证_java实现 SSL双向认证相关推荐

  1. Java笔记-基于Spring Boot的SOAP双向SSL认证及WS-Security

    这里服务端开放了简单的SOAP的API,但是想获取数据时需要双向SSL以及WS-Security签名. 其中对应的xsd文件如下: <xs:schema xmlns:xs="http: ...

  2. java使用bks双向认证_android客户端SSL单向双向认证

    最近一直在做SSL的研究,前几天写了一篇SSL握手过程的文章,今天写下android客户端SSL单双向认证的示例 操作系统是win7,服务器用的tomcat6,客户端跑在1.6的模拟器上,证书都是自签 ...

  3. SSL证书配置(https访问接口, 单向认证和双向认证)

    拿到SSL证书后, 如何才能解锁更多玩法? 一. SpringBoots项目配置https访问接口(直接配置) SSL协议 配置步骤 1. 获取证书/ 生成证书 2. 放置证书 3. 配置项目 pro ...

  4. Java nginx 双向ssl_nginx配置ssl双向验证 nginx https ssl证书配置

    参考<nginx安装>:http://www.ttlsa.com/nginx/nginx-install-on-linux/ 如果你想在单IP/服务器上配置多个https,请看<ng ...

  5. java ssl 加密传输_java线程之四 SSL加密传输

    网络传输是存在风险的,因此对服服务端和客户端进行安全校验和传输信息的加密就显得非常的重要. 上面一句有点拗口,简单解释如下文: 当客户使用SSL向站点服务器发送请求时,服务器向客户端发送一个证书,客户 ...

  6. java ssl证书生成_java – 使用jdk中提供的keytool生成SSL证书

    我在Web应用程序中使用的密钥库文件已于上周过期.我很久以前就生成了它.所以我开始使用keytool生成新证书.我使用此证书连接事务服务器和Web服务器.我想为此应用程序使用自签名证书.我使用以下命令 ...

  7. java ssl证书连接_JAVA连接HTTPS - HTTPS SSL 教程 - 数安时代(GDCA)SSL证书官网

    使用Apache的HttpClient 和 HttpCore https://hc.apache.org package cn.getssl.https; import java.io.Buffere ...

  8. java ssl 无证书_java – 如何修复SSL – 没有可用的证书

    我想使用以下代码建立服务器SSL套接字连接: int port = 12000; ServerSocketFactory ssocketFactory = SSLServerSocketFactory ...

  9. httos双向认证配置_APP爬虫双向认证抓包的两种方法

    APP抓包相对繁琐,越来越多的 APP 在 https 请求和响应时,为了防止中间人攻击(或中间人抓包),会做证书认证,让抓包工具抓不到请求.证书认证分单向认证和双向认证,双向认证是相较于单向认证而言 ...

  10. 服务器双向认证 原理,https认证方式以及HTTPS双向认证过程

    https认证方式以及HTTPS双向认证过程 分类:建站推广 编辑: 浏览量:100 2021-07-15 14:29:14 很多网站都配置了HTTPS而不是HTTP,因为安全性得到了极大的提高,如果 ...

最新文章

  1. 基于linux的ARM设备升级,烧写Nand flash总结
  2. hiho一下 第五周 Hihocoder #1037 : 数字三角形
  3. java并发排序_Java并发(三):重排序
  4. NOI2012 Day2
  5. JUC阻塞队列BlockingQueue讲解
  6. Java Timetask 无缘无故停止
  7. jQuery控制checkbox选中状态但是不显示选中
  8. 怎样取消隐式推送_九推,怎样寻找捡漏的机会?
  9. 吉林大学超星学习通06 07 08
  10. KL散度、JS散度 的理解以及一些问题
  11. linux返回上级目录
  12. Ferry工单管理系统安装部署
  13. C语言实现乘方运算---m的n次方(附完整源码)
  14. 杰理之MIC 省电 容方案 微信语音 或通话 时前面 几秒钟有 哒哒声【篇】
  15. python神经网络预测股票_用神经网络预测股票市场
  16. Sqlmap 渗透注入总是显示无法连接目标网络问题分析与解决
  17. 设计用于汽车和车身SPC58NH92C3RMI0X\SPC560B50L1B4E0X微控制器
  18. 申请单---申请人--审批人不同的入口
  19. 虎牙斗鱼“同病相怜”
  20. 过劳死 梦魇笼罩下的IT精英

热门文章

  1. Ubuntu上开发python的十大IDE
  2. 尘梦留痕:苏东坡的诗词里,藏着六种人生智慧
  3. YARN : FairScheduler深入解析(队列维护,demand、fair share计算)
  4. 毕业论文怎么降重?有什么技巧么?
  5. 学校计算机硬件管理制度,学校规章制度之计算机硬件管理制度.doc
  6. 2021-09-27 win10 IPV6连接:无网络访问权限 怎么解决
  7. 卖肉了也没火的十大悲催女星
  8. android 指纹存储密码,安卓指纹认证(Android Fingerprint Auth)
  9. win10系统登录服务器密码存储位置,win10远程服务器登录密码
  10. vim实用技巧总结 [Linux]