Spring Boot-實現Undertow服務器同時支持HTTP二、HTTPS

前言

現在,企業級應用程序的高性能安全加密的常見場景是同時支持HTTP和HTTPS兩種協議,這篇文章考慮如何讓Spring Boot應用程序同時支持HTTP和HTTPS兩種協議。Spring Boot的web容器已經有容器能夠支持HTTP2了,這個例子中選擇了Undertow高性能服務器做爲Spring Boot的web容器。html

What-什麼是HTTP2

HTTP2是HTTP協議自1999年HTTP1.1發佈後的首個更新,主要基於SPDY協議。由互聯網工程任務組(IETF)的 Hypertext Transfer Protocol Bis(httpbis)工做小組進行開發。該組織於2014年12月將HTTP/2標準提議遞交至IESG進行討論,於2015年2月17日被批准。HTTP2標準於2015年5月以RFC7540正式發表。java


Why-爲何要用HTTP2

HTTP2是第二代的HTTP協議,關於HTTP2的優勢這裏就不闡述了,能夠參考下面連接文章瞭解:http://ju.outofmemory.cn/entr...
下圖是Akamai 公司創建的一個官方的演示,主要用來講明在性能上HTTP/1.1和HTTP/2在性能升的差異。同時請求 379 張圖片,HTTP/1.1加載用時4.54s,HTTP/2加載用時1.47s,你們能夠經過 https://http2.akamai.com/demo 來感覺下HTTP2的提速。web

圖片描述

What-什麼是HTTPS

要說HTTPS咱們得先說SSL(Secure Sockets Layer,安全套接層),這是一種爲網絡通訊提供安全及數據完整性的一種安全協議,SSL在網絡傳輸層對網絡鏈接進行加密。SSL協議能夠分爲兩層:SSL記錄協議(SSL Record Protocol),它創建在可靠的傳輸協議如TCP之上,爲高層協議提供數據封裝、壓縮、加密等基本功能支持;SSL握手協議(SSL Handshake Protocol),它創建在SSL記錄協議之上,用於在實際數據傳輸開始以前,通訊雙方進行身份認證、協商加密算法、交換加密密鑰等。在Web開發中,咱們是經過HTTPS來實現SSL的。HTTPS是以安全爲目標的HTTP通道,簡單來講就是HTTP的安全版,即在HTTP下加入SSL層,因此說HTTPS的安全基礎是SSL,不過這裏有一個地方須要小夥伴們注意,就是咱們如今市場上使用的都是TLS協議(Transport Layer Security,它來源於SSL),而不是SSL,因爲SSL出現較早而且被各大瀏覽器支持所以成爲了HTTPS的代名詞。
圖片描述算法


Why-爲何要用HTTPS

超文本傳輸協議HTTP協議被用於在Web瀏覽器和網站服務器之間傳遞信息。HTTP協議以明文方式發送內容,不提供任何方式的數據加密,若是攻擊者截取了Web瀏覽器和網站服務器之間的傳輸報文,就能夠直接讀懂其中的信息,所以HTTP協議不適合傳輸一些敏感信息,好比信用卡號、密碼等。
爲了解決HTTP協議的這一缺陷,須要使用另外一種協議:安全套接字層超文本傳輸協議HTTPS。爲了數據傳輸的安全,HTTPS在HTTP的基礎上加入了SSL協議,SSL依靠證書來驗證服務器的身份,併爲瀏覽器和服務器之間的通訊加密。
HTTPS和HTTP的區別主要爲如下四點:
1、https協議須要到ca申請證書,通常免費證書不多,須要交費。
2、http是超文本傳輸協議,信息是明文傳輸,https 則是具備安全性的ssl加密傳輸協議。
3、http和https使用的是徹底不一樣的鏈接方式,用的端口也不同,前者是80,後者是443。
4、http的鏈接很簡單,是無狀態的;HTTPS協議是由SSL+HTTP協議構建的可進行加密傳輸、身份認證的網絡協議,比http協議安全。spring


How-如何使用HTTPS和HTTP

若是你使用Spring Boot,而且想在內嵌服務器中添加HTTPS,須要以下步驟:chrome

  • 要有一個SSL證書,買的或者本身生成的。
  • 在Spring Boot中啓動HTTPS。
  • 將HTTP重定向到HTTPS(可選)。

獲取SSL證書

證書獲取有兩種方式,一種是本身經過jdk的keytool命令生成,一種是經過證書受權機構購買,本文爲了方便採用第二種從阿里雲購買證書。api

去阿里雲購買證書(免費版),並提交審覈資料瀏覽器

圖片描述

圖片描述

圖片描述

圖片描述

圖片描述

  • 下載SSL證書

圖片描述

圖片描述

在證書目錄下執行阿里雲提供的命令,密碼都填 pfx-password.txt 中的內容(三次),會生成 javalsj.jks 文件。安全

keytool -importkeystore -srckeystore 214533136960974.pfx -destkeystore javalsj.jks -srcstoretype PKCS12 -deststoretype JKS

圖片描述

在Spring Boot中啓動HTTPS和HTTP2

將javalsj.jks複製到Spring Boot應用的resources目錄下
圖片描述服務器

在application.properties中配置證書及端口,密碼填寫第3步中的密碼

