Мне удалось реализовать websocket с помощью Актеров Akka .На первом шаге определите актера, который будет обрабатывать сообщения
public class WebSocketActor extends AbstractActor {
private final ActorRef out;
@Inject
public WebSocketActor(ActorRef out) {
this.out = out;
}
@Override
public Receive createReceive() {
return receiveBuilder()
.match(String.class, message ->
out.tell("Sending message at " + LocalDateTime.now().toString(), self())
)
.build();
}
public static Props props(final ActorRef out) {
return Props.create(WebSocketActor.class, out);
}
}
Этот актер будет создан для каждого клиента.ActorRef out
отправит сообщение подключенному клиенту.В этом примере ответ отправляется клиенту на каждое строковое сообщение, переданное WebSocketActor
.
Теперь определите конечную точку API, чтобы открыть доступ к веб-сокету для клиентов.Определите ActorFlow, который будет создавать новый экземпляр актера при новом подключении
public WebSocket ws() {
return WebSocket.Text.accept(request -> ActorFlow.actorRef((out) -> WebSocketActor.props(out), actorSystem, materializer));
}
Согласно исходный код ActorFlow создает актеров с именем flowActor
.Таким образом, чтобы отправить сообщение в веб-сокеты где-нибудь в коде, мы можем найти актеров по их пути .Это будет транслировать сообщение всем подключенным клиентам
actorSystem.actorSelection("/user/*/flowActor").tell("Hello", ActorRef.noSender());
К сожалению, я не нашел простого способа изменить имя по умолчанию ActorFlow, но, возможно, этот ответ может помочь вам play-scala-akka-websockets-change-actor-path .
Также вы можете проверить проект play-java-websocket-example из примеров playframework.