這節課咱們根據官網教程學習如何去消費(調用)一個 RESTful Web Service 。 原文連接 https://spring.io/guides/gs/consuming-rest/java
本指南將引導您完成建立使用RESTful Web服務的應用程序的過程。git
您將構建一個使用Spring RestTemplate的應用程序來檢索http://gturnquist-quoters.cfapps.io/api/random中的隨機Spring Boot引用。github
JDK1.8 或者更高web
Gradle 4+ 或者 Maven 3.2+spring
你也能夠直接導入Code 到你的IDE中apache
方法有不少種,這裏咱們僅經過STS來完成這個操做。api
參考連接 https://spring.io/guides/gs/sts/瀏覽器
1. 打開咱們的STS,點擊左上角的File————> New ————> Import Spring Getting Started Content
2. 咱們這裏輸入 rest 來搜索出「Consuming Rest」
Tips:這裏勾選構建的類型是Maven項目,Code Sets 兩個都勾選,這樣會生成兩個Project.
complete 是表示已經寫好的code,initial是初始化空的項目,咱們待會就在這個空的項目中進行修改和嘗試。
3. 經過完成項目設置,您能夠建立一個使用RESTful服務的簡單應用程序。
一個RESTful服務已經在http://gturnquist-quoters.cfapps.io/api/random 站起來了。 它隨機提取有關Spring Boot的引用,並將它們做爲JSON文檔返回。
若是您經過網絡瀏覽器或curl請求該URL,您將收到一個以下所示的JSON文檔:
{"type":"success","value":{"id":2,"quote":"With Boot you deploy everywhere you can find a JVM basically."}}
很簡單,但經過瀏覽器獲取時不會很是有用。以編程方式更有用的方式來使用REST Web服務。
爲了幫助你完成這個任務,Spring提供了一個名爲RestTemplate的方便的模板類。 RestTemplate使大多數RESTful服務與單行咒語交互。 它甚至能夠將該數據綁定到自定義域類型。
4. 首先咱們須要建立一個Domain 實體類
package hello; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; @JsonIgnoreProperties(ignoreUnknown = true) public class Quote { private String type; private Value value; public Quote() { } public String getType() { return type; } public void setType(String type) { this.type = type; } public Value getValue() { return value; } public void setValue(Value value) { this.value = value; } @Override public String toString() { return "Quote{" + "type='" + type + '\'' + ", value=" + value + '}'; } }
正如你所看到的,這是一個簡單的Java類,它有一些屬性和匹配的getter方法。 它使用Jackson JSON處理庫中的@JsonIgnoreProperties進行了註釋,以指示任何未綁定在此類型的屬性都應該被忽略。
爲了直接將數據綁定到自定義類型,您須要指定變量的名稱與從API返回的JSON文檔中的鍵徹底相同。 若是JSON文檔中的變量名和鍵不匹配,則須要使用@JsonProperty 註解來指定JSON文檔的確切鍵。
Tips: 注意上面返回的JSON中字段名稱是type和value 因此這裏咱們定義的也是type和value.
5. 須要額外的類來嵌入內部報價自己。
package hello; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; @JsonIgnoreProperties(ignoreUnknown = true) public class Value { private Long id; private String quote; public Value() { } public Long getId() { return this.id; } public String getQuote() { return this.quote; } public void setId(Long id) { this.id = id; } public void setQuote(String quote) { this.quote = quote; } @Override public String toString() { return "Value{" + "id=" + id + ", quote='" + quote + '\'' + '}'; } }
Tips: 因爲上面返回的JSON 中value 是一個對象,包含id和quote,因此這裏咱們須要一個額外的類來定義它。
6.使這個應用程序變得可執行
雖然能夠將此服務做爲傳統WAR文件打包以部署到外部應用程序服務器,但下面演示的更簡單的方法會建立獨立應用程序。 您將全部內容打包到一個單獨的,可執行的JAR文件中,由一個良好的舊Java main()方法驅動。 一路上,您使用Spring的支持將Tomcat servlet容器做爲HTTP運行時嵌入,而不是部署到外部實例。
如今您能夠編寫使用RestTemplate的Application類來從Spring Boot報價服務中獲取數據。
package hello; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.web.client.RestTemplate; public class Application { private static final Logger log = LoggerFactory.getLogger(Application.class); public static void main(String[] args) { // TODO Auto-generated method stub RestTemplate restTemplate = new RestTemplate(); Quote quote = restTemplate.getForObject("http://gturnquist-quoters.cfapps.io/api/random", Quote.class); log.info(quote.toString()); } }
Tips: 這裏咱們能夠看到經過一個RestTemplate 對象的方法,咱們消費(調用)了另一個Restfule web service 的數據。有了這種調用方式,咱們便將再也不須要編寫Httpclient方法來處理調用。
因爲Jackson JSON處理庫位於類路徑中,RestTemplate將使用它(經過消息轉換器)將傳入的JSON數據轉換爲Quote對象。 從那裏,Quote對象的內容將被記錄到控制檯。
在這裏,您只使用RestTemplate進行HTTP GET請求。 但RestTemplate還支持其餘HTTP動詞,例如POST,PUT和DELETE。
打印控制檯如圖所示:
7. 使用Spring Boot管理應用程序生命週期
到目前爲止,咱們尚未在咱們的應用程序中使用過Spring Boot,但這樣作有一些優勢,並且這並不難。 其中一個優勢是咱們可能但願讓Spring Boot管理RestTemplate中的消息轉換器,以便自定義很容易以聲明方式添加。 爲此,咱們在主類上使用@SpringBootApplication並轉換主要方法來啓動它,就像在任何Spring Boot應用程序中同樣。 最後,咱們將RestTemplate移動到一個CommandLineRunner回調函數中,以便在啓動時由Spring Boot執行:
src/main/java/hello/Application.java
package hello; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.boot.CommandLineRunner; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.boot.web.client.RestTemplateBuilder; import org.springframework.context.annotation.Bean; import org.springframework.web.client.RestTemplate; @SpringBootApplication public class Application { private static final Logger log = LoggerFactory.getLogger(Application.class); public static void main(String[] args) { // TODO Auto-generated method stub SpringApplication.run(Application.class); // RestTemplate restTemplate = new RestTemplate(); // Quote quote = restTemplate.getForObject("http://gturnquist-quoters.cfapps.io/api/random", Quote.class); // log.info(quote.toString()); } @Bean public RestTemplate restTemplate(RestTemplateBuilder builder) { return builder.build(); } @Bean public CommandLineRunner run(RestTemplate restTemplate) throws Exception { return args -> { Quote quote = restTemplate.getForObject("http://gturnquist-quoters.cfapps.io/api/random", Quote.class); log.info(quote.toString()); }; } }
Tips: 剛纔那種方式顯然並不優雅,咱們註釋掉剛纔的內容更換成使用Spring Boot 的code 來看下。經過這種方式顯然更優雅地調用了 其餘Restful Web service.
RestTemplateBuilder由Spring注入,若是您使用它建立RestTemplate,那麼您將受益於Spring Boot中使用消息轉換器和請求工廠進行的全部自動配置。
咱們還將RestTemplate提取到@Bean中以使其更易於測試(這樣能夠更輕鬆地進行模擬)。
8.編譯生一個可執行的Jar
您可使用Gradle或Maven從命令行運行應用程序。 或者您能夠構建一個包含全部必需的依賴項,類和資源的可執行JAR文件,並運行該文件。 這使得在整個開發生命週期內跨越不一樣環境等,將服務做爲應用程序發佈,版本化和部署變得很是容易。
這一步咱們使用STS中集成的工具來操做生成一個可執行的Jar,如圖所示:
以後咱們應該能看到target 文件夾下多了一個文件
若是您正在使用Gradle,則可使用./gradlew bootRun運行該應用程序。 或者您可使用./gradlew構建構建JAR文件。 而後你能夠運行JAR文件:
java -jar build/libs/gs-consuming-rest-0.1.0.jar
若是您使用的是Maven,則可使用./mvnw spring-boot:run來運行該應用程序。 或者,您可使用./mvnw clean包構建JAR文件。 而後你能夠運行JAR文件:
java -jar target/gs-consuming-rest-0.1.0.jar
上述過程將建立一個可運行的JAR。 您也能夠選擇構建經典的WAR文件。
您應該看到以下所示的輸出,並隨機引用:
若是你看到錯誤沒法提取響應:沒有找到合適的HttpMessageConverter用於響應類型[class hello.Quote],那麼你有可能處於一個沒法鏈接到後端服務的環境中(若是能夠的話,它會發送JSON)。 也許你背後是一個公司代理? 嘗試將標準系統屬性http.proxyHost和http.proxyPort設置爲適合您的環境的值。
好了本節課到這裏就結束了,經過本節課咱們發現Spring Boot 中服務之間相互調用時最原生的實際上是經過這種方式調用的。