ファイル受信した後、NASに保存。保存成功まではtempのファイル名。保存成功したら正式なファイル名に変更する。処理失敗したら、tempファイル名の末尾にyyyymmddhhmmssを付与したファイル名に変更

```java
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PostMapping;

import javax.servlet.http.HttpServletRequest;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.UUID;

@Controller
public class FileUploadController {

    private static final String NAS_DIRECTORY = "/path/to/nas"; // NASのディレクトリパスを指定

    @PostMapping("/upload")
    public ResponseEntity<String> handleFileUpload(HttpServletRequest request) {
        try {
　　　　    // try-with-resourcesを使ってInputStreamを処理
            try (InputStream inputStream = request.getInputStream()) {
                byte[] fileData = inputStream.readAllBytes();
                // fileDataの処理をここに書く
            } catch (IOException e) {
                // エラーハンドリング
                e.printStackTrace();
            }

            // Content-TypeとContent-Dispositionヘッダーを取得
            String contentType = request.getContentType();
            String contentDisposition = request.getHeader("Content-Disposition");

            // ファイル名を抽出
            String originalFileName = extractFileName(contentDisposition);
            String tempFileName = UUID.randomUUID().toString(); // 一時ファイル名を生成

            // 一時ファイルに保存
            Path tempFilePath = saveTempFile(fileData, tempFileName);

            // ファイルを連携先に送信
            sendFileToDestination(fileData, contentType, originalFileName);

            // 一時ファイルを正式なファイル名に変更
            Path finalFilePath = Paths.get(NAS_DIRECTORY, originalFileName);
            Files.move(tempFilePath, finalFilePath);

            return ResponseEntity.created(finalFilePath.toUri()).body("File uploaded and sent successfully: " + originalFileName);
        } catch (Exception e) {
            // 一時ファイル名の末尾にタイムスタンプを付与してリネーム
            handleFailedUpload(tempFilePath);
            return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body("Failed to upload file: " + e.getMessage());
        }
    }

    private Path saveTempFile(byte[] fileData, String tempFileName) throws IOException {
        Path tempFilePath = Paths.get(NAS_DIRECTORY, tempFileName);
        try (FileOutputStream fos = new FileOutputStream(tempFilePath.toFile())) {
            fos.write(fileData);
        }
        return tempFilePath;
    }

    private void handleFailedUpload(Path tempFilePath) {
        try {
            String timestamp = LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyyMMddHHmmss"));
            Path failedFilePath = Paths.get(tempFilePath.toString() + timestamp);
            Files.move(tempFilePath, failedFilePath);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    private void sendFileToDestination(byte[] fileData, String contentType, String fileName) throws IOException, InterruptedException {
        // 連携先のURL
        String destinationUrl = "http://example.com/destination";

        // HttpClientを使用してファイルを送信
        HttpClient client = HttpClient.newHttpClient();
        HttpRequest request = HttpRequest.newBuilder()
                .uri(URI.create(destinationUrl))
                .header("Content-Type", "multipart/form-data; boundary=----WebKitFormBoundary7MA4YWxkTrZu0gW")
                .POST(ofMimeMultipartData(fileData, contentType, fileName))
                .build();

        client.send(request, HttpResponse.BodyHandlers.ofString());
    }

    private HttpRequest.BodyPublisher ofMimeMultipartData(byte[] fileData, String contentType, String fileName) {
        var byteArrayOutputStream = new ByteArrayOutputStream();
        var writer = new PrintWriter(new OutputStreamWriter(byteArrayOutputStream, StandardCharsets.UTF_8), true);

        // バウンダリを設定
        String boundary = "----WebKitFormBoundary7MA4YWxkTrZu0gW";
        writer.append("--" + boundary).append("\r\n");
        writer.append("Content-Disposition: form-data; name=\"file\"; filename=\"" + fileName + "\"").append("\r\n");
        writer.append("Content-Type: " + contentType).append("\r\n");
        writer.append("\r\n").flush();
        try {
            byteArrayOutputStream.write(fileData);
        } catch (IOException e) {
            e.printStackTrace();
        }
        writer.append("\r\n").flush();
        writer.append("--" + boundary + "--").append("\r\n");

        return HttpRequest.BodyPublishers.ofByteArray(byteArrayOutputStream.toByteArray());
    }

    private String extractFileName(String contentDisposition) {
        if (contentDisposition != null) {
            String[] parts = contentDisposition.split(";");
            for (String part : parts) {
                if (part.trim().startsWith("filename")) {
                    return part.split("=")[1].trim().replace("\"", "");
                }
            }
        }
        return "unknown";
    }
}
```

## 設定

アップロードするファイルごとの最大サイズ 。デフォルトは「1MB」
spring.servlet.multipart.max-file-size
Multipartリクエスト全体の最大サイズを指定します。デフォルトは「10MB」
spring.servlet.multipart.max-request-size

```xml
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee 
                             http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"
         version="3.1">
    <context-param>
        <param-name>spring.servlet.multipart.max-file-size</param-name>
        <param-value>2MB</param-value>
    </context-param>
    <context-param>
        <param-name>spring.servlet.multipart.max-request-size</param-name>
        <param-value>2MB</param-value>
    </context-param>
</web-app>
```

## pom.xml

```xml
<dependencies>
    <!-- Spring Web MVC -->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>

    <!-- HTTP Client for Java 11 -->
    <dependency>
        <groupId>org.apache.httpcomponents.client5</groupId>
        <artifactId>httpclient5</artifactId>
    </dependency>
</dependencies>
```