You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何将Mono<FilePart>转换为byte[]并将Excel文件存入MongoDB?

响应式编程实现Excel文件存储到MongoDB方案

1. 前置准备

首先确保项目已引入Spring Data MongoDB Reactive依赖,定义响应式仓库接口:

import org.springframework.data.mongodb.repository.ReactiveMongoRepository;
import org.springframework.stereotype.Repository;

@Repository
public interface ExcelRepository extends ReactiveMongoRepository<Excel, Integer> {
}

注意:实体类中的id属性若使用int类型需自行处理主键生成逻辑,建议改为Integer或MongoDB原生的ObjectId类型避免主键冲突;同时请为Excel类添加对应的getter、setter方法,保证属性可正常读写

2. 修正Controller层代码

原Controller返回值不符合响应式规范,需调整为返回Mono<HttpStatus>:

@PostMapping(path = "/file", consumes = MediaType.MULTIPART_FORM_DATA_VALUE,
            produces = MediaType.APPLICATION_STREAM_JSON_VALUE)
public Mono<HttpStatus> uploadFile(@RequestPart("files") Mono<FilePart> file) {
    return excelService.save(file);
}

3. 实现Service层存储逻辑

Service层返回值调整为Mono<HttpStatus>,核心逻辑是将FilePart的响应式数据流合并为字节数组,封装为实体后存入MongoDB:

import org.springframework.core.io.buffer.DataBuffer;
import org.springframework.core.io.buffer.DataBufferUtils;
import org.springframework.http.HttpStatus;
import org.springframework.stereotype.Service;
import reactor.core.publisher.Mono;

@Service
public class ExcelService {

    private final ExcelRepository excelRepository;

    // 构造注入Repository
    public ExcelService(ExcelRepository excelRepository) {
        this.excelRepository = excelRepository;
    }

    public Mono<HttpStatus> save(Mono<FilePart> filePartMono) {
        return filePartMono
                // 读取文件所有内容合并为单个DataBuffer
                .flatMap(filePart -> DataBufferUtils.join(filePart.content()))
                // 将DataBuffer转为字节数组
                .map(dataBuffer -> {
                    byte[] fileBytes = new byte[dataBuffer.readableByteCount()];
                    dataBuffer.read(fileBytes);
                    // 释放内存避免泄漏
                    DataBufferUtils.release(dataBuffer);
                    // 构建Excel实体
                    Excel excel = new Excel();
                    excel.setFile(fileBytes);
                    return excel;
                })
                // 调用响应式仓库保存数据
                .flatMap(excelRepository::save)
                // 保存成功返回201状态码
                .thenReturn(HttpStatus.CREATED)
                // 异常场景返回500状态码
                .onErrorReturn(HttpStatus.INTERNAL_SERVER_ERROR);
    }
}

补充说明

如果需要处理大于16MB的Excel文件,超出MongoDB单文档大小限制,不适合直接存byte数组,建议改用MongoDB GridFS实现响应式大文件存储。

内容的提问来源于stack exchange,提问作者Koni

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.28 10:36:03