Desenvolvendo métrica personalizada para JBoss AS7/EAP6

Quem trabalha com Jboss AS7 e EAP6 sabe que é bem fácil de configurar um ambiente domain com um servidor web como o Apache usando Modcluster, o que é bem diferente de versões anteriores do Jboss que envolvia muita configuração e muito conhecimento.

Basicamente as configurações que necessitamos nessas versões do Jboss é definir qual métrica que define qual host deve receber ou não uma nova requisição, que são:

cpu
mem
heap
sessions
requests
send-traffic
receive-traffic
busyness
connection-pool

Por padrão a configuração é a “busyness” que é muito eficiente de um modo geral. Entretanto quando o sistema foge do trivial acabamos tendo situações específicas que não são identificadas através dessas métricas padrões e surge a necessidade de criar nossa própria métrica.

Esse é o caso de um sistema bancário que usa EAP6 e Apache como servidor web. Por um bom tempo ele trabalhou usando a métrica padrão do Jboss sem maiores problemas. Acontece que esse sistema possui processos que executam muito rápido e outros que são bem demorados e possuem transações grandes. Essas transações grandes acabam retendo uma conexão do pool com o Banco de Dados por muito tempo, mas isso não reflete expressivamente em consumo nos recursos da máquina como CPU e Memória. Nesse cenário muitas vezes um host recebia vários desses processos demorados, sobrecarregava o pool e mesmo assim continuava a receber novas requisições.

Diante disso a estratégia foi desenvolver uma métrica específica que valida o pool de conexão com o banco de dados e usar isso como fator para o balanceamento de carga. Esse será o exemplo que vou mostrar aqui.

Para criar sua própria métrica o processo é muito simples.

1) Crie um novo projeto Java e adicione as dependências do modcluster que ficam dentro dos modules do Jboss conforme imagem.

2) Feito isso basta criar uma classe que herda a classe org.jboss.modcluster.load.metric.impl.AbstractLoadMetric. Após isso implemente seu cálculo que será a métrica usada.

No exemplo abaixo vamos calcular a proporção de conexões em uso pela quantidade máxima disponível que será nossa métrica.

@Override
public double getLoad(Engine engine) throws Exception {

MBeanServer server = ManagementFactory.getPlatformMBeanServer();

try {

ObjectName datasourcePool = new ObjectName(“jboss.as:subsystem=datasources,data-source=MinhaAplicacaoDS,statistics=pool”);
ObjectName datasource = new ObjectName(“jboss.as:subsystem=datasources,data-source=MinhaAplicacaoDS”);
Integer inUseCount = (Integer) server.getAttribute(datasourcePool,”InUseCount”);
Integer maxPoolSize = (Integer) server.getAttribute(datasource,”max-pool-size”);
return inUseCount.doubleValue() / maxPoolSize.doubleValue();

} catch (InstanceNotFoundException e) {

return 0;

}

}

3) Com a implementação feita gere um JAR com essa classe e coloque na pasta das bibliotecas do modcluster (modules/system/layers/base/org/jboss/as/modcluster/main) e declare dentro do module.xml esse novo JAR, algo como:

<resources>

<resource-root path=”jboss-as-modcluster-7.2.1.Final-redhat-10.jar”/>
<resource-root path=”mod_cluster-container-spi-1.2.4.Final-redhat-1.jar”/>
<resource-root path=”mod_cluster-core-1.2.4.Final-redhat-1.jar”/>
<resource-root path=”mod_cluster-container-catalina-1.2.4.Final-redhat-1.jar”/>
<resource-root path=”mod_cluster-container-jbossweb-1.2.4.Final-redhat-1.jar”/>
<resource-root path=”datasource-metric.jar”/>
<!– Insert resources here –>

</resources>

4) Por último adicione essa nova estratégia em seu domain.xml no subsystem do modcluster:

<subsystem xmlns=”urn:jboss:domain:modcluster:1.1″>

<mod-cluster-config advertise-socket=”modcluster” proxy-list=”10.1.1.1:6666″ proxy-url=”10.1.1.1:6666″ balancer=”balancer01″ socket-timeout=”20″ sticky-session=”true” sticky-session-force=”false” worker-timeout=”-1″ max-attempts=”3″ flush-wait=”-1″ ttl=”-1″ node-timeout=”-1″ connector=”ajp”>

<dynamic-load-provider>

<load-metric type=”busyness”/>
<load-metric type=”cpu”/>
<custom-load-metric class=”br.com.evandropires.jboss.modcluster.metric.MyDSPoolMetric”/>

</dynamic-load-provider>

</mod-cluster-config>

</subsystem>

 Pronto. Sua nova métrica já está funcionando e sua aplicação estará balanceamento levando em consideração esse desenvolvimento. Você pode criar quantas métricas quiser e adicionar no modcluster. Ele vai usar todos em consideração.

Você pode ver o código fonte desse exemplo em: https://github.com/epiresdasilva/datasource-metric-modcluster

One thought on “Desenvolvendo métrica personalizada para JBoss AS7/EAP6

Deixe uma resposta