我正在尝试创建一个服务器 - 客户端捆绑包,它允许我发送带有ssl支持的简单消息。我是java的新手,我无法弄清楚我的问题是什么。我在同一网络的2台计算机上运行服务器和客户端程序,我可以发送消息。我的问题是,当我用wireshark捕获消息时,协议是TCP,我可以读取消息 关于证书,我已经用openssl创建了所有证书,并且我已经使用keytool将它们转换为.jks。 Myca.jks是自签名ca的证书,我已使用此证书对服务器和客户端进行了签名。 谢谢你的任何提示!
import java.io.*; import java.net.*; import java.security.*; import java.util.*; import javax.net.ssl.*; public class sslserver { ObjectOutputStream out; ObjectInputStream in; String message; sslserver(){} void run() throws Exception { char[] passphrase = "123456".toCharArray(); KeyStore keystore = KeyStore.getInstance("JKS"); keystore.load(new FileInputStream("/home/jimmysnn/JavaApplication4/src/keystore.jks"), passphrase); KeyStore serverkeystore = KeyStore.getInstance("JKS"); serverkeystore.load(new FileInputStream("/home/jimmysnn/JavaApplication4/src/server.jks"), passphrase); KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509"); kmf.init(keystore, passphrase); TrustManagerFactory tmf = TrustManagerFactory.getInstance("SunX509"); tmf.init(serverkeystore); SSLContext context = SSLContext.getInstance("TLS"); TrustManager[] trustManagers = tmf.getTrustManagers(); KeyManager[] keyManagers = kmf.getKeyManagers(); context.init(keyManagers, trustManagers, null); //1. creating a server socket SSLServerSocketFactory ssf = context.getServerSocketFactory(); ServerSocket ss = ssf.createServerSocket(2004); //2. Wait for connection System.out.println("Waiting for connection"); Socket s = ss.accept(); System.out.println("Connection received from " + s.getInetAddress().getHostName()); //3. get Input and Output streams out = new ObjectOutputStream(s.getOutputStream()); out.flush(); in = new ObjectInputStream(s.getInputStream()); sendMessage("Connection successful"); //4. The two parts communicate via the input and output streams Scanner input = new Scanner( System.in ); do{ message = (String)in.readObject(); System.out.println("client>" + message); if (message.equals("bye")) sendMessage("bye"); }while(!message.equals("bye")); //4: Closing connection in.close(); out.close(); ss.close(); } void sendMessage(String msg) throws Exception { out.writeObject(msg); out.flush(); System.out.println("server>" + msg); } public static void main(String args[]) throws Exception { Server server = new Server(); while(true){ server.run(); } } }
import java.io.*; import java.net.*; import java.util.*; import java.security.*; import javax.net.ssl.*; public class sslclient { ObjectOutputStream out; ObjectInputStream in; String message; sslclient(){} void run() throws Exception { char[] passphrase = "123456".toCharArray(); KeyStore keystore = KeyStore.getInstance("JKS"); keystore.load(new FileInputStream("/home/ge0rge/Javaaskhsh4/src/myca.jks"), passphrase); KeyStore keystoreclient = KeyStore.getInstance("JKS"); keystoreclient.load(new FileInputStream("/home/ge0rge/Javaaskhsh4/src/client.jks"), passphrase); TrustManagerFactory tmf = TrustManagerFactory.getInstance("SunX509"); tmf.init(keystore); KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509"); kmf.init(keystoreclient, passphrase); SSLContext context = SSLContext.getInstance("TLS"); TrustManager[] trustManagers = tmf.getTrustManagers(); KeyManager[] keyManagers = kmf.getKeyManagers(); context.init( keyManagers, trustManagers, null); SSLSocketFactory sf = context.getSocketFactory(); Socket s = sf.createSocket("192.168.1.5", 443); System.out.println("Connected to localhost in port 2004"); //2. get Input and Output streams out = new ObjectOutputStream(s.getOutputStream()); out.flush(); in = new ObjectInputStream(s.getInputStream()); //3: Communicating with the server Scanner input = new Scanner( System.in ); message = (String)in.readObject(); System.out.println("server>" + message); //message = input.nextLine(); sendMessage("Hi my server"); do{ message = input.nextLine(); sendMessage(message); if(message.equals("bye")){ message = (String)in.readObject(); System.out.println("server>" + message); } }while(!message.equals("bye")); in.close(); out.close(); s.close(); } void sendMessage(String msg) throws Exception { out.writeObject(msg); out.flush(); System.out.println("client>" + msg); } public static void main(String args[]) throws Exception { Client client = new Client(); client.run(); } }
答案 0 :(得分:3)
您在代码中使用了一些非标准术语,这可能反映了您的实现中的一些混淆或者确实存在一些错误。
服务器需要一个密钥库,其中包含他的私钥。
客户有一个信任,其中包含他准备信任其他人(即服务器)的证书。
服务器的证书需要从服务器的密钥库导出并导入到客户端的信任库中,除非它是由CA签名的,这是推荐且正常的。
服务器的密钥库停留在服务器上;客户的信任库在客户端。因此,您不需要像'serverKeystore'等变量名称。只需要'keystore'和'truststore'。
您没有使用客户端身份验证,因此客户端不需要密钥库,服务器也不需要信任库。
我建议你使用这些概念重做代码,然后对所有人来说都会变得更加清晰,尤其是你。
如果它仍然不起作用,则必须发布异常和堆栈跟踪。您可能还需要使用-Djavax.net.debug=ssl,handshake
运行服务器或客户端或两者,并在此处发布结果。