设置了码头和JavaScript客户端提供安全的WebSocket服务器

问题描述:

我试图建立一个安全的WebSocket服务器码头这样的:设置了码头和JavaScript客户端提供安全的WebSocket服务器

import java.util.ArrayList; 
import java.util.List; 

import org.eclipse.jetty.http.HttpVersion; 
import org.eclipse.jetty.server.Handler; 
import org.eclipse.jetty.server.HttpConfiguration; 
import org.eclipse.jetty.server.HttpConnectionFactory; 
import org.eclipse.jetty.server.Server; 
import org.eclipse.jetty.server.ServerConnector; 
import org.eclipse.jetty.server.SslConnectionFactory; 
import org.eclipse.jetty.server.handler.ContextHandler; 
import org.eclipse.jetty.server.handler.HandlerCollection; 
import org.eclipse.jetty.util.ssl.SslContextFactory; 
import org.eclipse.jetty.websocket.server.WebSocketHandler; 
import org.eclipse.jetty.websocket.servlet.WebSocketServletFactory; 


public class WebSocketServer 
{ 
    private Server server; 
    private String host="localhost"; 
    private int port=8080; 
    private String keyStorePath = "C:\\keystore"; 
    private String keyStorePassword="password"; 
    private String keyManagerPassword="password"; 
    private List<Handler> webSocketHandlerList = new ArrayList(); 
    MessageHandler messagehandler; 

    public WebSocketServer() 
    { 
     System.out.println("WebSocketServer"); 

     server = new Server(); 

     // connector configuration 
     SslContextFactory sslContextFactory = new SslContextFactory(); 
     sslContextFactory.setKeyStorePath(keyStorePath); 
     sslContextFactory.setKeyStorePassword(keyStorePassword); 
     sslContextFactory.setKeyManagerPassword(keyManagerPassword); 
     SslConnectionFactory sslConnectionFactory = new SslConnectionFactory(sslContextFactory, HttpVersion.HTTP_1_1.asString()); 
     HttpConnectionFactory httpConnectionFactory = new HttpConnectionFactory(new HttpConfiguration()); 
     ServerConnector sslConnector = new ServerConnector(server, sslConnectionFactory, httpConnectionFactory); 
     sslConnector.setHost(host); 
     sslConnector.setPort(port); 
     server.addConnector(sslConnector); 

     // handler configuration 
     HandlerCollection handlerCollection = new HandlerCollection(); 
     handlerCollection.setHandlers(webSocketHandlerList.toArray(new Handler[0])); 
     server.setHandler(handlerCollection); 

     WebSocketHandler wsHandler = new WebSocketHandler() { 
      @Override 
      public void configure(WebSocketServletFactory webSocketServletFactory) { 
       webSocketServletFactory.register(MyWebSocketHandler.class); 
      } 
     }; 
     ContextHandler wsContextHandler = new ContextHandler(); 
     wsContextHandler.setHandler(wsHandler); 
     wsContextHandler.setContextPath("/"); // this context path doesn't work ftm 
     webSocketHandlerList.add(wsHandler); 

     messagehandler = new MessageHandler(); 
     new Thread(messagehandler).start(); 

     try { 
      server.start(); 
     } catch (Exception e) { 
      e.printStackTrace(); 
     } 
    } 
} 

密钥库文件使用下面的命令创建发现here在JDK/bin文件夹:

keytool.exe -keystore keystore -alias jetty -genkey -keyalg RSA 

之后,我将文件移动到C目录以便于路径使用。

有了这个配置我的服务器似乎开始没有任何问题。所以,我想我的网站连接到它是这样的:

ws = new WebSocket("wss://localhost:8080/"); 

这并不在所有的工作。像写入here,我想我必须配置SSL证书。此外,为了创建服务器,我使用了这个tutorial,对于java客户端,他们实现了truststore。我是否必须为JavaScript做类似的事情?

答案可能有点晚,但是我经过多次尝试后才开始工作。


一些一般考虑第一:

  • 作为一般规则遵循(有效期为node.js的,太),您必须首先做出WSS工作HTTPS工作。 WebSocket通过HTTP工作,所以如果你的服务器已经正确配置了HTTPS(或HTTP),那么向它添加WebSocket将使WSS(或WS)工作。实际上HTTPS/WSS和HTTP/WS都可以同时工作

  • 证书是非常重要的,因为并非所有类型的证书都可以在Jetty中工作(node.js也是如此)。所以你必须生成Jetty将接受的证书。

  • 使HTTPS工作同样重要的是自签名证书,因为你可能通过HTTPS必须先访问服务器,并添加异常之前WSS可以工作(这可能取决于浏览器。)

  • 需要考虑的另一件事是上下文路径也需要被正确设置。我通过为HTTP和WS分开路径来实现它,例如用于HTTP(S)的/hello和用于WS(S)的/ws。这可能是可能的上是相同的上下文路径做到这一点,但我没有调查这还


下面是我遵循的步骤。 我在GitHub上放了一个working example

1)通过使用从here

命令上述连杆具有关于如何生成正确的自签名证书的示例生成正确的自签名的证书。 (如果你有CA签名的证书,我认为程序有些不同。)

我在这里粘贴命令以方便访问。请注意,每次询问时都要始终输入相同的密码(包括最后一个步骤中的一个,当您键入的密码将以明文显示在屏幕上时)。

openssl genrsa -aes256 -out jetty.key 
openssl req -new -x509 -key jetty.key -out jetty.crt 
keytool -keystore keystore -import -alias jetty -file jetty.crt -trustcacerts 
openssl req -new -key jetty.key -out jetty.csr 
openssl pkcs12 -inkey jetty.key -in jetty.crt -export -out jetty.pkcs12 
keytool -importkeystore -srckeystore jetty.pkcs12 -srcstoretype PKCS12 -destkeystore keystore 

2)在Jetty中有正确的HTTPS代码。

网上有一些资源显示了如何使用Jetty执行HTTPS,但对于我来说只有一个工作,并且它是here

3)有正确的代码来处理上下文。

这一个很难 - 从Jetty文档页面的示例代码不适合我。 工作原理是this。本教程还告诉我,如果我尝试对HTTP和WS使用相同的路径,可能会发生冲突。

4)最后,对WebSocket的

我找到了正确的WebSocket代码here正确的代码。有我们需要的是native-jetty-websocket-example

+0

感谢您的工作!这个问题还在我的列表上。下个月,当我回来工作时,我会尝试你的答案。 – Steckdoserich