嵌入式码头使用 RewriteHandler 和 SecuredRedirectHandler 重写和重定向 http 到 https 和路径
Embedded jetty rewrite and redirect http to https and path both using RewriteHandler and SecuredRedirectHandler
我有一个嵌入式码头应用程序(码头 9.3.12),我需要重定向来自 http://host and http://host/my/app to https://host/my/app
的请求
我已经使用 RewriteHandler 一段时间了,成功重定向 http://host -> http://host/my/app and https://host -> https://host/my/app。
我不知道如何让 http://host -> https://host/my/app 工作。
我还有另一个由同一服务器处理的码头上下文,我将其称为 /other(未反映在下面的代码中)。我不想重定向 http://other -> https://other.
这是我想要发生的事情的摘要
http:// -> https://my/app
http://my/app -> https://my/app
https:// -> https://my/app
http://other -> no change
如果我将 SecuredRedirectHandler 直接添加到服务器处理程序(请参阅代码中的替代方法),那么我在访问 /my/app 时会遇到 404 问题。原因:未找到。
如果我在 RewriteHandler 后面添加 SecuredRedirectHandler,则什么也不会发生(下面的代码)。
private Server createServer() {
Server server = new Server();
configureConnectors(server);
HandlerCollection handlers = getHandlers(server);
RewriteHandler rewriteHandler = createRewriteHandler(server);
server.setHandler(rewriteHandler);
return server;
}
private void configureConnectors(Server server) {
List<ServerConnector> connectors = new ArrayList<>();
ServerConnect httpsConnector = createHttpsConnector(server);
boolean httpsEnabled = httpsConnector != null;
ServerConnector httpConnector = createHttpConnector(server, httpsEnabled);
connectors.add(httpConnector);
connectors.add(httpsConnector);
// ALTERNATIVE METHOD - Results in 404 - Problem access /my/app Reason: Not Found
//addHandlerAsFirst(new SecuredRedirectHandler(), server);
for (ServerConnector connector : connectors) {
server.addConnector(connector);
}
}
private ServerConnector createHttpConnector(Server server, boolean httpsEnabled) {
HttpConfiguration httpConfig = new HttpConfiguration();
if (httpsEnabled) {
Integer httpsPort = getServiceUrl().getPortSsl();
httpConfig.addCustomizer(new SecureRequestCustomizer());
httpConfig.setSecureScheme(HttpScheme.HTTPS.asString());
httpConfig.setSecurePort(httpsPort);
}
Integer port = getServiceUrl().getPort();
ServerConnector connector = new ServerConnector(server, new HttpConnectionFactory(httpConfig));
connector.setPort(port);
configureConnector(connector);
return connector;
}
private ServerConnector createHttpsConnector(Server server) {
Integer httpsPort = getServiceUrl().getPortSsl();
Integer port = httpsPort;
HttpConfiguration httpConfig = new HttpConfiguration();
httpConfig.addCustomizer(new SecureRequestCustomizer());
SslContextFactory sslContextFactory = null;
try {
sslContextFactory = createSslContextFactory();
} catch (ConfigurationException | NotFoundException e) {
log.err(m, e, "Create SSL Context failed: Perhaps Certificate Policy Bindings are not configured?");
return null;
}
SslConnectionFactory connectionFactory = new SslConnectionFactory(sslContextFactory, HTTP_VERSION);
ServerConnector connector = new ServerConnector(server, connectionFactory, new HttpConnectionFactory(httpConfig));
connector.setPort(port);
configureConnector(connector);
return connector;
}
public RewriteHandler createRewriteContext(HandlerCollection handlerCollection) {
RewriteHandler rewrite = new RewriteHandler();
rewrite.setRewriteRequestURI(true);
rewrite.setRewritePathInfo(false);
rewrite.setOriginalPathAttribute("requestedPath");
rewrite.setHandler(handlerCollection);
String path = AppProductConfig.CONSOLE_CONTEXT_ROOT + AppUI.APP_PATH;
/*
* Redirect "/" to "/console/app". We use redirect instead of rewrite
* because Vaadin needs to access it's widgetset files. The rewrite requires
* multiple rules to accomplish this. The redirect is simpler.
*/
RedirectPatternRule rootRule = new RedirectPatternRule();
rootRule.setPattern(""); // Redirect / (root)
rootRule.setLocation(path);
rewrite.addRule(rootRule);
return rewrite;
}
protected void addHandlerAsFirst(Handler handler, Server server) {
HandlerCollection handlers = handlersMap.get(server);
if (handlers == null) {
handlers = new HandlerCollection();
handlersMap.put(server, handlers);
}
handlers.prependHandler(handler);
}
已解决
我能够使用这种方法使事情正常进行:
您将有 2 次重定向,而不是 1 次。
Server
HandlerList
SecuredRedirectHandler
RewriteHandler
Rule -> "/" to "/my/app"
ServletContextHandler or WebAppContext
DefaultHandler
不要尝试重写路径,也不要重定向到 HTTPS。
就让每个人独立做自己的事情吧
想想这些场景:
http://host/my/app
(仅使用 SecuredRedirectHandler)
https://host/
(仅使用 RewriteHandler)
http://host/
(2 次重定向,一次用于方案,第二次用于路径)
我有一个嵌入式码头应用程序(码头 9.3.12),我需要重定向来自 http://host and http://host/my/app to https://host/my/app
的请求我已经使用 RewriteHandler 一段时间了,成功重定向 http://host -> http://host/my/app and https://host -> https://host/my/app。
我不知道如何让 http://host -> https://host/my/app 工作。
我还有另一个由同一服务器处理的码头上下文,我将其称为 /other(未反映在下面的代码中)。我不想重定向 http://other -> https://other.
这是我想要发生的事情的摘要
http:// -> https://my/app
http://my/app -> https://my/app
https:// -> https://my/app
http://other -> no change
如果我将 SecuredRedirectHandler 直接添加到服务器处理程序(请参阅代码中的替代方法),那么我在访问 /my/app 时会遇到 404 问题。原因:未找到。
如果我在 RewriteHandler 后面添加 SecuredRedirectHandler,则什么也不会发生(下面的代码)。
private Server createServer() {
Server server = new Server();
configureConnectors(server);
HandlerCollection handlers = getHandlers(server);
RewriteHandler rewriteHandler = createRewriteHandler(server);
server.setHandler(rewriteHandler);
return server;
}
private void configureConnectors(Server server) {
List<ServerConnector> connectors = new ArrayList<>();
ServerConnect httpsConnector = createHttpsConnector(server);
boolean httpsEnabled = httpsConnector != null;
ServerConnector httpConnector = createHttpConnector(server, httpsEnabled);
connectors.add(httpConnector);
connectors.add(httpsConnector);
// ALTERNATIVE METHOD - Results in 404 - Problem access /my/app Reason: Not Found
//addHandlerAsFirst(new SecuredRedirectHandler(), server);
for (ServerConnector connector : connectors) {
server.addConnector(connector);
}
}
private ServerConnector createHttpConnector(Server server, boolean httpsEnabled) {
HttpConfiguration httpConfig = new HttpConfiguration();
if (httpsEnabled) {
Integer httpsPort = getServiceUrl().getPortSsl();
httpConfig.addCustomizer(new SecureRequestCustomizer());
httpConfig.setSecureScheme(HttpScheme.HTTPS.asString());
httpConfig.setSecurePort(httpsPort);
}
Integer port = getServiceUrl().getPort();
ServerConnector connector = new ServerConnector(server, new HttpConnectionFactory(httpConfig));
connector.setPort(port);
configureConnector(connector);
return connector;
}
private ServerConnector createHttpsConnector(Server server) {
Integer httpsPort = getServiceUrl().getPortSsl();
Integer port = httpsPort;
HttpConfiguration httpConfig = new HttpConfiguration();
httpConfig.addCustomizer(new SecureRequestCustomizer());
SslContextFactory sslContextFactory = null;
try {
sslContextFactory = createSslContextFactory();
} catch (ConfigurationException | NotFoundException e) {
log.err(m, e, "Create SSL Context failed: Perhaps Certificate Policy Bindings are not configured?");
return null;
}
SslConnectionFactory connectionFactory = new SslConnectionFactory(sslContextFactory, HTTP_VERSION);
ServerConnector connector = new ServerConnector(server, connectionFactory, new HttpConnectionFactory(httpConfig));
connector.setPort(port);
configureConnector(connector);
return connector;
}
public RewriteHandler createRewriteContext(HandlerCollection handlerCollection) {
RewriteHandler rewrite = new RewriteHandler();
rewrite.setRewriteRequestURI(true);
rewrite.setRewritePathInfo(false);
rewrite.setOriginalPathAttribute("requestedPath");
rewrite.setHandler(handlerCollection);
String path = AppProductConfig.CONSOLE_CONTEXT_ROOT + AppUI.APP_PATH;
/*
* Redirect "/" to "/console/app". We use redirect instead of rewrite
* because Vaadin needs to access it's widgetset files. The rewrite requires
* multiple rules to accomplish this. The redirect is simpler.
*/
RedirectPatternRule rootRule = new RedirectPatternRule();
rootRule.setPattern(""); // Redirect / (root)
rootRule.setLocation(path);
rewrite.addRule(rootRule);
return rewrite;
}
protected void addHandlerAsFirst(Handler handler, Server server) {
HandlerCollection handlers = handlersMap.get(server);
if (handlers == null) {
handlers = new HandlerCollection();
handlersMap.put(server, handlers);
}
handlers.prependHandler(handler);
}
已解决
我能够使用这种方法使事情正常进行:
您将有 2 次重定向,而不是 1 次。
Server
HandlerList
SecuredRedirectHandler
RewriteHandler
Rule -> "/" to "/my/app"
ServletContextHandler or WebAppContext
DefaultHandler
不要尝试重写路径,也不要重定向到 HTTPS。 就让每个人独立做自己的事情吧
想想这些场景:
http://host/my/app
(仅使用 SecuredRedirectHandler)https://host/
(仅使用 RewriteHandler)http://host/
(2 次重定向,一次用于方案,第二次用于路径)