14.2.3 发送 即发即忘 消息

想象一下,您在一艘刚刚受到敌舰攻击的星际飞船上。您发出全舰范围的“红色警报”,以便所有人员都处于战斗模式。您不需要等待飞船计算机的响应来确认警报发送状态。在这种情况下,您也没有时间等待阅读任何回应。您设置了警报,然后继续执行更多关键操作。

这是一个 即发即忘 的例子。考虑到目前的情况,虽然您可能不会忘记您处于红色警戒状态。对您来说,应对这场战争危机比处理警报响应显然更重要。

为了模拟这个场景,我们将创建一个 RSocket 服务器,它处理警报状态,但不进行任何响应。首先,我们需要定义一个请求数据类。像清单 14.6 中的 Alert 类。

清单 14.6 表示警报的模型类。

package rsocket;

import java.time.Instant;

import lombok.AllArgsConstructor;
import lombok.Data;

@Data
@AllArgsConstructor
public class Alert {

  private Level level;
  private String orderedBy;
  private Instant orderedAt;

  public static enum Level {
    YELLOW, ORANGE, RED, BLACK
  }
}

警报对象捕获警报级别、警报的请求者以及警报发出时的时间戳(定义为 Instant 类型)。同样,为了保持代码简短,我们使用 Lombok 自动生成构造和访问方法。

在服务器端,清单 14.7 中的 AlertController 类将处理警报消息。

清单 14.7 处理警报更新的 RSocket 控制器。

package rsocket;
import org.springframework.messaging.handler.annotation.MessageMapping;
import org.springframework.stereotype.Controller;
import lombok.extern.slf4j.Slf4j;
import reactor.core.publisher.Mono;

@Controller
@Slf4j
public class AlertController {

  @MessageMapping("alert")
  public Mono<Void> setAlert(Mono<Alert> alertMono) {
    return alertMono
        .doOnNext(alert -> {
          log.info(alert.getLevel() + " alert"
          + " ordered by " + alert.getOrderedBy()
          + " at " + alert.getOrderedAt());
        })
        .thenEmpty(Mono.empty());
  }
}

setAlert() 方法处理“alert”路由上的消息。为保持简单(尽管在实际作战情况下毫无用处),它只记录警报。但重要的是返回一个Mono<Void>,表示没有响应。因此此处理方法支持 即发即忘 模型。

在客户端中,代码与 请求/响应请求/流 的代码差别不大:

RSocketRequester tcp = requesterBuilder.tcp("localhost", 7000);
tcp
  .route("alert")
  .data(new Alert(
    Alert.Level.RED, "Craig", Instant.now()))
  .send()
  .subscribe();
log.info("Alert sent");

但是,请注意,客户端没有调用 retrieveMono()retrieveFlux(),而只是调用 send(),不需要响应。

现在,让我们看看如何处理 通道 通信模型,在该模型中,服务器和客户端相互发送多条消息。

results matching ""

    No results matching ""