Ocasionalmente, a transferência de recursos é extremamente lenta com o Tomcat no AWS EC2

5

Eu tenho uma instância Tomcat v9 em execução em um contêiner do Docker em um host do AWS EC2 .
Funciona perfeitamente na maior parte do tempo e, de vez em quando, fornece recursos muito lentamente .

O que exatamente é servido lentamente e o que é "lento"?

Estou falando de ambos os arquivos estáticos simples fora de qualquer WAR , mas também - e mais irritantemente, respostas de servlet .

Eu testemunho alguns 300 a 400KB recursos servidos em 5 a 12s , onde eles geralmente (95% + do tempo) chegam em ~ 300ms .

Veja um exemplo de qual guia Rede do Chrome informa sobre essas transferências de recursos bem-sucedidas:


319KBem12.02s


278KBem5.37s

Eunãotenhoideiadoquecausaisso.Eulimuitostópicosetenteimuitasconfigurações,masaindanãoconsigoentenderoqueestáacontecendo.

DedentrodomeuVPC

Comoo@Timsugeriu,tenteicolocaroclientedentrodomeuAWSVPCparaexcluirlatênciaderedeelarguradebandacomoacausadoproblema.

Nestaconfiguração,receborespostas"muito mais lentas", com um tempo de download de conteúdo ~ 600 ms onde às vezes pode ser apenas 200 ms no "mundo exterior".
Eu ainda noto os picos lentos que são um problema para mim, mas em vez de ir por dezenas de vezes o mínimo, duração de download "normal", sobe apenas cerca de 2,5s no máximo.

Response size       | 319 KB
------------------------------
Waiting (TTFB)      | ​99.00 ms
Content Download    | 2.81 s

O tempo de "espera" é o mesmo, como esperado, pois representa o tempo gasto pelo meu servlet para tratar a solicitação antes de começar a responder.

Meu ambiente (s)

Eu repliquei esse fenômeno com as seguintes configurações de ambiente:

No AWS linux AMI t2.medium

  • Tomcat v9 SEM Docker
  • Tomcat v9 com o Docker
  • Tomcat v8.5 com o Docker
  • Tomcat v8.0 com o Docker

Tomcat v9 com Docker em:

  • AWS linux AMI t2.micro
  • AWS linux AMI t2.medium
  • AWS linux AMI m4.xlarge

No AWS linux AMI t2.medium via ECS

  • Tomcat v9 com Docker

Pelo menos metade destes testes são provavelmente estúpidos, mas bem ... melhor informação em excesso do que muito pouco.

O que eu acho que posso excluir depois disso:

  • minha instância é muito pequena (falha com m4.xlarge )
  • As novas versões do Tomcat de alguma forma lidam com as coisas de maneira diferente
  • sobrecarga do contêiner do Docker atrapalhando as coisas

Minha configuração do Tomcat

Tudo bem, deve vir de lá, certo? Então, aqui está:

<?xml version="1.0" encoding="UTF-8"?>
<Server port="8005" shutdown="SHUTDOWN">
    <Listener className="org.apache.catalina.startup.VersionLoggerListener" />
    <Listener className="org.apache.catalina.core.JreMemoryLeakPreventionListener" />
    <Listener className="org.apache.catalina.mbeans.GlobalResourcesLifecycleListener" />
    <Listener className="org.apache.catalina.core.ThreadLocalLeakPreventionListener" />

    <Service name="Catalina">
        <Connector port="8009" protocol="AJP/1.3" redirectPort="8443" maxThreads="1500" />
        <Connector port="8080" protocol="HTTP/1.1" connectionTimeout="20000" redirectPort="443" maxThreads="1500" />
        <Connector port="8443" protocol="org.apache.coyote.http11.Http11Nio2Protocol" sslImplementationName="org.apache.tomcat.util.net.jsse.JSSEImplementation" maxThreads="1500" SSLEnabled="true"
            scheme="https" secure="true" keystoreFile="/root/ssl/XXXXXXXX.jks" keystorePass="XXXXXXXX" clientAuth="false" sslProtocol="TLS" compression="on" compressionMinSize="1024"
            compressableMimeType="application/json" />

        <Engine name="Catalina" defaultHost="localhost">
            <Realm className="org.apache.catalina.realm.LockOutRealm">
                <Realm />
            </Realm>
            <Host name="localhost" appBase="webapps" unpackWARs="true" autoDeploy="true">
                <Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs" prefix="localhost_access_log." suffix=".txt" pattern="%h %l %u %t &quot;%r&quot; %s %b" />
            </Host>
        </Engine>
    </Service>
</Server>

É claro que o <Realm /> bit deve ser substituído por uma configuração real do JDBC Realm. Apenas apontando isso; não é o problema de qualquer maneira :) .

Como você pode ver, tentei aumentar o atributo maxThreads em todos os meus conectores, conforme mostrado em essa resposta . Nenhuma alteração.

Mais informações

Eu tenho uma coisa do JMX mostrando exatamente o que está acontecendo na minha JVM, eu uso VisualVM para visualizar tudo, mas, como você provavelmente pode imaginar como eu falo sobre isso, perto de nenhuma ideia para o que eu estou olhando.

Meus encadeamentos https-jsse-nio2-8443-exec-X , que são os únicos que parecem estar fazendo alguma coisa quando uma solicitação atinge o servidor, são indiferentes a solicitações "lentas" ou "normais". Mas, novamente, talvez eu simplesmente não veja isso.

Talvez você veja isso com :) , então aqui está uma captura de tela de VisualVM durante uma solicitação lenta:

Éapenas"estacionado" (cor laranja) e às vezes fica "em execução" (verde), mas apenas momentaneamente e não corresponde a solicitações "lentas" ou qualquer outra coisa. Talvez não haja nada para ver aqui.

Eu posso lhe fornecer lixões de threads e tudo que você precisa!

Minha pergunta real

O que posso alterar para ter uma taxa de transferência consistente e razoável ?

    
por ccjmne 21.11.2016 / 18:35

0 respostas