Java 当我需要库函数的上下文和单响应时,如何重构嵌套的平面映射?

Java 当我需要库函数的上下文和单响应时,如何重构嵌套的平面映射?,java,rx-java2,spring-webflux,project-reactor,Java,Rx Java2,Spring Webflux,Project Reactor,我有一个反应式web应用程序(SpringWebFlux)通过Azure存储中的PostAPI存储用户配置文件图像。如果不存在,我需要为用户创建一个存储桶 服务层方法看起来是这样的:(它包含嵌套的平面图-这在反应式应用程序中被认为是一种不好的做法,而且是一种代码味道。)我想进行重构,这样就没有嵌套的平面图。有什么方法可以做到这一点吗 public Mono<BlockBlobItem> processAndUpload(FilePart filePart) { return

我有一个反应式web应用程序(SpringWebFlux)通过Azure存储中的PostAPI存储用户配置文件图像。如果不存在,我需要为用户创建一个存储桶

服务层方法看起来是这样的:(它包含嵌套的平面图-这在反应式应用程序中被认为是一种不好的做法,而且是一种代码味道。)我想进行重构,这样就没有嵌套的平面图。有什么方法可以做到这一点吗

public Mono<BlockBlobItem> processAndUpload(FilePart filePart) {

    return Mono.subscriberContext().flatMap(context -> {
      String userId = context.get(USER_ID_CONTEXT);
      BlobContainerAsyncClient blobContainerClient = blobServiceAsyncClient.getBlobContainerAsyncClient(userId);

      return blobContainerClient.exists()
          .doOnEach(logOnNext(doesContainerExist -> {
            if (doesContainerExist) {
              LOGGER.info(STORAGE_CONTAINER_EXISTS_MSG);
            } else {
              LOGGER.info(STORAGE_CONTAINER_DOES_NOT_EXIST_MSG);
            }
          }))
          .doOnEach(logOnError(err -> LOGGER.error(CONTAINER_CHECK_FAILURE_MSG, err.getMessage(), err)))
          .flatMap(doesContainerExist -> {
            if (doesContainerExist) {
              return uploadFile(filePart, blobContainerClient, userId);
            } else {
              return blobContainerClient.createWithResponse(null, null)
                  .doOnEach(logOnComplete(response -> LOGGER.info(CONTAINER_CREATION_SUCCESS_MSG)))
                  .doOnEach(logOnError(err -> LOGGER.error(CONTAINER_CREATION_FAILURE_MSG, err.getMessage(), err)))
                  .then(uploadFile(filePart, blobContainerClient, userId));
            }
          });
    });
  }

public Mono processAndUpload(FilePart FilePart){
返回Mono.subscriberContext().flatMap(上下文->{
字符串userId=context.get(USER\u ID\u context);
BlobContainerAsyncClient blobContainerClient=blobServiceAsyncClient.getBlobContainerAsyncClient(用户ID);
返回blobContainerClient.exists()
.doOnEach(logOnNext(doesContainerExist->{
如果(是否存在容器){
LOGGER.info(存储\容器\存在\消息);
}否则{
LOGGER.info(存储容器不存在消息);
}
}))
.doOnEach(logon错误(err->LOGGER.error(容器检查失败消息,err.getMessage(),err)))
.flatMap(doesContainerExist->{
如果(是否存在容器){
返回上传文件(filePart、blobContainerClient、userId);
}否则{
返回blobContainerClient.createWithResponse(null,null)
.doOnEach(logOnComplete(response->LOGGER.info(CONTAINER\u CREATION\u SUCCESS\u MSG)))
.doOnEach(logon错误(err->LOGGER.error(容器\u创建\u失败\u消息,err.getMessage(),err)))
.then(上传文件(filePart、blobContainerClient、userId));
}
});
});
}

我担心嵌套的
flatMap
是唯一的方法,只要您需要这两种上下文

如果您谈到重构,我会将lambda表达式(至少是它们的右边)移出方法以实现可读性。也可以考虑使用<代码> map 首先获得<代码>用户ID <代码>,只要你不需要最初的代码>上下文< /代码>。
public Mono<BlockBlobItem> processAndUpload(FilePart filePart) {

    return Mono.subscriberContext()
        .map(context -> context.get(USER_ID_CONTEXT))
        .flatMap(userId -> {
                var client = blobServiceAsyncClient.getBlobContainerAsyncClient(userId);
                return client.exists()
                    .doOnEach(logOnNext(doesContainerExistLambda))
                    .doOnEach(logOnError(errLambda))
                    .flatMap(doesExist -> existenceHandler(filePart, client, userId));
                }
        );
}
public Mono processAndUpload(FilePart FilePart){
返回Mono.subscriberContext()
.map(context->context.get(USER\u ID\u context))
.flatMap(用户ID->{
var client=blobServiceAsyncClient.getBlobContainerAsyncClient(userId);
返回client.exists()
.doOnEach(logOnNext(doesContainerExistLambda))
.doOnEach(logOnError(errLambda))
.flatMap(doesExist->existenceHandler(filePart、client、userId));
}
);
}
名为
doesContainerExistLambda
errLambda
existenceHandler
的方法和lambda表达式是根据您的需要和考虑进行更改的主题。代码片段的要点是强调可以移动到其他地方的内容