文件异步导入及springboot MultipartFile 上传文件后@Async异步处理报错:NoSuchFileException

第一个问题

当excel中的数据量比较大时,java后台解析的过程可能要持续很久,但是又不需要用户去进行等待,这时就考虑文件的异步导入

文件异步方法的实现有着几种实现方式,这里是通过指定异步线程池实现的,即@Async(“线程池名称”)标注异步方法。

然而,在经过测试时发现,该标注的注解也都标注了,但是就是不能实现异步效果。

几经波折,发现异步方法可以调用非异步方法,是可以实现异步效果;而先是非异步方法去调用异步方法,这样就会失效。这里所说的是在同一个java类里面。

而在不同的java类里面,就不存在上面的问题

第二个问题
使用了异步方法,通过controller接收文件,service层进行处理,这时controller已经将执行成功的结果返回,剩下的就是service层中去进行解析入库,结果,万万没想到,在service中报了一个错

java.nio.file.NoSuchFileException: D:\UserData\Temp\undertow.1407321862395783323.8400\undertow4517937229384702645upload

Controller中的方法

@PostMapping("/test")
public R<String> test(MultipartFile file) {
	testService.test(file);
	return R.success("导入成功");
}

Service中的方法

@Async("asyncImportExecutor")
public void test(MultipartFile file) {
    try {
        EasyExcelUtil.read(file.getInputStream(), Test.class, this::executeImport)
                    .sheet().doRead();
    } catch (Exception ex) {
        log.error("[test]异步导入异常:", ex);
    }
}

看到这个异常NoSuchFileException后就一脸懵逼,测试是通过postman进行的,就开始怀疑postman的问题,已经排查后postman、路径啥的都没有问题,异步调用的流程也是ok的

然后就想这个异常的提示,就是找不到文件,根据打印出来的日志去本地也确实没有找到。后来就有了下面的写法

Controller中的方法

@PostMapping("/test")
public R<String> test(MultipartFile file) {
	try {
		testService.test(file.getInputStream());
	} catch (IOException e) {
		log.error("[test]异常日志:", e);
		return R.fail("导入失败");
	}
	return R.success("导入成功");
}

Service中的方法

@Async("asyncImportExecutor")
public void test(InputStream file) {
    try {
        EasyExcelUtil.read(file, Test.class, this::executeImport)
                    .sheet().doRead();
    } catch (Exception ex) {
        log.error("[test]异步导入异常:", ex);
    }
}

这样就不报错了。。。
后来就进行debug调试,发现临时文件是controller层中的MultipartFile对象生成,一直在写同步方法,也没注意这个MultipartFile对象会生成临时文件。后来发现这个controller中返回结果后,临时文件也就没有了。

错误总结:
因为使用的是异步方法,这样就会有一个主线程和一个异步线程。在上传文件后会形成MultipartFile类型的实例,同时生成临时文件,此时是在主线程中。MultipartFile的实例交给异步线程处理后,该临时文件会被springboot(spring)销毁,在异步线程中去getInputStream就会出现上面的异常。

而在下面的写法是将InputStream流作为了入参,就不会产生找不到文件的情况。

你可能感兴趣的:(spring,java,restful,spring)