SpringとApacheのFileUpload

SpringおよびApache FileUpload

1. 概要

Apache Commons File Upload Libraryは、multipart/form-dataコンテンツタイプを使用してHTTPプロトコル経由で大きなファイルをアップロードするのに役立ちます。

このクイックチュートリアルでは、Springと統合する方法を見ていきます。

2. Mavenの依存関係

ライブラリを使用するには、commons-fileuploadアーティファクトが必要です。


    commons-fileupload
    commons-fileupload
    1.3.3

最新バージョンはMaven Centralにあります。

3. 一度に転送

デモンストレーションの目的で、ファイルペイロードを使用してController処理要求を作成します。

@PostMapping("/upload")
public String handleUpload(HttpServletRequest request) throws Exception {
    boolean isMultipart = ServletFileUpload.isMultipartContent(request);

    DiskFileItemFactory factory = new DiskFileItemFactory();
    factory.setRepository(
      new File(System.getProperty("java.io.tmpdir")));
    factory.setSizeThreshold(
      DiskFileItemFactory.DEFAULT_SIZE_THRESHOLD);
    factory.setFileCleaningTracker(null);

    ServletFileUpload upload = new ServletFileUpload(factory);

    List items = upload.parseRequest(request);

    Iterator iter = items.iterator();
    while (iter.hasNext()) {
        FileItem item = iter.next();

        if (!item.isFormField()) {
            try (
              InputStream uploadedStream = item.getInputStream();
              OutputStream out = new FileOutputStream("file.mov");) {

                IOUtils.copy(uploadedStream, out);
            }
        }
    }
    return "success!";
}

最初は、ライブラリのServletFileUploadクラスにあるisMultipartContentメソッドを使用するwe need to check if the request contains a multipart content

デフォルトでは、Spring features aMultipartResolverthat we’ll need to disable to use this library.それ以外の場合は、Controller.に到達する前にリクエストのコンテンツを読み取ります

これは、application.propertiesファイルにこの構成を含めることで実現できます。

spring.http.multipart.enabled=false

これで、ファイルを保存するディレクトリ、ライブラリがディスクに書き込むことを決定するしきい値、およびリクエストの終了後にファイルを削除するかどうかを設定できます。

ライブラリは、_ takes the responsibility of the configuration for the file saving and cleaning. The _setRepositoryメソッドがターゲットディレクトリを設定するDiskFileItemFactoryクラスを提供します。デフォルトは、例に示されています。

次に、setSizeThresholdは最大ファイルサイズを設定します。

次に、setFileCleaningTrackerメソッドがあり、nullに設定すると、一時ファイルは変更されません。 By default, it deletes them after the request has finished

これで、実際のファイル処理に進むことができます。

まず、以前に作成したファクトリを含めて、ServletFileUploadを作成します。次に、リクエストの解析に進み、フォームフィールドのライブラリの主要な抽象化であるFileItemのリストを生成します。

これが通常のフォームフィールドではないことがわかっている場合は、InputStreamを抽出し、IOUtilsから便利なコピーメソッドを呼び出します(その他のオプションについては、thisを参照してください。 )sチュートリアル).

これで、必要なフォルダーにファイルが保存されました。 これは通常、ファイルに簡単にアクセスできるため、この状況を処理するためのより便利な方法ですが、時間/メモリの効率も最適ではありません。

次のセクションでは、ストリーミングAPIについて見ていきます。

4. ストリーミングAPI

ストリーミングAPIは使いやすく、一時的な場所にコピーしないだけで大きなファイルを処理するのに最適な方法です。

ServletFileUpload upload = new ServletFileUpload();
FileItemIterator iterStream = upload.getItemIterator(request);
while (iterStream.hasNext()) {
    FileItemStream item = iterStream.next();
    String name = item.getFieldName();
    InputStream stream = item.openStream();
    if (!item.isFormField()) {
        // Process the InputStream
    } else {
        String formFieldValue = Streams.asString(stream);
    }
}

前のコードスニペットでは、DiskFileItemFactoryが含まれなくなっていることがわかります。 これは、when using the streaming API, we don’t need itであるためです。

次に、フィールドを処理するために、ライブラリはFileItemIteratorを提供します。これは、nextメソッドを使用してリクエストからフィールドを抽出するまで何も読み取りません。

最後に、他のフォームフィールドの値を取得する方法を確認できます。

5. 結論

この記事では、SpringでApacheCommonsファイルアップロードライブラリを使用して大きなファイルをアップロードおよび処理する方法を確認しました。

いつものように、完全なソースコードはover at GitHubで見つけることができます。