如何将安全的 Jersey 应用程序部署到 Heroku
How to deploy secure Jersey application to Heroku
很容易弄清楚如何将使用 Grizzly 的 Jersey 应用程序部署到 Heroku。启动基本应用程序后,我决定按照 https-clientserver-grizzly 示例中的说明来保护我的端点,但在将其部署到 Heroku 时遇到一些问题 运行。
部署到 Heroku 后,服务器拒绝响应,关闭所有连接请求而不发送响应。我在本地没有问题,只有当我部署到 Heroku 时才会出现此错误。
我在下面包含了我的 Server.java 文件的相关部分。
public class Server extends ResourceConfig {
private static final String DEFAULT_SERVER_PORT = "8443";
private static final String KEY_SERVER_PORT = "server.port";
private static final String KEY_TRUST_PASSWORD = "TRUST_PASSWORD";
private static final String KEYSTORE_SERVER_FILE = "./security/keystore_server";
private static final String LOCALHOST = "https://0.0.0.0:%s/v1";
private static final String TRUSTSTORE_SERVER_FILE = "./security/truststore_server";
private final String endpoint;
private final HttpServer httpServer;
private Server(final String endpoint) throws KeyManagementException,
NoSuchAlgorithmException, KeyStoreException, CertificateException,
FileNotFoundException, IOException, UnrecoverableKeyException {
super();
...
URI.create(this.endpoint),
this,
true,
secure());
this.httpServer.start();
System.out.println(String.format(
"Jersey app started with WADL available at %s/application.wadl",
this.endpoint));
}
/**
* Generates a secure configurator for the server.
* @return A {@link SSLEngineConfigurator} instance for the server.
* @throws IOException If the key or trust store password cannot be read.
* @throws RuntimeException If the configuration is considered invalid.
*/
private static SSLEngineConfigurator secure() throws IOException, RuntimeException {
// Set up security context
final String password = System.getenv(KEY_TRUST_PASSWORD);
if (password == null) {
throw new RuntimeException("Truststore password is not set in the environment");
}
// Grizzly ssl configuration
SSLContextConfigurator sslContext = new SSLContextConfigurator();
// set up security context
sslContext.setKeyStoreFile(KEYSTORE_SERVER_FILE); // contains server keypair
sslContext.setKeyStorePass(password);
sslContext.setTrustStoreFile(TRUSTSTORE_SERVER_FILE); // contains client certificate
sslContext.setTrustStorePass(password);
sslContext.setSecurityProtocol("TLS");
if (!sslContext.validateConfiguration(true)) {
throw new RuntimeException("SSL context is invalid");
}
return new SSLEngineConfigurator(sslContext)
.setClientMode(false)
.setNeedClientAuth(false);
}
}
如果有人经历过这个问题并有任何建议,我们将不胜感激!
在 Heroku 上,您不需要自己在 Java 应用程序中设置 HTTPS。 Heroku 为您处理 HTTPS,SSL 终止发生在 Heroku 路由器上,因此流量在到达您的应用程序时未加密。
只需以 https:// 访问您的站点。herokuapp.com
很容易弄清楚如何将使用 Grizzly 的 Jersey 应用程序部署到 Heroku。启动基本应用程序后,我决定按照 https-clientserver-grizzly 示例中的说明来保护我的端点,但在将其部署到 Heroku 时遇到一些问题 运行。
部署到 Heroku 后,服务器拒绝响应,关闭所有连接请求而不发送响应。我在本地没有问题,只有当我部署到 Heroku 时才会出现此错误。
我在下面包含了我的 Server.java 文件的相关部分。
public class Server extends ResourceConfig {
private static final String DEFAULT_SERVER_PORT = "8443";
private static final String KEY_SERVER_PORT = "server.port";
private static final String KEY_TRUST_PASSWORD = "TRUST_PASSWORD";
private static final String KEYSTORE_SERVER_FILE = "./security/keystore_server";
private static final String LOCALHOST = "https://0.0.0.0:%s/v1";
private static final String TRUSTSTORE_SERVER_FILE = "./security/truststore_server";
private final String endpoint;
private final HttpServer httpServer;
private Server(final String endpoint) throws KeyManagementException,
NoSuchAlgorithmException, KeyStoreException, CertificateException,
FileNotFoundException, IOException, UnrecoverableKeyException {
super();
...
URI.create(this.endpoint),
this,
true,
secure());
this.httpServer.start();
System.out.println(String.format(
"Jersey app started with WADL available at %s/application.wadl",
this.endpoint));
}
/**
* Generates a secure configurator for the server.
* @return A {@link SSLEngineConfigurator} instance for the server.
* @throws IOException If the key or trust store password cannot be read.
* @throws RuntimeException If the configuration is considered invalid.
*/
private static SSLEngineConfigurator secure() throws IOException, RuntimeException {
// Set up security context
final String password = System.getenv(KEY_TRUST_PASSWORD);
if (password == null) {
throw new RuntimeException("Truststore password is not set in the environment");
}
// Grizzly ssl configuration
SSLContextConfigurator sslContext = new SSLContextConfigurator();
// set up security context
sslContext.setKeyStoreFile(KEYSTORE_SERVER_FILE); // contains server keypair
sslContext.setKeyStorePass(password);
sslContext.setTrustStoreFile(TRUSTSTORE_SERVER_FILE); // contains client certificate
sslContext.setTrustStorePass(password);
sslContext.setSecurityProtocol("TLS");
if (!sslContext.validateConfiguration(true)) {
throw new RuntimeException("SSL context is invalid");
}
return new SSLEngineConfigurator(sslContext)
.setClientMode(false)
.setNeedClientAuth(false);
}
}
如果有人经历过这个问题并有任何建议,我们将不胜感激!
在 Heroku 上,您不需要自己在 Java 应用程序中设置 HTTPS。 Heroku 为您处理 HTTPS,SSL 终止发生在 Heroku 路由器上,因此流量在到达您的应用程序时未加密。
只需以 https:// 访问您的站点。herokuapp.com