- 浏览: 44125 次
- 性别:
- 来自: 济南
文章分类
最新评论
JAVA 双向SSL,SOCKET客户端/服务端
实现技术:
JSSE(Java Security Socket Extension)
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:
Java代码
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:
Java代码
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,进行逻辑处理。
如果过程中,解密失败,那么证明消息来源错误。不进行逻辑处理。这样就完成了双向的身份认证。
实现技术:
JSSE(Java Security Socket Extension)
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:
Java代码
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:
Java代码
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,进行逻辑处理。
如果过程中,解密失败,那么证明消息来源错误。不进行逻辑处理。这样就完成了双向的身份认证。
发表评论
-
Android下屏保程序的开发
2014-01-09 17:08 0有时候,需要在程序中实现屏保相关的功能,如指定一段时间后,显示 ... -
Android command
2013-11-06 11:20 01. Android支持的linux command不多,在/ ... -
如何一个android工程作为另外一个android工程的lib
2013-10-19 17:01 0在实际使用中,我们可能会把一个android工程作为库,然后 ... -
Android属性(property)机制
2013-09-25 14:39 25091. 属性简介 Android里有很多属性(property ... -
Android编译系统
2013-09-23 19:07 370上次翻译了官方的Android编译系统手册(http://bl ... -
1.把我调试好的NFC上层代码加入GIT服务器代码中,并创建编译开关。
2013-08-21 09:33 0之前遇到的问题:向系统发送一个长按触摸事件,再发送其他触摸事件 ... -
2013-01-10 10:47 android多国语言使用
2013-08-12 20:57 750多国语言:在res目录下建立不同名称的values文件来调用不 ... -
android中dip px sp度量单位
2013-08-06 15:24 0目前android默认的low=120 ... -
minicom的配置
2013-07-08 09:58 5421、在使用minicom之前,首先要保证你对串口有读/写的权限 ... -
Android扩展一个硬件模块
2013-06-19 13:30 0为Android扩展一个硬件模块需要做两件事: 1、硬件和内 ... -
Android修改默认浏览器为其他浏览器
2013-06-15 10:09 1319public class MainActivity exten ... -
Android::开放root权限
2013-05-31 12:59 0开放系统root权限,即使任何用户都可以执行su程序,以使得临 ... -
android 开机logo,和开机动画
2013-05-11 23:17 0一.设置LINUX内核启动LOGO 1、让内核 ... -
android 4.0读写HID装置
2013-05-03 18:31 0求解:android 4.0读写HID设备 大家好,从3.1开 ... -
java 面向 Socket 操作,TCP 和 UDP 示例
2013-03-21 15:55 657TCP/IP 参考模型 应用层-->传输层--> ... -
Android系统Surface制的SurfaceFlinger服务的线程模型分析
2013-03-21 11:31 585在前面两篇文章中,我们分析了SurfaceFlinge ... -
C++ 代码创建虚拟机调用java方法
2013-03-21 11:28 846Java 和 C/C++代码的互相调用一般都是采用JNI的方法 ... -
android keycode 分发
2013-03-11 16:20 0******************************* ... -
android 获得当前活动的Acticity
2013-02-25 15:17 1567ActivityManager activityManager ... -
Android 4.0 截屏(Screenshot)代码流程小结
2013-02-25 13:55 0一、基本介绍 在Android 4. ...
相关推荐
- 配置SSLSocket:通过SSLContext的getSocketFactory()方法创建SSLSocket,连接到服务器。 4. **握手过程**: - 客户端初始化SSL连接,发送其证书和公钥给服务器。 - 服务器验证客户端的证书,如果接受,则发送...
本项目包括客户端和服务端两部分,确保了通信的双向性,实现了客户端发送请求和服务端响应的功能。 SGIP1.2接口是基于SGIP1.0的升级版本,主要优化了数据传输的效率和安全性,增加了更多的控制命令和功能,比如支持...
在Java编程中,Socket是网络通信的基础,常用于实现客户端(Client)与服务器端(Server)之间的双向通信。本项目“java-socket大文件上传-含客户端和服务端”旨在演示如何利用Java Socket API来实现大文件的上传...
在本项目中,我们探讨的是使用Java语言开发的QQ客户端和服务端。这是一份非常有价值的教育资源,适合于学习Java编程的学生以及对网络通信感兴趣的开发者。它涵盖了从基础的Socket编程到复杂的多线程处理,以及可能...
《Java 实时通信客户端与服务端详解》 在IT领域,网络通信是不可或缺的一部分,而Java作为一门跨平台、面向对象的语言,提供了丰富的API来实现客户端和服务端的通信。本篇将深入探讨“liaotian.rar”这个压缩包中...
在标题提到的"Java Web Project开发WebSocket服务端/客户端"项目中,开发者选择了Jetty作为服务器平台。Jetty 7.0版本的WebSocket API与后续版本(如9.0及以上)有较大差异。在Jetty 9.0之后,WebSocket API进行了...
在Android客户端中,我们通常使用`java.net.Socket`类来创建Socket实例,以连接到服务端。首先,我们需要指定服务器的IP地址和端口号,然后调用`connect()`方法建立连接。以下是一个简单的示例: ```java Socket ...
在本文中,我们将深入探讨Socket客户端的工作原理、如何向服务端发送数据以及接收服务端响应消息的过程。 首先,Socket是一种网络通信协议,它允许两个应用程序通过网络进行双向通信。在TCP/IP模型中,Socket位于...
本案例将深入探讨如何使用Mina作为服务端,结合Socket客户端实现文件的传输。 一、Apache Mina框架介绍 Apache Mina,全称为“Minimalist Application Networking Abstraction”,是一个提供了统一的API来处理多种...
- Android中的Socket编程涉及ServerSocket和Socket类,通过它们可以建立TCP连接,进行双向数据传输。 5. **Android权限管理**: - 进行网络操作时,Android应用需要在Manifest.xml中声明INTERNET权限:...
1. 服务器架构:仿QQ服务端可能采用了基于Socket编程的TCP/IP通信协议,用于处理客户端的连接请求和数据传输。此外,服务端可能还集成了消息中间件,如RabbitMQ或Kafka,以实现高效的消息队列管理。 2. RESTful API...
### Java Socket 服务端与客户端编程详解 #### 一、网络编程中的主要问题及解决方案 在进行网络编程时,我们面临着两大核心问题:如何精确地定位网络中的主机以及如何高效可靠地进行数据传输。 1. **主机定位**:...
生成 SSLServerSocket 和 SSLSocket 需要使用 SSLContext、KeyManagerFactory 和 TrustManagerFactory。代码示例如下: SSLContext ctx = SSLContext.getInstance("SSL"); KeyManagerFactory kmf = ...
SSL Socket 双向认证实现技术:JSSE(Java Security Socket Extension),它实现了 SSL 和 TSL(传输层安全)协议。在 JSSE 中包含了数据加密,服务器验证,消息完整性和客户端验证等技术。通过使用 JSSE,可以在...
1. **Socket类**:Java中的`java.net.Socket`类代表网络上的套接字,它是连接的两端,提供了双向的通信通道。服务端使用`ServerSocket`类监听指定端口,接受客户端的连接请求。 2. **IO流**:在文件传输过程中,...
希望对大家有所帮助",这暗示了压缩包内的SSLServer.java和SSLClient.java是两个关键文件,分别代表了SSL服务端和客户端的程序示例,用于展示如何在Java中配置和使用SSL连接。 SSLServer.java文件很可能是实现一个...
- **Socket编程**:Java的Socket类用于建立客户端和服务端的连接,实现数据的双向传输,这是QQ通信的基础。 - **多线程**:QQ客户端需要处理多个并发连接,多线程技术是必不可少的,如Thread和Runnable接口。 - *...
Socket通讯是计算机网络编程中的重要概念,主要用于在两台设备之间建立双向通信链路,使得数据能在客户端和服务器之间高效传输。本项目提供了一款服务端软件的源码,名为"MySocketServerDemo",用于实现Socket通信,...
在Java中,`java.net.Socket` 和 `java.net.ServerSocket` 分别代表客户端和服务端的Socket。 1. **服务器端实现**: - 创建ServerSocket:通过`new ServerSocket(port)`来监听指定的端口。 - 接受连接:调用`...
Java中的Socket类和ServerSocket类分别代表客户端和服务端的通信端点。通过建立Socket连接,双方可以进行双向数据交换。 2. **界面设计**: 项目的界面风格进行了全面更新,这通常意味着使用了Java Swing或JavaFX...