Zip 支援

此 Spring Integration 模組提供了 Zip (解)壓縮支援。壓縮演算法實現基於 ZeroTurnaround ZIP Library。提供了以下元件:

你需要將此依賴項新增到你的專案中

  • Maven

  • Gradle

<dependency>
    <groupId>org.springframework.integration</groupId>
    <artifactId>spring-integration-zip</artifactId>
    <version>6.4.4</version>
</dependency>
compile "org.springframework.integration:spring-integration-zip:6.4.4"

名稱空間支援

Spring Integration Zip 模組中的所有元件都提供名稱空間支援。要啟用名稱空間支援,你需要匯入 Spring Integration Zip 模組的模式。以下示例展示了一個典型的設定:

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xmlns:int="http://www.springframework.org/schema/integration"
  xmlns:int-zip="http://www.springframework.org/schema/integration/zip"
  xsi:schemaLocation="http://www.springframework.org/schema/beans
    https://www.springframework.org/schema/beans/spring-beans.xsd
    http://www.springframework.org/schema/integration
    https://www.springframework.org/schema/integration/spring-integration.xsd
    http://www.springframework.org/schema/integration/zip
    https://www.springframework.org/schema/integration/zip/spring-integration-zip.xsd">
</beans>

(解)Zip 轉換器

ZipTransformer 為以下輸入 payload 型別實現了壓縮功能:FileStringbyte[]Iterable。輸入資料型別可以在 Iterable 中混合。例如,壓縮包含 String、位元組陣列和 File 的集合應該很容易。需要注意的是,目前不支援巢狀的 Iterables。

ZipTransformer 可以透過設定幾個屬性來定製

  • compressionLevel - 設定壓縮級別。預設值為 Deflater#DEFAULT_COMPRESSION

  • useFileAttributes - 指定是否應使用檔名作為 zip 條目名稱。

  • fileNameGenerator - 用於根據請求訊息生成原始檔名。預設為 DefaultFileNameGenerator.zip 副檔名會新增到此名稱中作為目標 zip 檔名,除非此生成器生成的結果已經包含該副檔名。

此外,可以提供 ZipHeaders.ZIP_ENTRY_FILE_NAMEZipHeaders.ZIP_ENTRY_LAST_MODIFIED_DATE 作為 zip 條目名稱及其 lastmodified 屬性。如果未提供,條目名稱將是 fileNameGenerator 的確切結果,而 lastmodified 將回退到當前日期和時間。如果請求訊息的 payload 是 Iterable,則此條目名稱將透過從 1 開始的索引進行修改。

例如,將一個簡單的 test.txt 檔案壓縮到 test.txt.zip 中,只需要以下配置就足夠了:

  • Java DSL

  • Kotlin DSL

  • Groovy DSL

  • Java

  • XML

@Bean
public IntegrationFlow zipFlow() {
    return IntegrationFlow
             .from("zipChannel")
             .transform(new ZipTransformer())
             .get();
}
@Bean
fun zipFlow() =
    integrationFlow("zipChannel") {
        transform(ZipTransformer())
    }
@Bean
zipFlow() {
    integrationFlow 'zipChannel',
            {
                transform new ZipTransformer()
            }
}
@Transformer(inputChannel = "zipChannel")
@Bean
ZipTransformer zipTransformer() {
    return new ZipTransformer();
}
<int-zip:zip-transformer input-channel="zipChannel"/>

有關更多資訊,請參閱 ZipTransformer Javadocs。

UnZipTransformer 支援以下輸入 payload 型別:Filebyte[]InputStream。解壓資料時,可以指定 expectSingleResult 屬性。如果設定為 true 並且檢測到超過 1 個 zip 條目,將丟擲 MessagingException。此屬性還會影響 payload 的返回型別。如果設定為 false(預設值),則 payload 型別將為 SortedMap;如果設定為 true,則將返回實際的 zip 條目。

可以在 UnZipTransformer 上設定的其他屬性:

  • deleteFiles - 如果 payload 是 File 例項,此屬性指定是否在轉換後刪除檔案。預設值為 false

  • ZipResultType - 定義轉換後返回的資料格式。可用選項有:Filebyte[]

  • workDirectory - 當 ZipResultType 設定為 ZipResultType.FILE 時使用的工作目錄。預設情況下,此屬性設定為系統臨時目錄中包含子目錄 ziptransformer 的路徑。

例如,將一個簡單的 test.zip 檔案解壓到其條目的 map 中,只需要以下配置就足夠了:

  • Java DSL

  • Kotlin DSL

  • Groovy DSL

  • Java

  • XML

@Bean
public IntegrationFlow unzipFlow() {
    return IntegrationFlow
             .from("unzipChannel")
             .transform(new UnZipTransformer())
             .get();
}
@Bean
fun unzipFlow() =
    integrationFlow("unzipChannel") {
        transform(UnZipTransformer())
    }
@Bean
unzipFlow() {
    integrationFlow 'unzipChannel',
            {
                transform new UnZipTransformer()
            }
}
@Transformer(inputChannel = "unzipChannel")
@Bean
UnZipTransformer unzipTransformer() {
    return new UnZipTransformer();
}
<int-zip:unzip-transformer input-channel="unzipChannel"/>

解壓分離器

UnZipResultSplitter 在 zip 檔案包含多個條目的情況下非常有用。它本質上必須在前面提到的 UnZipTransformer 之後用作整合流的下一步。它僅支援 Map 作為輸入資料,並將每個條目以包含 FileHeaders.FILENAMEZipHeaders.ZIP_ENTRY_PATH 頭部的方式傳送到 outputChannel

以下示例演示了用於分割解壓結果的簡單配置:

  • Java DSL

  • Kotlin DSL

  • Groovy DSL

  • Java

  • XML

@Bean
public IntegrationFlow unzipSplitFlow(Executor executor) {
    return IntegrationFlow
             .from("unzipChannel")
             .transform(new UnZipTransformer())
             .split(new UnZipResultSplitter())
             .channel(c -> c.executor("entriesChannel", executor))
             .get();
}
@Bean
fun unzipFlow(executor: Executor) =
    integrationFlow("unzipChannel") {
        transform(UnZipTransformer())
        split(UnZipResultSplitter())
        channel { executor("entriesChannel", executor) }
    }
@Bean
unzipFlow(Executor executor) {
    integrationFlow 'unzipChannel',
            {
                transformWith {
                    ref new UnZipTransformer()
                }
                splitWith {
                    ref new UnZipResultSplitter()
                }
                channel { executor 'entriesChannel', executor }
            }
}
@Transformer(inputChannel = "unzipChannel", outputChannel = "splitChannel")
@Bean
UnZipTransformer unzipTransformer() {
    return new UnZipTransformer();
}

@Spitter(inputChannel = "splitChannel", outputChannel = "entriesChannel")
@Bean
UnZipResultSplitter unZipSplitter() {
    return new UnZipResultSplitter();
}

@Bean
ExecutorChannel entriesChannel(Executor executor) {
    return new ExecutorChannel(executor);
}
<int:chain input-channel="unzipChannel" output-channel="entriesChannel">
    <int-zip:unzip-transformer/>
    <int:splitter>
        <bean class="org.springframework.integration.zip.splitter.UnZipResultSplitter"/>
    </int:splitter>
</int:chain>

<int:channel id="entriesChannel">
    <int:dispatcher task-executor="executor"/>
</int:channel>