Почему сервер иногда не отправляет СОЕДИНЕННЫЙ кадр при высокой нагрузке (топать)? - PullRequest
0 голосов
/ 10 июля 2019

У меня есть такая настройка: внешнее приложение, написанное на Angular, использует ng-stompjs для подключения к микросервису Spring, используемому в качестве реле для подключения к кластеру RabbitMQ, расположенному в cloud-amqp .

Когда количество подключений мало (200-400), все работает нормально.Но когда недавно мы подошли к 1000 подключений, сервер неожиданно начал не отвечать с кадром CONNECTED.И что странно, это не удается не во всех случаях, но почти в каждой третьей попытке.

http-запрос проходит нормально и возвращает 101 код, после чего фрейм CONNECT успешно отправлен.Но тогда не возвращается ни СОЕДИНЕННЫЙ кадр, ни ошибок.Я ждал этого около 10 минут, но ничего не получил.

Уже установленные соединения работают отлично и доставляют все сообщения в ближайшее время.

Мы используем "Awesome Ape" план в облачном amqp, и под нагрузкой он использует только около 30% ресурсов, поэтому я думаю, что он не голодает.

В качестве ретранслятора веб-сокетов мы используем загрузочное приложение Spring, которое упаковано в докер и работает как три экземпляра на трех узлах кластера kubernetes, и они также не испытывают голода, как я вижу.

@SpringBootApplication
@EnableWebSocketMessageBroker
@EnableWebSocket
public class WsRelayApplication implements WebSocketMessageBrokerConfigurer {

    public static void main(String[] args) {
        SpringApplication.run(WsRelayApplication.class, args);
    }

    @Override
    public void registerStompEndpoints(StompEndpointRegistry registry) {
        registry.addEndpoint("/ws").setAllowedOrigins("*");
    }

    @Override
    public void configureMessageBroker(MessageBrokerRegistry registry) {
        registry.enableStompBrokerRelay("/exchange", "/topic")
                .setRelayHost(relayHost)
                .setRelayPort(relayPort)
                .setClientLogin(username)
                .setClientPasscode(password)
                .setSystemLogin(username)
                .setSystemPasscode(password)
                .setVirtualHost(relayVirtualHost);
    }
}

Журналы содержат два типа ошибок, но они также присутствуют при небольшой нагрузке.

o.s.w.s.s.s.DefaultHandshakeHandler : Handshake failed due to invalid Upgrade header: null

Я не знаю, почему я редко (только 5 таких ошибок в одном журнале экземпляра) получаю это, потому что у меня настроено ssl-завершение в nginx, как описано в этомвопрос: Spring WebSocket: рукопожатие не удалось из-за недопустимого заголовка обновления: null .

o.s.w.s.m.StompSubProtocolHandler : Failed to parse TextMessage payload=[SUBSCRIBE ..], byteCount=119, last=true] in session 28f8037f-194c-7f50-333f-cc19680ca8e1. Sending STOMP ERROR to client. java.lang.IllegalStateException: No decoder for session id '28f8037f-194c-7f50-333f-cc19680ca8e1'

Я не обращал на них внимания, потому что до этого момента все работало нормально, и мои небольшие попытки найти их источник не увенчались успехом.

У меня также много ошибок транспорта в информационном журнале:

INFO 1 --- [MessageBroker-1] o.s.w.s.c.WebSocketMessageBrokerStats : WebSocketSession[8 current WS(8)-HttpStream(0)-HttpPoll(0), 9073 total, 0 closed abnormally (0 connect failure, 0 send limit, 5113 transport error)], stompSubProtocol[processed CONNECT(9037)-CONNECTED(4511)-DISCONNECT(0)], stompBrokerRelay[4521 sessions, ReactorNettyTcpClient[reactor.netty.tcp.TcpClientDoOn@a7f0ab6] (available), processed CONNECT(9038)-CONNECTED(4518)-DISCONNECT(7367)], inboundChannel[pool size = 2, active threads = 0, queued tasks = 0, completed tasks = 572724], outboundChannelpool size = 2, active threads = 0, queued tasks = 0, completed tasks = 1403923], sockJsScheduler[pool size = 1, active threads = 1, queued tasks = 0, completed tasks = 46]

Я понятия не имею, что делать дальше, чтобы найти проблему.Любая помощь будет оценена.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...