java - enable - spring security example
Habilitar http2 con Tomcat en Spring Boot (4)
Tomcat 8.5
, que será el predeterminado en Spring Boot 1.4
, (que se lanzará mañana) es compatible con http2
.
¿Cómo se puede habilitar http2
en una aplicación Spring Boot
?
Debe agregar el protocolo de actualización HTTP 2 al conector de Tomcat. Puede hacerlo personalizando el contenedor de Tomcat incorporado:
Java 8:
@Bean
public EmbeddedServletContainerCustomizer tomcatCustomizer() {
return (container) -> {
if (container instanceof TomcatEmbeddedServletContainerFactory) {
((TomcatEmbeddedServletContainerFactory) container)
.addConnectorCustomizers((connector) -> {
connector.addUpgradeProtocol(new Http2Protocol());
});
}
};
}
Java 7:
@Bean
public EmbeddedServletContainerCustomizer tomcatCustomizer() {
return new EmbeddedServletContainerCustomizer() {
@Override
public void customize(ConfigurableEmbeddedServletContainer container) {
if (container instanceof TomcatEmbeddedServletContainerFactory) {
((TomcatEmbeddedServletContainerFactory) container)
.addConnectorCustomizers(new TomcatConnectorCustomizer() {
@Override
public void customize(Connector connector) {
connector.addUpgradeProtocol(new Http2Protocol());
}
});
}
}
};
}
En Spring Boot 2, primero necesita un certificado; se puede generar de esta manera:
keytool -genkey -keyalg RSA -alias my-the-best-api -keystore c:/tmp/keystore.store -storepass secret -validity 3650 -keysize 2048
De lo que solo necesita agregar este certificado a la ruta de clase y agregar las propiedades necesarias a application.properties:
server.http2.enabled=true
server.port = 8443
server.ssl.key-store=classpath:keystore.jks
server.ssl.key-password=secret
Esto probablemente hace lo mismo en Spring Boot 2.0:
@Bean
public ConfigurableServletWebServerFactory tomcatCustomizer() {
TomcatServletWebServerFactory factory = new TomcatServletWebServerFactory();
factory.addConnectorCustomizers(connector -> {
connector.addUpgradeProtocol(new Http2Protocol());
});
return factory;
}
La forma más elegante y con mejor rendimiento de habilitar HTTP/2
con una aplicación Spring Boot se encuentra aquí.
Primero, como se mencionó en la respuesta de Andy Wilkinson, debe habilitar HTTP / 2 en el nivel de Tomcat:
@Bean
public EmbeddedServletContainerCustomizer tomcatCustomizer() {
return (container) -> {
if (container instanceof TomcatEmbeddedServletContainerFactory) {
((TomcatEmbeddedServletContainerFactory) container)
.addConnectorCustomizers((connector) -> {
connector.addUpgradeProtocol(new Http2Protocol());
});
}
};
}
En caso de que no esté utilizando un Tomcat incorporado, puede configurar la escucha HTTP / 2 de la siguiente manera:
<Connector port="5080" protocol="HTTP/1.1" connectionTimeout="20000">
<UpgradeProtocol className="org.apache.coyote.http2.Http2Protocol" />
</Connector>
Recuerda que necesitas Tomcat> = 8.5.
Luego, debe usar HAProxy
(versión> = 1.7) delante de Tomcat para encargarse del cifrado.
El cliente hablará https a HAProxy, y HAProxy hablará HTTP / 1.1 o HTTP / 2 de texto simple al backend, según lo solicite el cliente. No habrá traducciones de protocolo innecesarias.
La configuración HAProxy correspondiente está aquí:
# Create PEM: cat cert.crt cert.key ca.crt > /etc/ssl/certs/cert.pem
global
tune.ssl.default-dh-param 2048
ssl-default-bind-options no-sslv3 no-tls-tickets force-tlsv12
ssl-default-bind-ciphers ECDH+AESGCM:DH+AESGCM:ECDH+AES256:DH+AES256:ECDH+AES128:DH+AES:ECDH+3DES:DH+3DES:RSA+AESGCM:RSA+AES:RSA+3DES:!aNULL:!MD5:!DSS
chroot /var/lib/haproxy
user haproxy
group haproxy
defaults
timeout connect 10000ms
timeout client 60000ms
timeout server 60000ms
frontend fe_https
mode tcp
rspadd Strict-Transport-Security:/ max-age=31536000;/ includeSubDomains;/ preload
rspadd X-Frame-Options:/ DENY
bind *:443 ssl crt /etc/ssl/certs/cert.pem alpn h2,http/1.1
default_backend be_http
backend be_http
mode tcp
server domain 127.0.0.1:8080
compression algo gzip
compression type text/html text/css text/javascript application/json