我正在尝试使用Jetty设置安全的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();
}
}
}
创建密钥库文件使用以下命令发现这里在JDK / bin文件夹:
keytool.exe -keystore keystore -alias jetty -genkey -keyalg RSA
之后,我将该文件移到C目录中,以方便使用路径。
通过这种配置,我的服务器似乎可以正常启动。所以我试图像这样通过我的网站连接到它:
ws = new WebSocket("wss://localhost:8080/");
这根本不起作用。就像这里写的,我想我必须配置SSL证书。此外,为了创建服务器,我使用了本教程,对于Java客户端,他们实现了一个truststore
。我必须对JavaScript做类似的事情吗?
答案可能为时已晚,但经过多次尝试,我已使其成功。
首先要注意以下几点:
作为要遵循的一般规则(对node.js也有效),必须首先使HTTPS起作用才能使WSS起作用。WebSocket通过HTTP运行,因此,如果服务器已正确配置了HTTPS(或HTTP),则向其添加WebSocket将使WSS(或WS)正常工作。实际上,HTTPS / WSS和HTTP / WS可以同时工作
证书非常重要,因为并非所有类型的证书都可以与Jetty一起使用(node.js也是如此)。因此,您必须生成Jetty将接受的证书。
使HTTPS起作用对于自签名证书也很重要,因为您可能必须首先通过HTTPS访问服务器并在WSS起作用之前添加异常(这可能取决于浏览器。)
要考虑的另一件事是上下文路径也需要正确设置。我通过为HTTP和WS设置了单独的路径来使其工作,例如/hello
HTTP(S)和/ws
WS(S)。两者可能都可以使用相同的上下文路径来完成,但我尚未对此进行调查
以下是我遵循的步骤。我在GitHub上放了一个工作示例。
1)使用此处的命令生成正确的自签名证书
上面的链接提供了有关如何生成正确的自签名证书的示例。(我认为,如果您具有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,但对我来说只有一个有效,就在这里。
3)具有用于处理上下文的正确代码。
这很困难-Jetty文档页面上的示例代码对我不起作用。什么工作是这样。本教程还启发了我一个事实,即如果我尝试对HTTP和WS使用相同的路径,则可能会发生冲突。
4)最后,获取正确的WebSocket代码
我在这里找到了正确的WebSocket代码。我们需要的是native-jetty-websocket-example
。
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句