領先一步
VMware 提供培訓和認證,以加速您的進度。
了解更多我們很高興宣布 Spring Cloud Function 3.0.0.M2 的第二個里程碑版本。
注意:Spring Cloud Function 3.0.0.M1 主要是為了建立與 Spring Boot 2.2.x 的相容性,因此沒有發布公告。
Spring Cloud Function 3.0.0.M2 模組可在 Spring Milestone 儲存庫中使用。
此里程碑版本引入的最大功能之一是支援具有多個輸入和輸出的函數。重要的一點是,此功能僅在反應式環境中才有意義,您可能希望將多個串流傳遞給函數,以便對這些串流執行某種類型的聚合/合併操作。對於傳統情況,您可以始終使用某種類型的 Collection 傳送多個參數。
為了以型別安全的方式表示多個輸入/輸出,從而受益於型別轉換和先前提及的其他功能,我們選擇了 project reactor 中的 Tuple
函式庫,因為 spring-cloud-function 從一開始就將其作為核心依賴項。但是,未來我們也打算支援 BiFunction
之類的型別以及 POJO 樣式的函數,如果我們可以透過某種類型的慣例來確定輸入和輸出的元數和型別。
雖然此功能是新的並且正在增強,但它已經被幾個內部專案使用,您也可以嘗試一下。這是一個範例
假設以下函數
@Bean
public Function<Tuple2<Flux<String>, Flux<Integer>>, Flux<?>[]> repeater() {
return tuple -> {
Flux<String> stringFlux = tuple.getT1();
Flux<Integer> integerFlux = tuple.getT2();
Flux<Integer> sharedIntFlux = integerFlux.publish().autoConnect(2);
Flux<String> repeated = stringFlux
.zipWith(sharedIntFlux)
.flatMap(t ->
Flux.fromIterable(Collections.nCopies(t.getT2(), t.getT1())));
Flux<Integer> sum = sharedIntFlux
.buffer(3, 1)
.map(l -> l.stream().mapToInt(Integer::intValue).sum());
return new Flux[] { repeated, sum };
};
}
您可以這樣呼叫它
Function<Tuple2<Flux<String>, Flux<Integer>>, Flux<?>[]> repeater = catalog.lookup("repeater");
Flux<String> stringStream = Flux.just("one", "two", "three");
Flux<Integer> intStream = Flux.just(3, 2, 1);
Flux<?>[] result = repeater.apply(Tuples.of(stringStream, intStream));
result[0].subscribe(System.out::println);
result[1].subscribe(System.out::println);
未來將會有一篇關於此主題的單獨部落格文章。
與之前一樣,函數可以使用命令式或反應式風格透過 project reactor 實作。但是,在先前的版本中,我們總是對使用命令式風格實作的函數應用反應式轉換。例如,Function<Foo, Foo>
會變成 Function<Flux<Foo>, Flux<Foo>>
。在此版本中,情況不再如此。以命令式方式實作的函數可以按原樣 (命令式) 或作為反應式來查找和呼叫。例如,假設以下組態
@Bean
public Function<String, String> uppercase() {
return v -> v.toUpperCase();
}
您可以按照編寫的方式存取此函數
Function<String, String> function = functionCatalog.lookup("uppercase");
或作為反應式等效項
Function<Flux<String>, Flux<String>> reactiveFunction = functionCatalog.lookup("uppercase");
Spring Cloud Function 會自動調整。
此里程碑版本帶來的新功能之一是在函數核心進行透明型別轉換,因此雖然其中一些已經存在於 Web 配接器中,但現在它可以在函數呼叫層級使用,允許任何類型的函數使用者 (而不僅僅是 Web) 從中受益。當組合函數時,此功能的主要優點之一得以實現 (有關此內容的更多資訊,請參閱下文)。例如,假設以下函數:Function<Foo, Foo> foo()
和 Function<Bar, Bar> bar()
組合為 foo|bar
。雖然它在先前的版本中由於一個的輸出和另一個的輸入之間的型別不相容而無法運作,但現在支援它,前提是提供了適當的轉換策略。此類轉換策略是標準 Spring 的 ConversionService
和 MessageConverters
。雖然我們仍在完善此功能並提供詳細文件,但適用於大多數情況 (例如,JSON) 的 ConversionService
和 MessageConverters
預設已初始化。
例如,假設以下函數組態
@Bean
public Function<Person, Person> uppercasePerson() {
return person -> {
return new Person(person.getName().toUpperCase(), person.getId());
};
}
為了從 MessageConverters
中受益,我們可以將此函數呼叫為 Function<Message<String>, Person>
(或 byte[] 作為有效負載),從而採用可用的 JSON MessageConverter
將 String
轉換為 Person
(請參閱下文)。
Function<Message<String>, Person> uppercasePerson = catalog.lookup("uppercasePerson");
Person person = uppercasePerson.apply(MessageBuilder.withPayload("{\"name\":\"bill\",\"id\":2}").build());
請記住,對於使用反應式風格編寫的函數,沒有任何改變,並且應用了相同的轉換策略。
雖然函數組合對於 Spring Cloud Function 來說不是一個新功能,但它在此里程碑版本中得到了改進。
與之前一樣,您可以透過 "|" 或 "," 字元組合函數。
作為額外的好處,您可以將具有不同程式設計風格 (例如,反應式和命令式) 的函數組合在一起,您可以將 Supplier 與 Function、Supplier 與 Consumer、Function 與 Consumer 等組合在一起 - 我們將進行調整。您可以組合生產者函數的輸出與消費者函數的輸入不符的函數 - 我們將進行轉換。未來將會有一篇關於此主題的單獨部落格文章,我們也正在完善文件。
與往常一樣,我們歡迎回饋和貢獻,因此請透過 Stackoverflow 或 GitHub 與我們聯繫。