Groovy DSL
Groovy DSL 是 Java DSL 的包裝器和擴充功能。我們在此追求的主要目標是使 Groovy 上的 Spring Integration 開發盡可能順暢和直接,並與現有的 Java DSL 和一些 Groovy 擴充功能或語言特定結構互通。此實作是 Groovy 支援 模組的一部分。
您開始使用所需的一切只是一個匯入:import static org.springframework.integration.groovy.dsl.IntegrationGroovyDsl.integrationFlow
- 一個包含 Groovy DSL 的過載工廠方法的類別。
對於作為 Lambda 的 IntegrationFlow
定義,我們通常不需要 Groovy 的任何其他東西,只需像這樣宣告一個 Bean
@Bean
IntegrationFlow oddFlow() {
{ IntegrationFlowDefinition flow ->
flow.handle(Object, { p, h -> 'odd' })
}
}
在這種情況下,Groovy 了解閉包應轉換為 IntegrationFlow
匿名實例,並且目標 Java DSL 處理器會將此建構正確地解析為 Java 物件。
作為上述建構的替代方案,並為了與下面說明的用例保持一致,spring-integration-groovy
模組提供了一個 Groovy 特定的 DSL,用於以建構器模式風格宣告整合流程
@Bean
flowLambda() {
integrationFlow {
filter String, { it == 'test' }, { id 'filterEndpoint' }
wireTap integrationFlow {
channel { queue 'wireTapChannel' }
}
delay {
messageGroupId 'delayGroup'
defaultDelay 100
}
transform {
transformer { it.toUpperCase() }
expectedType String
}
}
}
這樣的全域 integrationFlow()
函數預期在建構器樣式中使用閉包,用於 GroovyIntegrationFlowDefinition
(IntegrationFlowDefinition
的 Groovy 包裝器),並產生常規的 IntegrationFlow
Lambda 實作。請參閱下方更多過載的 integrationFlow()
變體。
許多其他情境需要從資料來源啟動 IntegrationFlow
(例如 JdbcPollingChannelAdapter
、JmsInboundGateway
或僅僅是現有的 MessageChannel
)。為此,Spring Integration Java DSL 提供了一個 IntegrationFlow
工廠,其中包含許多過載的 from()
方法。此工廠也可以在 Groovy 中使用
@Bean
flowFromSupplier() {
IntegrationFlow.fromSupplier({ 'bar' }) { e -> e.poller { p -> p.fixedDelay(10).maxMessagesPerPoll(1) } }
.channel({ c -> c.queue('fromSupplierQueue') } as Function)
.get()
}
但不幸的是,並非所有 from()
方法都與 Groovy 結構相容。為了解決這個問題,Spring Integration 在 IntegrationFlow
工廠周圍提供了一個 Groovy DSL 工廠。它以一組過載的 integrationFlow()
函數實作。搭配 GroovyIntegrationFlowDefinition
的消費者來宣告流程的其餘部分作為 IntegrationFlow
閉包,以重複使用上述經驗,並避免最後需要 get()
呼叫。例如
@Bean
functionFlow() {
integrationFlow Function<byte[], String>,
{ beanName 'functionGateway' },
{
transform {
transformer Transformers.objectToString()
id 'objectToStringTransformer'
}
transform {
transformer { it.toUpperCase() }
expectedType String
}
splitWith {
expectedType Message<?>
function { it.payload }
}
splitWith {
expectedType Object
id 'splitterEndpoint'
function { it }
}
resequence()
aggregate {
id 'aggregator'
outputProcessor { it.one }
}
}
}
@Bean
someFlow() {
integrationFlow ({ 'test' },
{
poller { it.trigger new OnlyOnceTrigger() }
id 'pollingSource'
})
{
log LoggingHandler.Level.WARN, 'test.category'
channel { queue 'pollerResultChannel' }
}
}