##################################---Undertow服務器支持HTTPS服務---##############################################
server.http2.enabled=true
server.servlet.context-path=/blog
custom.server.http.port=8080
server.port=8443
server.ssl.key-store=classpath:javalsj.jks
server.ssl.key-store-password=214533136960974

server.undertow.worker-threads=20
server.undertow.buffer-size=512
server.undertow.io-threads=2

圖片描述
此配置會使Undertow容器監聽8443端口,那麼只有在域名前添加 https://才能訪問網站內容,添加http://則不行,因此須要讓Undertow容器監聽8080端口,並將8080端口的全部請求重定向到8443端口,即完成http到https的跳轉。

將HTTP重定向到HTTPS(可選)

工程使用Gradle集成輕量級高性能非阻塞服務器undertow所須要的jar包:
compile group: 'org.springframework.boot', name: 'spring-boot-starter-undertow'
而後編寫代碼以下:

package com.javalsj.blog.configuration;

import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.web.embedded.undertow.UndertowServletWebServerFactory;
import org.springframework.boot.web.servlet.server.ServletWebServerFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import io.undertow.Undertow;
import io.undertow.servlet.api.SecurityConstraint;
import io.undertow.servlet.api.SecurityInfo;
import io.undertow.servlet.api.TransportGuaranteeType;
import io.undertow.servlet.api.WebResourceCollection;

/**
 * @description 採用Undertow做爲服務器,支持Https服務配置
 * @author WANGJIHONG
 * @date 2018年3月7日 下午8:34:18
 * @Copyright 版權全部 (c) www.javalsj.com
 * @memo 備註信息
 */
@Configuration
public class WebServerConfiguration {
    
    /** 
     * http服務端口
     */ 
    @Value("${custom.server.http.port}")
    private Integer httpPort;
    
    /** 
     * https服務端口
     */ 
    @Value("${server.port}")
    private Integer httpsPort;
    
    /**
     * 採用Undertow做爲服務器。
     * Undertow是一個用java編寫的、靈活的、高性能的Web服務器,提供基於NIO的阻塞和非阻塞API,特色:
     * 很是輕量級,Undertow核心瓶子在1Mb如下。它在運行時也是輕量級的,有一個簡單的嵌入式服務器使用少於4Mb的堆空間。
     * 支持HTTP升級,容許多個協議經過HTTP端口進行多路複用。
     * 提供對Web套接字的全面支持,包括JSR-356支持。
     * 提供對Servlet 3.1的支持,包括對嵌入式servlet的支持。還能夠在同一部署中混合Servlet和本機Undertow非阻塞處理程序。
     * 能夠嵌入在應用程序中或獨立運行,只需幾行代碼。
     * 經過將處理程序連接在一塊兒來配置Undertow服務器。它能夠對各類功能進行配置,方便靈活。
     */
    @Bean
    public ServletWebServerFactory undertowFactory() {
        UndertowServletWebServerFactory undertowFactory = new UndertowServletWebServerFactory();
        undertowFactory.addBuilderCustomizers((Undertow.Builder builder) -> {
            builder.addHttpListener(httpPort, "0.0.0.0");
            // 開啓HTTP2
            builder.setServerOption(UndertowOptions.ENABLE_HTTP2, true);
        });
        undertowFactory.addDeploymentInfoCustomizers(deploymentInfo -> {
            // 開啓HTTP自動跳轉至HTTPS 
            deploymentInfo.addSecurityConstraint(new SecurityConstraint()
                    .addWebResourceCollection(new WebResourceCollection().addUrlPattern("/*"))
                    .setTransportGuaranteeType(TransportGuaranteeType.CONFIDENTIAL)
                    .setEmptyRoleSemantic(SecurityInfo.EmptyRoleSemantic.PERMIT))
                    .setConfidentialPortManager(exchange -> httpsPort);
        });
        return undertowFactory;
    }
    
}

圖片描述

驗證HTTPS和HTTP2開啓成功

重啓服務,即完成了HTTP到HTTPS的升級,且能自動跳轉HTTPS,讓網站更安全。輸入http://localhost:8080/blog/swagger-ui.html後回車地址欄自動跳轉至https://localhost:8443/blog/swagger-ui.html,如圖:

圖片描述


使用Chrome瀏覽器的console控制檯,輸入腳本後回車查看HTTP2是否開啓,腳本以下:

(function(){
    // 保證這個方法只在支持loadTimes的chrome瀏覽器下執行
    if(window.chrome && typeof chrome.loadTimes === 'function') {
        var loadTimes = window.chrome.loadTimes();
        var spdy = loadTimes.wasFetchedViaSpdy;
        var info = loadTimes.npnNegotiatedProtocol || loadTimes.connectionInfo;
        // 就以 「h2」做爲判斷標識
        if(spdy && /^h2/i.test(info)) {
            return console.info('本站點使用了HTTP/2');
        }
    }
    console.warn('本站點沒有使用HTTP/2');
})();

圖片描述

總結

本文只是介紹了Undertow服務器的HTTPS支持,Spring Boot支持Jetty,Tomcat等服務器,不一樣的服務器實現能夠查資料瞭解,嘿嘿。
圖片描述

相關文章
相關標籤/搜索