Por que eu devo ler este artigo:

O artigo atualiza o leitor em relação às novas características do JBoss Application Server 7, demonstrando algumas diferenças entre as versões anteriores e exemplos de possíveis configurações, além de ressaltar suas principais inovações.

Neste artigo veremos as principais alterações do JBoss AS 7, principalmente em sua arquitetura e os modos Domain e Standalone. Em seguida, mostraremos os novos arquivos de configuração com exemplos, bem como a facilidade de uso de suas novas interfaces administrativas.


Guia do artigo:

O JBoss Application Server 7 é uma das primeiras plataformas de uma nova etapa de projetos da JBoss, que visam ambientes como Cloud, passando por pequenos dispositivos a grandes servidores. O JBoss AS 7 traz inúmeras inovações. Dentre elas podemos destacar uma incrível rapidez de aproximadamente 4 segundos na inicialização, baixíssimo consumo de recursos e serviços iniciados on-demand. Tudo isso é possível graças à nova arquitetura baseada em um kernel ainda mais modular, composto por JBoss Modules e o JBoss Modular Service Container (MSC).

Desde que a Red Hat adquiriu o JBoss em 2006, houve um grande avanço em relação a plataformas e projetos existentes na comunidade. O número de plataformas saltou de apenas uma, que representava o próprio application server, para oito, incluindo soluções para SOA, Portais, Regras e Cloud. Já o número de projetos cresceu de aproximadamente 20 para mais de 140 disponíveis na JBoss Community (www.jboss.org).

A Tecnologia da Informação mudou drasticamente nestes últimos anos. Se considerarmos hardware, por exemplo, é fato que existem muito mais celulares hoje em dia do que computadores. É possível encarar smartphones como computadores, pois sua capacidade de processamento e memória são incrivelmente altas. Hoje em dia é comum encontrarmos processadores em câmeras, Smartphones, Kindles, iPads, ou até mesmo em máquinas de café e geladeiras. Podemos dizer também que estes equipamentos são equivalentes a supercomputadores de 20 anos atrás, ou até mesmo desktops de 10 anos atrás, e ainda assim, muitos deles estão presentes em nossos bolsos. Estes tipos de dispositivos já estão aqui há algum tempo e vieram para ficar.

Desde o último ano, quando a Apple criou um segmento de mercado completamente novo, o iPad, já existe mais de 20 milhões deles por aí e a utilização de smartphones vem crescendo ainda mais. Em nossas casas, mais e mais dispositivos estão se conectando e se comunicando, desde XBox ou PlayStation 3, até aparelhos de TV e home theaters. Atualmente é comum armazenarmos informações em Cloud, como simples scores de um videogame ou até mesmo documentos usando serviços do Google, e isto tudo ocorre de forma natural. Sem falar das redes sociais estourando em nosso cotidiano, é notável que interagir neste mundo que vivemos se tornou muito mais fácil.

Caro leitor, antes de se questionar se este artigo é realmente sobre JBoss, dizemos que sim, e destacamos que Middleware ainda é vital. De uma forma ou de outra, Middleware é necessário e importante para que se obtenha sucesso ao implementar tais soluções. Quando falamos de Tablets, Smartphones, Cloud, SOA e Redes Sociais, podemos dizer que hoje é possível estar conectados o tempo todo e realizar tarefas como comprar um livro, ou até mesmo um carro, ler e-mails, acessar nossas agendas, ouvir nossas músicas preferidas de forma rápida e direta e compartilhar pensamentos com nossos seguidores quando bem entendermos. Características como segurança, gerenciamento de transações, mensageria, entre inúmeras outras que compõem um Middleware são importantes e obrigatórias, ainda mais nestes dispositivos.

o último JBoss World, Mark Little (Sr. Director Engineering), surpreendeu ao dizer que as pessoas devem parar de pensar que Middleware é apenas relevante para hardwares corporativos, pois existem muitos outros projetos onde middleware é importante em ambientes menores. Além disso, que será comum ver algum projeto ou plataforma JBoss rodando em qualquer tipo de hardware, não apenas em grandes servidores processando milhares de requisições por segundo.

O JBoss Application Server 7 é a primeira plataforma desta nova etapa, que traz inúmeras inovações, como rapidez na inicialização, baixíssimo consumo de recursos, serviços iniciando on-demand, entre tantas outras, pensando no que estamos vivendo hoje e o que poderá vir para amanhã, adaptando-se a ambientes nas nuvens com clusters elásticos ou até mesmo a dispositivos que cabem em nossos bolsos.

Este artigo apresenta os principais conceitos do JBoss AS 7 e faz uma introdução na forma de utilização de cada um deles.

Primeiros Passos no JBoss

O JBoss Application Server 7, ou simplesmente AS 7, é a mais nova versão do Servidor de Aplicação Java de código aberto mais utilizado por desenvolvedores de aplicações corporativas baseadas na plataforma Java EE. Como veremos ao longo do artigo, a nova versão teve seu núcleo totalmente remodelado para fornecer um servidor leve, modular, de fácil administração e melhor performance. Sem sombra de dúvidas, uma das características que mais se destaca nessa nova versão é a sua velocidade de inicialização.

Mais adiante, quando falarmos sobre o novo Kernel do AS 7, veremos maiores detalhes sobre o que torna o AS 7 tão performático. Outras melhorias incluem o novo modo de operação baseado em domínios de servidores de aplicação e as novas ferramentas de administração. Com um núcleo totalmente modular e otimizado para ambientes multiprocessados, o AS 7 leva aproximadamente três segundos para iniciar em um hardware comum encontrado em qualquer laptop pessoal utilizado nos dias de hoje.

Essa versão não possui um instalador automático. Para instalar o AS 7 basta fazer o download do pacote distribuído em formato compactado (ZIP ou TAR GZ) e extrai-lo em um diretório qualquer. Para baixar a última release do JBoss AS 7, acesse a página do projeto através da URL http://jboss.org/jbossas/downloads. A Figura 1 mostra a página de downloads com a última release disponível no momento da escrita deste artigo. O único pré-requisito para instalação é ter o JDK 6 com a variável de ambiente JAVA_HOME configurada.

Página de
    download do JBoss AS 7
Figura 1. Página de download do JBoss AS 7: http://jboss.org/jbossas/downloads.

No momento da edição deste artigo a última versão estável era a 7.0.2.Final. Esta versão fornece uma implementação 100% compatível com a especificação Java EE 6 Web Profile. A release mais recente é a 7.1.0.CR1b, que é uma versão chamada de release candidate, que antecede a versão final 7.1. A versão 7.1 do JBoss AS, por sua vez, promete ser 100% compatível com as especificações que compõem a plataforma Java EE 6.

Após baixar e extrair a distribuição do AS 7 é hora de testar nossa instalação. Para isso, executaremos três operações simples: start, stop e restart do servidor de aplicação. A partir de agora, faremos referência ao diretório raiz da instalação do JBoss AS como AS7_HOME. Assim, acesse o diretório AS7_HOME/bin e execute o script standalone.(sh|bat).

Como pode ser notado, existem duas versões para cada script fornecido pelo AS 7. Uma para a plataforma Linux (.sh):


      $ ./standalone.sh 

E outra para a plataforma Windows (.bat):

  > standalone.bat 

Após um breve instante o servidor é inicializado, como mostra a Figura 2. Vale destacar o tempo de inicialização em apenas 3847ms, ou 3.8 segundos, em que 130 serviços foram iniciados, de um total de 200. Outros 68 serviços irão subir on-demand. Além disso, um processo Java de uma instância do JBoss AS 7, sem nenhuma aplicação deployada, consome aproximadamente 130Mb de memória (veja a Figura 3).

Uma inicialização rápida e o baixo consumo de memória abrem diversas possibilidades, como executar o container Java EE em um teste unitário. Outra possibilidade seria utilizar apenas uma JVM com o Application Server por aplicação, tornando a manutenção de aplicações independente. Desta forma, caso seja necessário parar o servidor, teríamos impacto apenas em uma aplicação.

Outra vantagem é executar o JBoss AS 7 em diversos ambientes como cloud, pois caso surja uma grande demanda de acessos, um novo servidor poderá ser iniciado de forma extremamente rápida. Com o baixo consumo de memória, quem sabe até mesmo rodar o JBoss AS 7 em ambientes portáteis, como smartphones ou tablets. Já para ambientes comuns como de desenvolvimento, se for necessário parar o servidor por algum motivo qualquer, você poderá inicializá-lo em poucos segundos, aumentando sua produtividade.

Além de todas estas vantagens, ainda torna-se extremamente fácil rodar diversas instâncias em seu próprio laptop.

Para verificar se o JBoss AS 7 está iniciado, uma forma seria acessar sua página de boas vindas. Assim, acesse a página de boas vindas com a URL http://localhost:8080 em seu navegador, como mostra a Figura 4.

Terminal com
    o tempo de inicialização
Figura 2. Terminal com o tempo de inicialização.
Terminal com
    o tempo de inicialização
Figura 3. System Monitor mostrando o processo Java do JBoss AS 7.
AS 7 – Página de boas vindas
Figura 4. AS 7 – Página de boas vindas.

O AS 7 disponibiliza duas novas formas de gerenciamento. Uma delas é a Command Line Interface (ou CLI), que possibilita visualizar e modificar atributos e executar operações utilizando um terminal. Dentre as inúmeras operações, é possível parar e reiniciar o servidor. Para acessar a CLI, execute o script AS7_HOME/bin/jboss-admin.(sh|bat).


      ./jboss-admin.sh 

Dentro da CLI, digite o comando connect para se conectar à instância local em execução. Em seguida, digite :shutdown. Com isto, o servidor será desligado. A Figura 5 mostra a operação de shutdown do AS 7 usando a CLI.

Shutdown do servidor através da CLI
Figura 5. Shutdown do servidor através da CLI.

Para reiniciar a instância local do servidor, basta digitar o comando :reload.

Além da CLI, o AS 7 fornece também a Web Management Console, ou simplesmente console web, que nada mais é que uma interface web para gerenciamento e execução de operações. No próximo artigo desta série veremos mais detalhes sobre o gerenciamento do servidor através da CLI e console web.

Estrutura de diretórios

A distribuição do AS 7 está organizada em uma estrutura de diretórios bem diferente das versões anteriores. A Figura 6 mostra como essa nova estrutura é composta. Veja a seguir mais detalhes sobre cada um dos diretórios:

  • appclient: contém a configuração de um Application Client Container – ACC. Trata-se de um container pré-configurado usado quando se deseja acessar recursos Java EE remotos (EJB, Filas JMS, etc.) a partir de aplicações standalone (aplicação Desktop Swing);
  • bin: contém vários scripts para manutenção e gerenciamento da instalação do servidor de aplicação, que estão disponíveis para as plataformas Linux (.sh) e Windows (.bat). Também são fornecidos scripts utilitários, como por exemplo, para acesso à CLI;
  • bundles: contém os bundles (serviços) OSGi que fazem parte do subsistema OSGi fornecido pelo AS 7. Como veremos mais adiante, o AS 7 fornece suporte ao deployment de bundles OSGi;
  • docs: ao contrário do que parece, não contém a documentação do servidor de aplicação. A documentação oficial está disponível online no site do JBoss AS. Este diretório é dividido três subdiretórios:
  • examples: contém alguns exemplos de configuração de profiles (conjunto de subsistemas) específicos;
  • licenses: contém as licenças de todas as tecnologias que compõem o servidor de aplicação;
  • schema: contém os arquivos XML Schema que definem os diversos descritores utilizados na configuração do servidor. Bastante útil tanto para referência como para uso em uma IDE.
  • domain: contém os arquivos de configuração, bem como toda a estrutura necessária para execução do servidor em modo Domain. O diretório domain é composto por vários subdiretórios. O primeiro deles é o configuration, que armazena os descritores domain.xml e host.xml – veremos detalhes dessa configuração mais adiante, quando falarmos sobre domínios. Após a primeira inicialização temos o diretório content, que armazena os deployments realizados no domínio. O diretório log armazena os logs dos processos que compõem o domínio (process-controller e host-controller) – também veremos detalhes sobre estes processos em breve. O diretório servers hospeda a estrutura individual de cada instância do servidor (server nodes) configurada no host para fazer parte do domínio. Cada server node possui seu próprio log (diretório log), bem como seus próprios arquivos de dados (diretório data) e temporários (diretório tmp). Por último, temos o subdiretório tmp, que armazena alguns artefatos temporários gerados em tempo de execução pelos processos do domínio. Como veremos mais adiante, o modo Domain é uma das grandes novidades no AS 7;
  • modules: contém todos os módulos e extensões que compõem o núcleo do AS 7, bem como os serviços fornecidos pelo servidor de aplicação. Como veremos mais adiante, o AS 7 é composto por diversos módulos;
  • standalone: contém os arquivos de configuração necessários para executar o servidor em modo isolado. Esse diretório é semelhante aos profiles (all, default e minimal) encontrados em versões anteriores do JBoss AS. O diretório standalone também é composto por vários subdiretórios. O primeiro deles é o configuration, que armazena o descritor standalone.xml que define o conjunto de subsistemas (profile) a ser inicializado pela instância do servidor em modo standalone. O diretório deployments armazena os pacotes (WAR, EAR, JAR, SAR) implantados no servidor. O diretório lib é usado para armazenar bibliotecas e extensões do servidor de aplicação. Por fim, após a primeira inicialização, são criados os diretórios data, log e tmp, que armazenam, respectivamente, arquivos de dados, log de saída e arquivos temporários gerados em tempo de execução;
  • welcome-content: contém a página de boas-vindas do AS 7. É o contexto raiz (http://localhost:8080/) do container web do servidor.

Após instalarmos o JBoss AS 7 e realizarmos um tour inicial em sua estrutura de diretórios, vamos conhecer alguns detalhes e novidades desta versão.

JBoss AS 7 – Estrutura de Diretórios
Figura 6. JBoss AS 7 – Estrutura de Diretórios.

Modos de Operação

AS 7 possui dois modos de operação: Standalone e Domain. O que os diferencia basicamente é a execução e o gerenciamento. Como o próprio nome diz, Standalone significa uma única instância de execução. Já o modo Domain permite a execução distribuída e o gerenciamento centralizado de múltiplas instâncias.

Estes dois modos não existiam nas versões anteriores do JBoss AS, portanto, havia apenas uma única forma de iniciar uma nova instância do servidor, que se parecia muito com o modo Standalone do AS 7. Esta instância era baseada em um profile, que nada mais é do que um conjunto de recursos e serviços fornecidos pelo Servidor de Aplicação devidamente configurado e pronto para uso. Um profile define as características, bem como as capacidades oferecidas por uma instância de execução do servidor.

Como exemplo podemos citar um profile especializado na camada web, que oferece a configuração necessária para o deployment e execução de aplicações utilizando JSP, Servlet, JSF, CDI, JPA, etc. Outro exemplo seria um profile que traz todo o arsenal necessário para desenvolver qualquer aplicação Java EE, como suporte a objetos distribuídos, EJB, Remoting, JNDI, Mensageria, entre outras coisas que fazem parte desta especificação.

Estes profiles eram definidos em vários arquivos de configuração organizados em diretórios específicos (all, default, minimal, web e standard). Desta forma, os serviços fornecidos eram declarados em diversos pontos da estrutura de diretórios do JBoss AS, fazendo com que as configurações ficassem espalhadas. Até a versão 4, que utilizava um Microkernel JMX, os serviços eram declarados como MBeans (veja a Listagem 1). A partir da versão 5, o Microkernel foi substituído e o JBoss AS passou a utilizar um Microcontainer baseado em AOP com serviços definidos como Pojo Beans (veja a Listagem 2).

Nesta nova versão do JBoss Application Server, o AS 7, tais configurações estão disponíveis de forma unificada e os profiles são definidos nos arquivos de configuração standalone.xml e domain.xml, os quais iremos descrever a seguir.

Listagem 1. MBean ThreadPool definido no arquivo jboss-service.xml do JBoss AS 4.

      <!-- A Thread pool service -->
      <mbean code="org.jboss.util.threadpool.BasicThreadPool"
        name="jboss.system:service=ThreadPool">
        <attribute name="Name">JBoss System Threads</attribute>
        <attribute name="ThreadGroupName">System Threads</attribute>
        <!-- How long a thread will live without any tasks in MS -->
        <attribute name="KeepAliveTime">60000</attribute>
        <!-- The max number of threads in the pool -->
        <attribute name="MaximumPoolSize">10</attribute>
        <!-- The max number of tasks before the queue is full -->
        <attribute name="MaximumQueueSize">1000</attribute>
        <!-- The behavior of the pool when a task is added and the queue is full. -->
        <attribute name="BlockingMode">run</attribute>
      </mbean> 
Listagem 2. Pojo Bean ProfileService definido no arquivo profile.xml do JBoss AS 5.

      <!-- The ProfileService -->
      <bean name="ProfileService"   class="org.jboss.system.server.profileservice.repository.AbstractProfileService">
        <constructor>
          <parameter><inject bean="jboss.kernel:service=KernelController" /></parameter>
        </constructor>
        <property name="deployer"><inject bean="ProfileServiceDeployer" /></property>
        <property name="defaultProfile"><inject bean="DefaultProfileKey" /></property>
      </bean> 

Modo Standalone

O modo Standalone é muito semelhante aos profiles default, all e minimal das versões anteriores. Ao utilizá-lo será iniciada apenas uma instância de AS 7 por script de inicialização (no caso, standalone.sh). Este modo pode pertencer a ambientes que necessitam de apenas uma instância do JBoss AS 7, ou em aplicações que não requeiram gerenciamento unificado.

Embora seja possível formar um cluster de alta disponibilidade utilizando várias instâncias em modo standalone, não será possível ter este ponto único de gerenciamento, portanto, a administração de cada nó é feita de forma isolada e repetitiva. O deploy de uma aplicação, por exemplo, deve ser feita em todos os nós do cluster.

No AS 7 os serviços são chamados de subsistemas, e no modo Standalone estes serviços estão configurados em um único arquivo denominado standalone.xml, localizado no diretório AS7_HOME/standalone/configuration. Desta forma, torna-se muito mais fácil qualquer tipo de manutenção ou configuração em qualquer um dos subsistemas. A Listagem 3 mostra a definição do subsistema de logging.

Diferente do esquema de configuração distribuída em vários arquivos, encontrado nas versões anteriores, standalone.xml (veja a Listagem 4) contém toda a configuração necessária para a inicialização do servidor: módulos, subsistemas, interfaces de gerenciamento, segurança, data sources, socket bindings, etc. Assim, quando quiser fazer qualquer tipo de alteração, basta olhar apenas este arquivo.

Para facilitar o entendimento, a Figura 7 traz todos os elementos que podem ser configurados em um arquivo standalone.xml. Para mais detalhes sobre o que pode ser definido neste descritor, consulte o XML Schema localizado na distribuição do AS 7 em AS7_HOME/docs/schema/jboss-as-config_1_1.xsd.

Listagem 3. Subsistema de logging definido no arquivo standalone.xml do JBoss AS 7.

      <subsystem xmlns="urn:jboss:domain:logging:1.1">
        <console-handler name="CONSOLE">
          <level name="INFO"/>
          <formatter>
            <pattern-formatter pattern="%d{HH:mm:ss,SSS} %-5p [%c] (%t) %s%E%n"/>
          </formatter>
        </console-handler>
       
        <periodic-rotating-file-handler name="FILE">
          <formatter>
            <pattern-formatter pattern="%d{HH:mm:ss,SSS} %-5p [%c] (%t) %s%E%n"/>
          </formatter>
          <file relative-to="jboss.server.log.dir" path="server.log"/>
          <suffix value=".yyyy-MM-dd"/>
          <append value="true"/>
        </periodic-rotating-file-handler>
       
        <logger category="com.arjuna">
          <level name="WARN"/>
        </logger>
        <logger category="org.apache.tomcat.util.modeler">
          <level name="WARN"/>
        </logger>
        <logger category="sun.rmi">
          <level name="WARN"/>
        </logger>
        <logger category="jacorb">
          <level name="WARN"/>
        </logger>
        <logger category="jacorb.config">
          <level name="ERROR"/>
        </logger>
       
        <root-logger>
          <level name="INFO"/>
          <handlers>
            <handler name="CONSOLE"/>
            <handler name="FILE"/>
          </handlers>
        </root-logger>
      </subsystem> 
Listagem 4. Descritor AS7_HOME/standalone/configuration/standalone.xml. Modo de execução Standalone.

      <server xmlns="urn:jboss:domain:1.1">
          <extensions>
              <extension module="org.jboss.as.clustering.infinispan"/>
              <extension module="org.jboss.as.connector"/>
              ...
          <extensions>
       
          <management>
              <security-realms>
                  <security-realm name="ManagementRealm">
                  ...
              </security-realms>
              <management-interfaces>
                 ...
              <management-interfaces>
          <management>
          ...
          <profile>
              <subsystem xmlns="urn:jboss:domain:logging:1.1">
                 ...
              <subsystem xmlns="urn:jboss:domain:datasources:1.0">
                 ...
              <subsystem xmlns="urn:jboss:domain:deployment-scanner:1.0">
                 ...
          </profile>
       
          <socket-binding-group name="standard-sockets" default-interface="public" port-offset="${jboss.socket.binding.port-offset:0}">
              <socket-binding name="http" port="8080"/>
              <socket-binding name="https" port="8443"/>
              ...
          <socket-binding-group>
      </server> 
Macro esquema do descritor standalone.xml
Figura 7. Macro esquema do descritor standalone.xml.

Para iniciar o AS 7 em modo standalone basta executar o script standalone.(sh|bat) disponível para ambientes Linux ou Windows, no diretório AS7_HOME/bin.


      $ ./standalone.sh 

Por padrão, o script acima inicia o AS 7 utilizando o descritor standalone.xml. A Figura 8 mostra a saída do console durante a inicialização do servidor neste modo.

Startup do AS 7 em modo Standalone
Figura 8. Startup do AS 7 em modo Standalone.

Além do arquivo de configuração standalone.xml, o AS 7 disponibiliza mais dois arquivos com profiles pré-definidos: standalone-full.xml, com subsistemas adicionais habilitados (Messaging, CORBA/IIOP, CMP, entre outros); e standalone-ha.xml, com suporte a cluster. Assim como standalone.xml, estes dois arquivos também estão localizados em AS7_HOME/standalone/configurations. Para iniciar o AS com uma configuração específica, utilize o parâmetro -c <nome do arquivo>. Por exemplo, para iniciar uma instância standalone com suporte a cluster, entre no diretório AS7_HOME/bin e execute o comando:


      $ ./standalone.sh -c standalone-ha.xml 

Existem vários outros parâmetros que podem ser utilizados na inicialização do servidor. Para verificar a lista completa, execute o script com o parâmetro --help:


      $ ./standalone.sh --help 

Como veremos mais adiante, tudo o que se define nesse descritor pode ser visualizado e manipulado através das novas interfaces de gerência fornecidas pelo AS 7.

Modo Domain

Esta é sem dúvida umas das principais novidades do AS 7. A possibilidade de iniciar várias instâncias, bem como gerenciá-las de forma centralizada em um ponto único, traz benefícios notáveis para o administrador do Application Server.

Basicamente um domínio pode ser interpretado como uma unidade administrativa. Um conjunto de instâncias do servidor de aplicação que compartilham configurações comuns e que são coordenadas por um ponto central – o Domain Controller.

Em versões anteriores do JBoss AS, caso o administrador quisesse iniciar várias instâncias com exatamente as mesmas configurações, era necessário realizar cópias do diretório referente ao profile utilizado para cada instância. Por exemplo, caso fosse necessário iniciar três instâncias do profile default, era necessário copiar o diretório deste profile três vezes (default-1, default-2 e default-3) e iniciar três processos da JVM utilizando o script run.sh:


      $ ./run.sh -c default-1 -Djboss.service.binding.set=ports-01
      $ ./run.sh -c default-2 -Djboss.service.binding.set=ports-02
      $ ./run.sh -c default-3 -Djboss.service.binding.set=ports-03 

Também não era possível compartilhar e nem gerenciar as configurações das três instâncias de forma centralizada, dificultando a manutenção e criação de novas instâncias. Era preciso replicar a mesma configuração em vários pontos manualmente ou usando alguma ferramenta externa ao servidor de aplicação, como o RHQ ou sua versão Enterprise, chamada JBoss Operations Network (JON). Qualquer alteração feita em uma das instâncias teria que ser copiada para as outras, tornando a manutenção em grandes parques de servidores muito tediosa. É para lidar com esse tipo de situação que o modo Domain, implementado no AS 7, se aplica.

Antes de prosseguirmos com a descrição do modo Domain, é importante termos em mente que um domínio NÃO é necessariamente um Cluster de Servidores de Aplicação. Embora possa ser utilizado para gerenciar servidores em cluster, o modo Domain não tem nenhuma relação com as características fornecidas por um cluster (alta disponibilidade e balanceamento de carga). O termo domínio está associado ao conceito de gerenciamento de um conjunto de servidores de aplicação. A principal vantagem de se utilizar o AS 7 em modo Domain é a possibilidade de gerenciar configurações e deploys a partir de um ponto central.

A melhor forma de compreender a estrutura lógica de um domínio é visualizar seus elementos como processos em execução. Estruturalmente, um domínio é composto por quatro elementos:

  • Domain controller: é o ponto central de controle e mantém toda a política de gerenciamento do domínio. Ele hospeda a configuração do AS e a compartilha com todas as outras instâncias que fazem parte do mesmo domínio;
  • Host controller: é responsável por coordenar, juntamente com o Domain Controller, todo o ciclo de vida (start/stop) das instâncias que fazem parte do domínio, além de executar o trabalho de distribuir os deploys em todas elas;
  • Process controller: é responsável por criar as instâncias do servidor, inclusive a instância do host controller. É sua função também gerenciar os fluxos de entrada e saída das instâncias do servidor. O fato deste processo estar em uma JVM isolada permite que o host controller seja atualizado e, até mesmo, reiniciado sem impactar nas demais instâncias do domínio;
  • Server nodes: são as instâncias propriamente ditas, onde as aplicações e serviços são implantadas. Cada server node terá seu próprio processo Java no sistema operacional.

Quando se inicia o AS em modo Domain no mínimo três processos Java (JVM) são criados no sistema operacional: um Host Controller (que também pode agir como Domain Controller no mesmo processo), um Process Controller e um Server Node. Relatamos no mínimo três porque dependendo da configuração definida o domínio pode possuir três ou mais processos executando em um mesmo host (físico ou virtual). A configuração padrão do modo Domain fornecida pelo AS 7 é composta pela topologia mostrada na Figura 9. Observe que nesta estrutura tanto o Host Controller quanto o Domain Controller executam em um mesmo processo Java.

Domínio
    padrão do AS 7
Figura 9. Domínio padrão do AS 7.

Para iniciar o AS 7 em modo Domain com a configuração padrão (AS7_HOME/domain/configuration/domain.xml), basta executar o script domain.sh encontrado em AS7_HOME/bin:


      $ ./domain.sh 

Após a inicialização do domain ser concluída, é possível visualizar quatro processos Java em execução. A Figura 10 mostra essa visão de processos através da ferramenta Java VisualVM, que acompanha a instalação do Oracle JDK 1.6.

Processos
    criados no modo de domínio
Figura 10. Processos criados no modo de domínio.

Nessa figura observamos quatro processos diferentes: um host controller, um process controller e dois server nodes. Você deve estar se perguntando onde está a JVM que representa o elemento Domain Controller, correto? Na verdade, um Domain Controller é essencialmente um processo Host Controller, porém dependendo da topologia usada para executar e formar o domínio, ele assume o papel de Domain Controller.

No início este conceito é um pouco confuso, mas em breve veremos outro exemplo um pouco mais claro. Neste outro exemplo utilizaremos uma topologia em que o domínio é formado por servidores instalados em hosts distintos. Outro questionamento que o leitor pode ter é: e quanto ao processo referente ao server #3 mostrado na Figura 10? Bem, como veremos mais adiante na configuração do host (host.xml), um server node pode ser definido para ficar em modo standby, ou seja, ele não inicia automaticamente juntamente com os demais nodes configurados no mesmo host. O trecho que declara os server nodes é apresentado na Listagem 5. Na definição padrão temos três server nodes (server-one, server-two e server-three). No entanto, observe a propriedade auto-start, que possui valor false para o server-three, indicando que ele não será inicializado durante o startup do host em questão.

Listagem 5. Descritor AS7_HOME/standalone/configuration/host.xml. Definição dos server-nodes que serão inicializados no host membro do domínio.

      <servers>
        <server name="server-one" group="main-server-group">
          <!-- Remote JPDA debugging for a specific server
          <jvm name="default">
            <jvm-options>
              <option value="-Xrunjdwp:transport=dt_socket,address=8787,server=y,suspend=n"/>
            </jvm-options>
          </jvm>
       
          -->
        </server>
        <server name="server-two" group="main-server-group" auto-start="true">
          <!-- server-two avoids port conflicts by incrementing the ports in
            the default socket-group declared in the server-group -->
          <socket-bindings port-offset="150"/>
        </server>
       
        <server name="server-three" group="other-server-group" auto-start="false">
          <!-- server-three avoids port conflicts by incrementing the ports in
            the default socket-group declared in the server-group -->
          <socket-bindings port-offset="250"/>
        </server>
      </servers> 

Dessa forma ele é um servidor sobressalente, que pode ser iniciado manualmente usando uma das interfaces de gerenciamento disponíveis no AS 7.

descritor domain.xml contém toda a configuração usada pelos servidores membros do domínio. A estrutura do arquivo segue um esquema semelhante ao do descritor standalone.xml. Porém, com uma importante diferença que permite a configuração de diferentes profiles (subsistemas, configuração de JVM, grupos de servidores, entre outros). Veja o esquema macro do descritor domain.xml na Figura 11. Para mais detalhes sobre o que pode ser definido no descritor, consulte o XML Schema localizado na distribuição do AS 7 em AS7_HOME/docs/schema/jboss-as-config_1_1.xsd.

A Figura 12 mostra algumas das principais diferenças de profiles nos dois modos de execução.

Macro esquema do descritor domain.xml
Figura 11. Macro esquema do descritor domain.xml.
Definição de profiles no modo standalone e no modo domain
Figura 12. Definição de profiles no modo standalone e no modo domain.

A Listagem 6 mostra o trecho de definição dos profiles no arquivo domain.xml. No início desta listagem, note que é declarado o profile default com os subsistemas e suas respectivas configurações de logging, cmp, datasources, javaee, ejb3 e weld. Para criar vários profiles, basta utilizar a tag <profile name=“nome_do_profile”> abaixo da tag <profiles>.

Listagem 6. Exemplo de profile default e ha. Arquivo AS7_HOME/domain/configuration/domain.xml.

      <domain xmlns="urn:jboss:domain:1.1">
      ...
          <profiles>
              <profile name="default">
                  <subsystem xmlns="urn:jboss:domain:logging:1.1">
                      <console-handler name="CONSOLE">
                          <level name="INFO"/>
                          <formatter>
                              <pattern-formatter pattern="%d{HH:mm:ss,SSS} %-5p [%c] (%t) %s%E%n"/>
                          </formatter>
                      </console-handler>
       
                      <periodic-rotating-file-handler name="FILE">
                          <formatter>
                              <pattern-formatter pattern="%d{HH:mm:ss,SSS} %-5p [%c] (%t) %s%E%n"/>
                          </formatter>
                          <file relative-to="jboss.server.log.dir" path="server.log"/>
                          <suffix value=".yyyy-MM-dd"/>
                      </periodic-rotating-file-handler>
                      ...
                      <logger category="com.arjuna">
                          <level name="WARN"/>
                      </logger>
                      <root-logger>
                          <level name="INFO"/>
                          <handlers>
                              <handler name="CONSOLE"/>
                              <handler name="FILE"/>
                          </handlers>
                      </root-logger>
                  </subsystem>
       
                  <subsystem xmlns="urn:jboss:domain:cmp:1.0"/>
                  <subsystem xmlns="urn:jboss:domain:datasources:1.0">
                      <datasources>
                          <datasource jndi-name="java:jboss/datasources/ExampleDS" pool-name="ExampleDS" enabled="true" use-java-context="true">
                              <connection-url>
                                  jdbc:h2:mem:test;DB_CLOSE_DELAY=-1
                              </connection-url>
                              <driver>
                                  h2
                              </driver>
                              <security>
                                  <user-name>
                                      sa
                                  </user-name>
                                  <password>
                                      sa
                                  </password>
                              </security>
                          </datasource>
                          <drivers>
                              <driver name="h2" module="com.h2database.h2">
                                  <xa-datasource-class>
                                      org.h2.jdbcx.JdbcDataSource
                                  </xa-datasource-class>
                              </driver>
                          </drivers>
                      </datasources>
                  </subsystem>
       
                  <subsystem xmlns="urn:jboss:domain:ee:1.0"/>
                  <subsystem xmlns="urn:jboss:domain:ejb3:1.2">
                      <session-bean>
                          <stateless>
                              <bean-instance-pool-ref pool-name="slsb-strict-max-pool"/>
                          </stateless>
                          <stateful default-access-timeout="5000" cache-ref="simple"/>
                          <singleton default-access-timeout="5000"/>
                      </session-bean>
                      <mdb>
                          <resource-adapter-ref resource-adapter-name="hornetq-ra"/>
                          <bean-instance-pool-ref pool-name="mdb-strict-max-pool"/>
                      </mdb>
                      <pools>
                          <bean-instance-pools>
                              <strict-max-pool name="slsb-strict-max-pool" max-pool-size="20" instance-acquisition-timeout="5" instance-acquisition-timeout-unit="MINUTES"/>
       
                              <strict-max-pool name="mdb-strict-max-pool" max-pool-size="20" instance-acquisition-timeout="5" instance-acquisition-timeout-unit="MINUTES"/>
                          </bean-instance-pools>
                      </pools>
                      <caches>
                          <cache name="simple" aliases="NoPassivationCache"/>
                          <cache name="passivating" passivation-store-ref="file" aliases="SimpleStatefulCache"/>
                      </caches>
                      <passivation-stores>
                          <file-passivation-store name="file"/>
                      </passivation-stores>
                      <async thread-pool-name="default"/>
                      <timer-service thread-pool-name="default">
                          <data-store path="timer-service-data" relative-to="jboss.server.data.dir"/>
                      </timer-service>
                      <remote connector-ref="remoting-connector" thread-pool-name="default"/>
                      <thread-pools>
                          <thread-pool name="default" max-threads="10" keepalive-time="100"/>
                      </thread-pools>
                      <iiop use-qualified-name="true" enable-by-default="true"/>
                  </subsystem>
      ...
                  <subsystem xmlns="urn:jboss:domain:weld:1.0"/>
              </profile>
       
              <profile name="ha">
      ...
              </profile>
      </profiles>
      ... 

Da mesma forma que podemos criar diferentes profiles para um mesmo domínio, podemos subdividir o domínio em grupos de servidores (server groups). Dessa forma cada grupo de servidores pode ter sua própria configuração, ou seja, possuir um conjunto de serviços específico, configurações de JVM, endereços e portas de acesso aos serviços (socket bindings).

Imagine um domínio contendo dois grupos diferentes de servidores, sendo: um para aplicações que consomem menos recursos e outro para aplicações mais críticas e que requeiram mais recursos de hardware. A Figura 13 mostra quais características podem ser customizadas quando definimos grupos de servidores em um domínio.

Configuração de grupos de servidores
Figura 13. Configuração de grupos de servidores.

A Listagem 7 mostra um exemplo de dois grupos de servidores configurados por padrão no arquivo domain.xml. O main-server-group faz referência ao profile default, já com uma configuração de JVM, atribuindo os valores mínimo de 64Mb e máximo de 512Mb para a memória heap. O main-server-group utiliza como endpoints os endereços de portas definidos no socket-binding-group standard-sockets (veja a Listagem 8). A Listagem 7 também traz o grupo de servidores do tipo other-server-group, referenciando o profile ha. A principal diferença entre os dois grupos está relacionada às portas de cada um. No caso, o grupo other-server-group utiliza as portas definidas em ha-sockets (também descrito na Listagem 8), contendo portas para a configuração de cluster com jgroups e balanceamento de carga com mod cluster.

Listagem 7. Grupos de Servidores. AS7_HOME/domain/configuration/domain.xml.

      <server-groups>
        <server-group name="main-server-group" profile="default">
          <jvm name="default">
            <heap size="64m" max-size="512m"/>
          </jvm>
          <socket-binding-group ref="standard-sockets"/>
        </server-group>
        <server-group name="other-server-group" profile="ha">
          <jvm name="default">
            <heap size="64m" max-size="512m"/>
          </jvm>
          <socket-binding-group ref="ha-sockets"/>
        </server-group>
      </server-groups> 
Listagem 8. Socket Bindings. AS7_HOME/domain/configuration/domain.xml.

      <socket-binding-groups>
        <socket-binding-group name="standard-sockets" default-interface="public">
          <socket-binding name="http" port="8080"/>
       
          <socket-binding name="https" port="8443"/>
       
          <socket-binding name="jacorb" port="3528"/>
       
          <socket-binding name="jacorb-ssl" port="3529"/>
       
          <socket-binding name="jgroups-diagnostics" port="0" multicast-address="224.0.75.75" multicast-port="7500"/>
       
          <socket-binding name="jgroups-mping" port="0" multicast-address="${jboss.default.multicast.address:230.0.0.4}" multicast-port="45700"/>
       
          <socket-binding name="jgroups-tcp" port="7600"/>
       
          <socket-binding name="jgroups-tcp-fd" port="57600"/>
       
          <socket-binding name="jgroups-udp" port="55200" multicast-address="${jboss.default.multicast.address:230.0.0.4}" multicast-port="45688"/>
       
          <socket-binding name="jgroups-udp-fd" port="54200"/>
       
          <socket-binding name="jmx-connector-registry" interface="management" port="1090"/>
       
          <socket-binding name="jmx-connector-server" interface="management" port="1091"/>
       
          <socket-binding name="messaging" port="5445"/>
       
          <socket-binding name="messaging-throughput" port="5455"/>
       
          <socket-binding name="modcluster" port="0"  multicast-address="224.0.1.105" multicast-port="23364"/>
       
          <socket-binding name="osgi-http" interface="management" port="8090"/>
       
          <socket-binding name="remoting" port="4447"/>
       
          <socket-binding name="txn-recovery-environment" port="4712"/>
       
          <socket-binding name="txn-status-manager" port="4713"/>
       
          <outbound-socket-binding name="mail-smtp">
       
            <remote-destination host="localhost" port="25"/>
       
          </outbound-socket-binding>
        </socket-binding-group>  
      </socket-binding-groups> 

Um domínio pode ser formado por servidores instalados em uma mesma máquina (física ou virtual) onde vários processos Java são inicializados no sistema operacional.


O termo host deve ser entendido como um computador executando um sistema operacional que irá hospedar a instalação do AS 7, bem como a configuração das instâncias que fazem parte de um domínio específico.

Quando iniciamos um domínio através do script AS7_HOME/bin/domain.(sh|bat), como vimos anteriormente, um processo Java chamado Host Controller é instanciado. Este processo é responsável especificamente pela gerência do servidor. Ao contrário das instâncias do AS (server nodes), ele não processa requisições ou deployments. Seu trabalho é cuidar do ciclo de vida do servidor, como iniciar e parar instâncias individuais que estejam em execução no mesmo host, bem como interagir com o Domain Controller a fim de gerenciá-las.

O Host Controller é configurado no arquivo host.xml localizado no diretório AS7_HOME/domain/configuration (veja a Listagem 9). Este descritor contém a configuração específica para o host em que o AS está instalado, incluindo:

  • A lista de instâncias do servidor (server nodes) definidas para executarem no host em questão;
  • A configuração do processo Host Controller e como ele interage com o Domain Controller (que pode ser um processo local ou remoto) para acessar a configuração do domínio;
  • Um processo do Host Controller pode ser o próprio Domain Controller do domínio. Esse é o cenário padrão, onde o domínio é executado em um único host. Ao utilizar uma topologia distribuída em vários hosts, o domínio pode ser gerenciado por um Host Controller rodando em um host remoto. Nesse caso, o Host Controller remoto assume o papel de Domain Controller do domínio.

  • A configuração de características específicas do host em questão, como interfaces de gerência, paths do sistema de arquivos, JVM, etc. As configurações do host (host.xml) têm precedência sobre as definidas pelo domínio (domain.xml).

Para ilustrar um domínio distribuído em diferentes hosts, a Figura 14 propõe uma topologia organizada em dois hosts distintos.

Listagem 9. Definição de grupos de servidores. AS7_HOME/domain/configuration/host.xml.

      <server-group name="custom-server-group" profile="default">
        <deployments>
          <deployment name="sample.war_v1" runtime-name="sample.war" hash="ABCDEFG1234567890ABC"/>
        </deployments>
       
        <jvm name="default">
          <heap size="512m" max-size="1g"/>
        </jvm>
       
        <socket-binding-group ref="standard-sockets"/>
       
        <system-properties>
          <property name="foo" value="bar" boot-time="true"/>
          <property name="key" value="value" boot-time="true"/>
        </system-properties>
      </server-group> 
Domínio formado por dois hosts virtuais e seis server nodes
Figura 14. Domínio formado por dois hosts virtuais e seis server nodes.

Como podemos observar na imagem, o domínio pode ser composto por vários hosts (host #1 e host #2) e ainda possuir grupos diferentes de servidores (server group #1 e server group #2). Lembrando que cada grupo possui características específicas que são empregadas nas instâncias que fazem parte dele.

Entenda server group como um conjunto lógico de instâncias que podem ser executadas em uma mesma máquina, utilizando processos Java diferentes ou até mesmo rodando em máquinas diferentes. Para ser um server group, estas instâncias precisarão possuir algumas configurações em comum, não importando onde elas estão sendo executadas.

Podemos simular o domínio proposto na Figura 14 usando duas instalações do AS 7 configuradas em duas máquinas (virtuais ou físicas) hospedadas em um mesmo segmento de rede. Para esta simulação, vamos utilizar alguns passos da instalação do JBoss AS descrita anteriormente. Porém, para tornar o exemplo um pouco mais atrativo, usaremos duas máquinas virtuais. A criação de um ambiente virtualizado foge do escopo deste artigo. Portanto, partiremos do princípio de que o leitor possui duas máquinas virtuais devidamente instaladas com seu sistema operacional preferido.

No nosso caso, temos duas máquinas virtuais rodando o Red Hat Enterprise Linux (RHEL) 6.x. As duas VMs possuem 512Mb de memória RAM e dois CPUs virtuais. Como ambiente de virtualização, utilizamos a plataforma KVM, que já é nativa no RHEL 6.x. A JVM OpenJDK 1.6 também foi instalada e configurada em ambas as máquinas virtuais, as quais chamaremos de Host #1 e Host #2. Por fim, vale ressaltar que o AS 7 foi instalado no diretório /opt nos dois ambientes.

No entanto, antes de iniciarmos o domínio nos dois hosts precisamos definir alguns parâmetros. O primeiro deles é dar um nome para cada host. Para isso, edite o arquivo AS7_HOME/domain/configuration/host.xml nos dois hosts e altere o atributo name na tag <host> logo no início do arquivo. A Listagem 10 mostra essa alteração.

Listagem 10. Alteração do nome padrão do host. AS7_HOME/domain/configuration/host.xml.

      em Host #1
      <host name="host1" xmlns="urn:jboss:domain:1.1">
      ...
       
      em Host #2
      <host name="host2" xmlns="urn:jboss:domain:1.1">
      ... 

Em seguida, defina o endereço IP que será habilitado como interface de acesso (public) e gerenciamento (management) em cada host.

No Host #1 utilizamos o IP 192.168.122.131, que foi atribuído durante sua inicialização. Execute o seguinte comando para iniciar o AS nesse host, lembrando que este script se encontra no diretório AS7_HOME/bin:


      $ ./domain.sh -bpublic=192.168.122.131 -bmanagement=192.168.122.131 

O parâmetro -b<interface>=<ip> informado na inicialização do servidor define os endereços IP utilizados pelas interfaces de acesso (public) e de gerência (management). Essa definição também pode ser feita manualmente no arquivo host.xml, conforme mostra a Listagem 11.

Saiba mais sobre Java ;)

  • Carreira Programador Java:
    Aprender Java não é uma tarefa simples, mas seguindo a ordem proposta nesse Guia, você evitará muitas confusões e perdas de tempo no seu aprendizado. Vem aprender java de verdade, vem!
  • Linguagem Java:
    Neste Guia de Referência você encontrará todo o conteúdo que precisa para começar a programar com a linguagem Java, a sua caixa de ferramentas base para criar aplicações com Java.
  • JSF - JavaServer Faces:
    Neste Guia de Referência você encontrará todo o conteúdo que precisa para conhecer o JSF, especificação Java que traz conceitos do padrão MVC e que facilita a construção de interfaces web utilizando componentes.
  • Java Enterprise Edition - Java EE:
    Neste Guia de Referência você encontrará todo o conteúdo que precisa para conhecer o Java EE, Java Enterprise Edition, a plataforma Java voltada para o desenvolvimento de aplicações web/corporativas.
  • JBoss: Introdução e Aplicação MVC completa:
    Neste curso de JBoss, composto por uma sequência de video aulas, iremos desvendar este que é um dos mais conhecidos e utilizados servidores de aplicação java do mercado opensource.
Listagem 11. Interfaces public e management do host. AS7_HOME/domain/configuration/host.xml.

      <interfaces>
        <interface name="management">
          <inet-address value="192.168.122.131"/>
        </interface>
        <interface name="public">
          <inet-address value="192.168.122.131"/>
        </interface>
      </interfaces> 

Nesse exemplo de domínio, o processo Host Controller iniciado em Host #1 assume o papel de Domain Controller. Para isso, a configuração do Domain Controller traz a tag <local/>, como pode ser observado na Listagem 12.

Listagem 12. Configuração de Host Controller com papel de Domain Controller. AS7_HOME/domain/configuration/host.xml.

      <domain-controller>
        <local/>
      </domain-controller> 

A menos que seja alterado, por padrão, Host Controller é o próprio Domain Controller local do host.

Em Host #1 também foram iniciadas duas instâncias do servidor (server-one e server-two). A Listagem 13 mostra esse trecho da configuração no arquivo host.xml.

Listagem 13. Instâncias do servidor a serem iniciadas. AS7_HOME/domain/configuration/host.xml.

      <servers>
        <server name="server-one" group="main-server-group" auto-start="true"/>
        <server name="server-two" group="main-server-group" auto-start="true">
          <!-- server-two avoids port conflicts by incrementing the ports in
            the default socket-group declared in the server-group -->
        <socket-bindings port-offset="150"/>
        </server>
       
        <server name="server-three" group="other-server-group" auto-start="false">
          <!-- server-three avoids port conflicts by incrementing the ports in
            the default socket-group declared in the server-group -->
          <socket-bindings port-offset="250"/>
        </server>
      </servers> 

Embora tenha sido definida uma terceira instância (server-three) neste host, apenas as duas primeiras (server-one e server-two) foram configuradas para iniciarem automaticamente. A terceira ficará em standby.

No Host #2 utilizamos o IP 192.168.122.132, que foi atribuído durante sua inicialização. Para que esse host faça parte do domínio, precisamos informar quem deve ser o Domain Controller responsável por ele. Para tal, podemos utilizar o Domain Controller que já está sendo executado no Host #1. Desta forma, iremos compartilhá-lo entre os dois hosts. No entanto, para o correto funcionamento, é necessário também alterar a configuração referente ao Domain Controller do #Host 2, conforme mostrado na Listagem 14.

Listagem 14. Domain Controller remoto utilizando o host #1. AS7_HOME/domain/configuration/host.xml.

      <host name="host2" xmlns="urn:jboss:domain:1.1">
          <management>
              <security-realms>
                  <security-realm name="ManagementRealm">
                      <authentication>
                          <properties path="mgmt-users.properties" relative-to="jboss.domain.config.dir"/>
                      </authentication>
                     
                      <!-- credencial do usuário as7admin para se conectar ao DC do Host #1 -->
                      <server-identities>
                         <secret value="MTIzNDU2" /> <!-- senha do user as7admin codificada em base64 -->
                      </server-identities>
                  </security-realm>
              </security-realms>
      ...
          </management>
      ...
          <domain-controller>
             <!-- <local/> -->
             <remote host="${jboss.domain.master.address}" port="9999" security-realm=”ManagementRealm”/>
          </domain-controller>
      ... 

Nesta nova configuração temos dois pontos importantes. O primeiro é a referência ao Domain Controller remoto nas últimas quatro linhas da Listagem 14, o que torna o Host #2 um slave gerenciado por Host #1. O segundo é que para que um Host Controller se conecte a um Domain Controller remoto, é necessário que ele se autentique. Por isso configuramos o security realm ManagementRealm.

O endereço do Domain Controller remoto pode ser informado na linha de comando através do parâmetro --master-address=<ip remoto>. Assim, para iniciar o AS no Host #2, entre no diretório AS7_HOME/bin e execute o seguinte comando:


      $ /domain.sh -bpublic=192.168.122.132 --master-address=192.168.122.131 

O parâmetro --master-address=<ip> informado na inicialização do servidor em Host #2 define o endereço do Host que hospeda o Domain Controller. Neste caso, o IP do Host #1 (192.168.122.131).

Após a inicialização do Host #2, observe que no log de saída do Host #1 (Domain Controller) aparece a informação de que um host remoto acaba de se registrar no domínio (veja a Listagem 15).

Listagem 15. Host #2 se registrando no Domain Controller. Arquivo de log AS7_HOME/domain/log/host-controller/boot.log do Host 1.

      [Host Controller] 17:19:03,795 INFO  [org.jboss.as.domain] (management-handler-threads - 1) JBAS010918: Registered remote slave host host2 

Em Host #2 também foi iniciada mais uma instância do servidor (server-four) que fará parte do mesmo domínio iniciado em Host #1. A Listagem 16 mostra esse trecho da configuração no arquivo host.xml.

Listagem 16. Instância 4 deste domínio configurada no host #2. AS7_HOME/domain/configuration/host.xml.

      <servers>
        <server name="server-four" group="main-server-group" auto-start="true"/>
      </servers> 

Após o servidor ter sido iniciado em ambos os hosts, o próximo passo é acessar a console de gerenciamento web e iniciar o gerenciamento do domínio. Como o Domain Controller responsável pelo domínio está sendo executado em Host #1, devemos utilizar o endereço http://192.168.122.131:9990. Ao acessá-la pela primeira vez, uma página como mostra a Figura 15 será exibida.

Página
    inicial do JBoss AS 7
Figura 15. Página inicial do JBoss AS 7.

Por padrão, o acesso através do usuário admin vem desabilitado. Conforme as instruções da própria página carregada, será necessário criar um novo usuário de administração. Para isso, execute o script add-user.(sh|bat) fornecido no diretório AS7_HOME/bin. O script é interativo e irá guiá-lo nesse processo. A Figura 16 mostra um exemplo de criação do usuário as7admin.

Criação do usuário as7admin para acessar a console de gerência do AS 7
Figura 16. Criação do usuário as7admin para acessar a console de gerência do AS 7.

Como o domínio será gerenciado a partir do Domain Controller hospedado em Host #1, basta que o usuário seja criado na instalação do Host #1.

Após criar o usuário, acesse novamente a página (http://192.168.122.131:9990) ou simplesmente clique no link Try again apresentado na Figura 15. Em seguida, entre com as credenciais do usuário recém-criado e voilá. Você agora pode gerenciar o domínio e todas as instâncias que o integram. Fazer alterações na configuração, gerenciar deployments, fazer start/stop de server nodes, criar novos server nodes, entre outras opções. A Figura 17 mostra a console de gerência do AS 7. Ao efetuar o login, a primeira página carregada mostra a visão dos server nodes configurados em Host #1.

Console de gerência do AS 7. Visão dos server nodes configurados em Host #1
Figura 17. Console de gerência do AS 7. Visão dos server nodes configurados em Host #1.

Para demonstrarmos mais um pouco do modo Domain, vamos realizar algumas tarefas gerenciais. Primeiro, iremos criar uma nova instância do servidor e adicioná-la a um server-group específico. Deste modo, com a console de gerência aberta:

  1. 1. Acesse o menu superior Server;
  2. 2. Selecione o host2 na lista superior esquerda;
  3. 3. Clique no botão Add;
  4. 4. Preencha as informações da nova instância e salve (veja a Figura 18).
Adicionando um novo server node ao Host #2
Figura 18. Adicionando um novo server node ao Host #2.

Feito isso, basta iniciar a instância recém-criada, executando os passos (veja a Figura 19):

  1. 1. Acesse o menu superior Runtime;
  2. 2. Selecione o host2 na lista superior esquerda e depois o server node server-five;
  3. >3. Clique em Start;
  4. 4. E para finalizar, clique em Ok.
Iniciando o server node server-four
Figura 19. Iniciando o server node server-four.

Após alguns instantes recarregue a página. Na coluna status deve aparecer uma bola azul indicando que o server-four está ativo.

É possível realizar diversas tarefas através da nova console do AS 7. Porém, para não estendermos ainda mais este tópico, deixamos como tarefa para o leitor a criação de um novo grupo de servidores, adicionar novas instâncias a ele e fazer o deployment de uma aplicação. Tudo pela console de gerenciamento, sem reiniciar o domínio e sem mexer em arquivos XML manualmente.

Certifique-se de que ambos os hosts se conectam através das interfaces de rede virtual criada no ambiente virtual. Execute os comandos ping e/ou telnet para testar a conectividade entre as máquinas criadas para o teste. Como o JBoss utiliza portas altas para acessar os serviços remotos, garanta que o firewall local de cada máquina esteja desligado no momento do teste.

Agora que conhecemos os dois modos de execução do AS 7, resta decidir qual deles atende melhor as nossas necessidades. Isso depende de alguns fatores. Como pudemos perceber, o objetivo principal do modo Domain é facilitar o gerenciamento de múltiplas instâncias do servidor de aplicação. Portanto, podemos inferir alguns cenários em que esse modo não se aplica:

  1. 1. Ambiente de Desenvolvimento. Durante a fase de desenvolvimento o deployment das aplicações geralmente é feito em uma única instância de teste, eliminando a necessidade de manter várias instâncias do servidor para uma mesma aplicação;
  2. 2. Em alguns cenários como no uso de um framework de testes que utiliza o AS 7 de forma embutida (embedded), como é o caso do framework de testes de integração Arquillian. Um projeto Arquillian emprega o AS 7 em modo standalone;
  3. 3. Se a equipe de administração do servidor de aplicação já possui ou desenvolveu um mecanismo/ferramenta de configuração centralizada para múltiplos servidores. Neste caso é necessário avaliar se o uso do modo Domain oferecido pelo AS 7 será mais produtivo e interessante que o atual modo de administração.

Por outro lado, o modo Domain pode ser mais eficiente para o ambiente de produção em que uma mesma aplicação deva ser implantada em servidores espalhados em várias máquinas. Isso é muito comum quando se utiliza um balanceador de carga como front-end para aplicações web hospedas em diversos servidores de aplicação. Neste caso o modo Domain oferece uma administração centralizada que facilita a manutenção da configuração, a adição ou remoção de novas instâncias, bem como o deployment da aplicação.

Em suma, a decisão sobre qual modo utilizar deve levar em conta como o servidor de aplicação será gerenciado. Pois, como vimos neste tópico, não há diferenças em relação aos serviços e as capacidades oferecidas pelos dois. Ambos podem ser configurados para oferecer os mesmos subsistemas e ambos podem ser utilizados em cluster.

O novo kernel do JBoss AS

Sem dúvida uma das características mais marcantes do AS 7 é a velocidade do startup. Ao longo do tempo o kernel do JBoss AS passou por várias redefinições. Até a versão 4, o JBoss utilizava um kernel modular baseado em JMX chamado Microkernel, onde os serviços eram definidos como MBeans JMX. A partir da versão 5, ele foi totalmente remodelado e passou a se chamar Microcontainer, tendo como base a AOP. O Microcontainer, além de possuir todas as características do Microkernel JMX, trouxe uma série de inovações ao JBoss AS. Dentre elas, podemos citar a implantação e injeção de serviços baseados em POJO, VFS, classloading OSGi, uso do kernel de forma embutida, entre outras. Para a versão 7, os engenheiros utilizaram uma nova abordagem para o kernel, que se baseia no conceito de módulos e serviços. O novo kernel do JBoss é formado basicamente por duas camadas, denominadas JBoss Modules e JBoss Modular Service Container (MSC).

JBoss Modules

Um dos motivos pelos quais o AS 7 é tão performático e flexível (pode ser inicializado até mesmo de forma embutida em um cenário de testes) é que ele foi projetado desde sua concepção para ser modular e tirar o máximo de proveito de plataformas multiprocessadas. A propósito, hoje em dia, é muito comum executar o servidor de aplicação em um hardware com mais de um núcleo de processamento. Qualquer laptop atual, por exemplo, possui um processador com no mínimo dois núcleos.

Embora o AS 7 forneça uma implementação do framework OSGi, diferentemente de outros servidores Java mais recentes, seu núcleo não executa sobre uma plataforma OSGi. O núcleo do AS 7 é executado sobre uma camada chamada JBoss Modules, que difere do OSGi em alguns aspectos. JBoss Modules implementa apenas os requisitos de modularização definidos pelo framework OSGi.

O time de engenheiros responsável pelo novo design do AS 7 preferiu uma abordagem mais simplista para o novo kernel. Porém, que resolvesse questões importantes como isolamento, modularidade e, principalmente, performance. Isso pode ser percebido através do nível de isolamento que o AS oferece entre sua implementação e as aplicações e serviços implantados no servidor. Outro aspecto que chama ainda mais atenção para esta versão é a velocidade de inicialização. Algo em torno de 2 a 3 segundos, dependendo do hardware utilizado. O JBoss Modules pode ser considerado um precursor do que poderá ser uma implementação compatível com a JSR 294 (Java Modules).

Conceitualmente JBoss Modules não é um container Java, mas sim um ambiente de execução totalmente isolado e leve que implementa um classloader modular e não hierárquico. O modelo tradicional oferecido pelo Java SE utiliza um classpath único, contendo uma lista com todos os JARs carregados de uma única vez formando um classloader único e hierárquico para a aplicação. Este modelo é inadequado para ambientes de execução que precisam gerenciar dependências complexas e, em alguns casos, isolamentos específicos. Imagine um cenário em que é necessário manter diferentes versões de bibliotecas utilizadas por diferentes serviços e aplicações hospedadas em um mesmo servidor de aplicação. Esse problema é conhecido como JAR Hell ou ClassLoader Hell.

A implementação do JBoss Modules se propõe a atacar esse problema com a seguinte abordagem: uma vez que um conjunto de JARs são empacotados como módulos, não haverá mais conflito de versões entre classes dependentes ou o risco de se utilizar um recurso de outro JAR de forma inadvertida. As dependências são configuradas de forma explícita para cada módulo usando como base informações de nome e versão. E cada módulo está associado a uma única instância de classloader. Dessa forma um módulo não enxerga dependências transitivas, a menos que seja explicitamente referenciada.

A Figura 20 mostra um exemplo de classloader gerenciado pelo sistema de módulos. Nesse esquema as dependências são declaradas usando as diretivas Imports e Exports, que são utilizadas para carregar e gerenciar os módulos.

Classloader modular
Figura 20. Classloader modular.

Diferentemente do modelo de classloader hierárquico, onde o relacionamento entre dependências é feito em forma de árvore, em um ambiente modular as referências são declaradas de forma independente de um módulo para outro em forma de grafo, como ilustra a Figura 21.

Grafo de módulos e suas dependências
Figura 21. Grafo de módulos e suas dependências.

O mecanismo de gerenciamento de módulos não está disponível apenas para os módulos ou serviços que fazem parte da implementação interna do AS 7. Um arquivo EAR ou WAR pode declarar uma dependência explícita a um arquivo JAR externo de forma modular em uma aplicação Java EE utilizando o descritor de manifesto (META-INF/manifest.mf) com as diretivas Class-path ou Dependency.

Outro aspecto importante é que um módulo só será carregado se for utilizado por alguma dependência, caso contrário ele nunca será carregado. Em suma, podemos destacar as seguintes características oferecidas pela implementação do JBoss Modules:

  • Mecanismo de classloader concorrente de alta performance, thread-safe e com excelente gerenciamento de memória capaz de carregar qualquer classe Java em um tempo extremamente curto;
  • Isolamento entre a implementação do servidor e aplicações implantadas;
  • Regras de visibilidade de classes e pacotes customizáveis;
  • Sistema de carregamento de módulos extensível que suporta diferentes estratégias de definição de módulos;
  • Mecanismo de carregamento de módulos bastante simples que permite carregar qualquer módulo no formato JAR ou, até mesmo, um diretório com extensão .jar com uma estruturada pré-definida;
  • API para carregar módulos, obter um classloader específico, criar módulos em tempo de execução, entre outros.

A Figura 22 mostra um esquema de como o JBoss Modules e o JBoss MSC interagem.

JBoss Modules e JBoss MSC
Figura 22. JBoss Modules e JBoss MSC.

Por ser um ambiente de execução Java, qualquer implementação de uma API pode ser plugada e inicializada pelo JBoss Modules. É dessa forma que os serviços Java EE fornecidos pelo AS 7, inclusive a própria implementação do framework OSGi (JBoss OSGi), são plugados.

Um módulo para o JBoss Modules nada mais é do que uma coleção de recursos. Um conjunto de classes associadas a um classloader específico contendo dependências explícitas. Classes e recursos expostos por uma dependência são visíveis a partir dos recursos integrantes do módulo dependente. Portanto, o que o sistema de módulos fornece é uma forma de empacotar esses recursos em módulos e estabelecer, em tempo de execução, uma espécie de grafo de classloaders onde todas as dependências possam ser satisfeitas.

Uma aplicação modularizada conforme os conceitos apresentados neste tópico pode ser inicializada através do JBoss Modules executando a seguinte linha de comando:


      $ java -jar jboss-modules.jar -mp /camindo/diretorio/modulos modulo.principal.Nome 

O parâmetro -mp especifica o diretório raiz onde o módulo principal reside. O JBoss Modules é também capaz de varrer recursivamente subdiretórios dentro da raiz informada. No AS 7, os módulos carregados durante a inicialização do servidor residem em uma estrutura de diretórios semelhante à apresentada na Listagem 17. O módulo h2database, por exemplo, representa o driver jdbc utilizado para o banco de dados H2.

Listagem 17. Repositório de módulos do AS 7.

      ...
      |-- jboss-modules.jar
      |
      |-- modules
      |   |-- asm
      |   |   `-- asm
      |   |       `-- main
      |   |           |-- asm-3.3.1.jar
      |   |           |-- asm-3.3.1.jar.index
      |   |           `-- module.xml
      |   |-- ch
      |   |   `-- qos
      |   |       `-- cal10n
      |   |           `-- main
      |   |               |-- cal10n-api-0.7.3.jar
      |   |               |-- cal10n-api-0.7.3.jar.index
      |   |               `-- module.xml
      |   |-- com
      |   |   |-- google
      |   |   |   `-- guava
      |   |   |       `-- main
      |   |   |           |-- guava-10.0.1.jar
      |   |   |           |-- guava-10.0.1.jar.index
      |   |   |           `-- module.xml
      |   |   |-- h2database
      |   |   |   `-- h2
      |   |   |       `-- main
      |   |   |           |-- h2-1.3.161.jar
      |   |   |           |-- h2-1.3.161.jar.index
      |   |   |           `-- module.xml
      ... 

Um módulo é descrito utilizando um simples XML, como o da Listagem 18. O descritor do módulo define qual a classe principal na inicialização por meio da tag <main-class>, em seguida são informados os recursos que compõem o módulo com a tag <resources>, e por fim é possível especificar as dependências do módulo com o bloco <dependencies>.

Listagem 18. Descritor do módulo h2database. AS7_HOME/modules/com/h2database/h2/main/module.xml.

      <module xmlns="urn:jboss:module:1.1" name="com.h2database.h2">
        <resources>
          <resource-root path="h2-1.3.161.jar"/>
          <!-- Insert resources here -->
        </resources>
        <dependencies>
          <module name="javax.api"/>
          <module name="javax.transaction.api"/>
          <module name="javax.servlet.api" optional="true"/>
        </dependencies>
      </module> 

O JAR jboss-modules.jar, que reside no diretório raiz do AS 7 (AS7_HOME), possui o XML Schema (jboss-modules.jar/schema/module-1_1.xsd) que define o descritor de módulos. Ele pode ser útil para descrever módulos utilizando uma IDE com suporte à edição de XML.

JBoss Modular Service Container

O JBoss Modular Service Container, do AS 7, é quem coordena o mecanismo de registro, bem como a instalação e execução de todos os serviços oferecidos pelo servidor. Trata-se de uma máquina de estados que mantém de forma paralela todo o ciclo de vida dos serviços instalados. O JBoss MSC também é utilizado como implementação da camada de serviços do JBoss OSGi. A Tabela 1 apresenta um comparativo das principais características entre a especificação da camada de serviços OSGi e a implementação do JBoss MSC.

Serviços OSGi

JBoss MSC

Um serviço é identificado pelo seu Tipo

Um serviço é identificado pelo seu Nome

Suporte a filtro usando LDAP

Sem suporte a filtro. Utiliza apenas o nome

Ciclo de vida gerenciado pelo próprio Bundle ou explicitamente via API

Ciclo de vida gerenciado pelo próprio Bundle ou explicitamente via API

Dependência e Injeção de Serviços via Declarative Services (DS) ou Blueprint

Dependência e Injeção de Serviços via API própria (MSC API)

Suporte a ServiceListener

Suporte a ServiceListener

Suporte a ServiceFactory

Instanciação através do nome do Serviço

ConfigurationAdmin

Console Administrativa do AS 7

Tabela 1. Comparativo entre OSGi Services e JBoss MSC.

Conclusão

Este foi o primeiro artigo da série sobre o JBoss AS 7, que apresentou suas principais novidades e características, trazendo os passos básicos para instalação e configurações. Mantivemos foco nos modos Standalone e Domain, descrevendo uma introdução ao conceito de subsistemas para os serviços, as especializações dos novos profiles e a nova estrutura de diretórios e arquivos.

O JBoss AS 7 foi totalmente reinventado, seu kernel é ainda mais modular e extremamente performático. Com as camadas JBoss Modules e JBoss Modular Service Container (MSC) e com serviços iniciados on-demand, foi possível um boot de aproximadamente quatro segundos.

Trouxemos tudo que o leitor precisa saber para fazer uma instalação simples e ter seu servidor JBoss iniciado em modo Standalone. No modo Domain, tivemos o objetivo de trazer uma visão geral da nova arquitetura com a utilização de Domain Controller, Host Controller, grupos de servidores e suas configurações. O exemplo prático mostra a utilização de todos estes componentes e suas relações, ajudando o leitor no entendimento destes conceitos.

Além disso, mostramos um pouco das novas formas de administração como o CLI e a console web, que disponibilizam formas mais intuitivas, fáceis e inovadoras para gerenciamento e atualização de configurações do JBoss AS 7.

Para finalizar, é válido informar que o JBoss AS 7 está tendo um impacto muito positivo, principalmente na comunidade, mas precisa da participação e contribuição de desenvolvedores e usuários. A comunidade é o poder do open source. Deste modo, utilize os fóruns, abra Jiras, estude as documentações e wikis. O www.jboss.org está aí para todos nós, grupo de usuários JBoss.

JBoss Application Server: Deploy e o gerenciamento de componentes modulares desenvolvidos utilizando o framework OSGi

Neste artigo, veremos como o JBoss AS 7 suporta o deploy e o gerenciamento de componentes modulares desenvolvidos utilizando o framework OSGi. Analisaremos um simples exemplo de como implantar um Bundle OSGi. Preparamos também um pequeno guia para administradores apresentando algumas das funcionalidades disponíveis nos novos consoles de gerência. Ademais, aproveitamos para divulgar o mais recente release do AS 7, certificado Java EE 6 Full Profile e com inúmeras melhorias no console de gerenciamento.

Este tema é de grande importância para desenvolvedores e administradores de servidores de aplicação que buscam conhecer os recursos oferecidos pelo novo JBoss Application Server. Neste artigo analisaremos o suporte ao framework OSGi e a nova interface de gerência e configuração baseada em linha de comando.

A cada nova release o JBoss AS traz grandes inovações, visando, acima de tudo, fornecer soluções que facilitem e impulsionem a produtividade e a qualidade do desenvolvimento para a plataforma Java EE. O JBoss AS 7 segue essa linha de inovação e qualidade, oferecendo, em sua versão mais recente, um servidor de aplicação 100% certificado Java EE 6 Full Profile. Além da plataforma Java EE, o AS 7 oferece suporte a outras especificações. É o caso do suporte ao framework OSGi, que abordaremos neste artigo. Por fim, não podemos deixar de citar os notáveis avanços e melhorias relacionados à gerência e configuração trazidos pelos novos consoles do servidor.

Desenvolver aplicações modulares para a plataforma Java nunca foi uma tarefa trivial. De fato, até o presente momento, a Java SE não oferece suporte adequado a esse tipo de desenvolvimento. No entanto, existem várias iniciativas em torno da plataforma com o objetivo de prover um sistema modular que suporte, tanto o desenvolvimento, quanto a execução de componentes modulares. O projeto Jigsaw [1], proposto originalmente com o objetivo de tornar a própria distribuição do JDK modular, é uma das principais iniciativas em discussão no momento. Outras propostas como as JSRs 277 [2] e 294 [3] também visam estender e preparar a linguagem, bem como a Máquina Virtual Java para suportarem a programação modular. Outra importante iniciativa nesse mesmo sentido é o framework OSGi [4]. De todas as propostas com esse objetivo, o framework OSGi tem sido considerada a mais madura, estável e robusta.

Como vimos na primeira parte deste artigo, todo o Kernel do AS 7 foi remodelado seguindo a premissa de um projeto 100% modular. Para atingir esse objetivo os desenvolvedores criaram uma camada leve e robusta chamada JBoss Modules, que atua como o núcleo do novo Servidor de Aplicação JBoss. Mesmo não sendo seu objetivo primário, JBoss Modules tem provado ser uma implementação viável de um ambiente de execução modular para a plataforma Java.

Nesta segunda parte do artigo não abordaremos os conceitos relacionados à modularidade ou sobre o framework OSGi. Entretanto, pretendemos mostrar como o JBoss AS 7 fornece suporte a OSGi através de sua implementação JBoss OSGi. Veremos como implantar um Bundle OSGi juntamente com os demais artefatos comumente instalados no servidor de aplicação.

Para mais detalhes sobre modularidade na plataforma Java, consulte o artigo “Modularidade em Java”, publicado na edição 85 da Java Magazine.

Além do suporte a OSGi oferecido pelo AS 7, iremos explorar o novo console de administração baseado em linha de comando (CommandLineInterface). O novo console CLI é mais uma ferramenta disponível para o administrador realizar e automatizar diversas tarefas de configuração e gerência do servidor de aplicação.

Neste artigo, usaremos em nossos exemplos a release 7.1.1.Final – de codinome “Brontes” – do AS 7. Como destacado no artigo anterior, a versão final do AS 7 é 100% certificada Java EE 6 Full Profile, conforme consta na página “Java EE Compatibility” [5] no site da Oracle. A última release do AS 7 pode ser obtida na página de download do projeto, em jboss.org/jbossas/downloads/ (veja a Figura 1). Lançada em Março deste ano, ela é uma versão de manutenção da versão 7.1.0.Final, e conta com aproximadamente 260 issues resolvidas e uma série de melhorias relacionadas a gerência e configuração através do console web. Dentre essas melhorias podemos citar: gerenciamento do serviço de Cache Distribuído Infinispan; gerenciamento do mecanismo de cluster JGroups; visualização de propriedades do Sistema Operacional; gerenciamento do serviço de e-mail embutido no AS; possibilidade de habilitar e desabilitar deployments; entre outras.

JBoss
    AS 7.1 Final release
Figura 1. JBoss AS 7.1 Final release.

JBoss OSGi

O principal artefato definido pelo framework OSGi é chamado de Bundle. O bundle trata-se de uma unidade modular que pode ser implantada em um ambiente OSGi, ou seja, instalada em uma plataforma que implementa a especificação do framework OSGi [6].

Antes de prosseguir com nosso raciocínio, precisamos definir o que é um módulo ou unidade modular. Segundo Mark Reinhold [7]: “Um modulo é uma coleção de tipos Java (ex. classes e interfaces) com nome, um número de versão opcional, e uma descrição formal de seu relacionamento com outros módulos. Além de tipos Java, um módulo pode incluir arquivos de recursos, configuração, bibliotecas nativas, e comandos nativos...”.

Nesse contexto podemos afirmar que um Bundle OSGi nada mais é do que um módulo, um arquivo JAR contendo classes e recursos que juntos fornecem a implementação de uma determinada funcionalidade ou serviço Java. Como diferencial, todo Bundle possui um arquivo de manifesto que o descreve (localizado sob a estrutura META-INF/MANIFEST.MF). Este manifesto possui diretivas (conhecidas como headers) definidas pelo framework para gerenciar o ciclo de vida do Bundle quando implantado em uma plataforma OSGi.

Dada essa breve introdução sobre o que é um módulo/bundle no contexto da plataforma OSGi, falaremos agora sobre a implementação do framework oferecida pelo JBoss AS 7.

A implementação do JBoss OSGi [8] disponível no AS 7 é 100% compatível com a versão 4.2 do framework OSGi. Isso significa que você pode realizar o deploy de Bundles OSGi juntamente com os demais serviços e aplicações instalados no servidor de aplicação. O JBoss OSGi passou em todos os testes TCK, e para as próximas versões buscará a certificação para a versão 4.3 do framework fornecida pela OSGi Alliance.

Technology Compatibility Kit: TCK é uma suite de testes com o objetivo de checar a compatibilidade de determinada implementação com sua respectiva especificação. Para a plataforma Java especificamente, o kit de compatibilidade é chamado de Java Compability Kit. O JCK integra um conjunto composto por três partes:

  • A especificação em si – Java Specification Request (JSR). Como exemplo podemos citar a JSR 299 –Contexts and Dependency Injection, que define a especificação para Injeção de Dependência na plataforma Java;
  • A implementação de referência da JSR (Reference Implementation – RI). Como exemplo podemos citar o Weld, que é a implementação de referência da JSR 299;
  • A suite de testes (Technology Compatibility Kit – TCK) fornecida pelo líder da JSR no Java Community Process (JCP).

Dessa forma, a implementação que passar em 100% dos testes definidos no TCK pode ser considerada compatível com tal especificação.

O JBoss OSGi utiliza a implementação Apache Felix como resolver. No Framework OSGi, o resolver é o componente responsável por computar o grafo de dependências entre os bundles e seus respectivos classloaders. Ele utiliza as diretivas (headers) declaradas no arquivo de manifesto do Bundle para materializar os requisitos das dependências. Internamente, após a análise dessas diretivas, o resolver delega ao JBoss Modules (camada mais baixo nível do núcleo do AS 7) o trabalho de carregamento dos módulos propriamente ditos.

Outro aspecto interessante do JBoss OSGi é a possibilidade de integração entre componentes e serviços não OSGi, isto é, Java EE padrão, com módulos OSGi. Por definição, não é possível acessar um componente ou serviço Java EE a partir de um módulo OSGi ou vice-versa. Contudo, no AS 7, isso é possível através da camada de integração com o JBoss Modules, oferecida pelo container JBoss MSC. Dessa forma pode-se acessar componentes e serviços Java EE (Filas JMS, CDI Beans, EJBs, Servlets, etc.) a partir de módulos OSGi e vice-versa.

Vale ressaltar que para o AS 7 todo bundle OSGi é um módulo (gerenciado pelo JBoss Modules), mas nem todo módulo é um bundle OSGi.

Apesar de ser um projeto isolado, o JBoss OSGi vem totalmente integrado ao AS 7. O deploy de um bundle OSGi pode ser realizado da mesma forma como é feito para aplicações e serviços Java no JBoss. Basta colocar o bundle no diretório AS7_HOME/<modo[standalone|domain]>/deployments. Assim como acontece com outros serviços no AS 7, por padrão, o módulo OSGi é ativado sob demanda (comportamento controlado pelo atributo activation na Listagem 1). Dessa forma o JBoss ativa o suporte a OSGi apenas quando existe um bundle implantado, tornando o respectivo serviço disponível para uso.

O subsistema OSGi é configurado assim como qualquer outro, através do descritor da configuração standalone ou domain. A Listagem 1 contém um exemplo de configuração do subsistema OSGi no modo standalone do AS 7. Essa configuração é dividida em três partes:

  • OSGi Configuration Admin Service: responsável pela configuração propriamente dita de aplicações e serviços OSGi;
  • OSGi Framework Properties: define as propriedades gerais do framework;
  • Preloaded Modules/Bundles: define quais módulos/bundles devem ser pré-carregados na inicialização do subsistema. Qualquer módulo (AS7_HOME/modules) ou bundle (AS7_HOME/bundles) pode ser carregado na inicialização do subsistema OSGi.
Listagem 1. Configuração do subsistema OSGi. Descritor AS7_HOME/standalone/configuration/standalone.xml.
<subsystem xmlns="urn:jboss:domain:osgi:1.2" activation="lazy">
        <properties>
          <property name="org.osgi.framework.startlevel.beginning">
            1
          </property>
          </properties>
        <capabilities>
          <capability name="javax.servlet.api:v25"/>
          <capability name="javax.transaction.api"/>
          <capability name="org.apache.felix.log" startlevel="1"/>
          <capability name="org.jboss.osgi.logging" startlevel="1"/>
          <capability name="org.apache.felix.configadmin" startlevel="1"/>
          <capability name="org.jboss.as.osgi.configadmin" startlevel="1"/>
        </capabilities>
      </subsystem>

Para testar o deploy de um bundle OSGi no AS 7 usaremos o exemplo helloworld-osgi fornecido pelo pacote JBoss AS 7 Quickstarts. Esse pacote está disponível para download na mesma página onde se obtém o binário do AS 7 (jboss.org/jbossas/downloads). Então, faça o download do pacote jboss-as-quickstarts-7.1.0.Final e em seguida extraia o arquivo na raiz do AS (AS7_HOME).

O JBoss AS 7 Quickstarts fornece um conjunto de exemplos prontos para uso em seu ambiente local. Os exemplos estão organizados em diretórios de acordo com a implementação do serviço/especificação fornecida pelo AS 7. Todos os exemplos possuem código fonte (diretório src), um roteiro de utilização (README.html) e o descritor do projeto (pom.xml) para permitir o build utilizando a ferramenta Apache Maven [9]. Os exemplos contidos no pacote jboss-as-quickstarts também estão documentados no guia “The Getting Started Developing Applications Guide”, disponível na documentação online do AS 7 [10].

Antes de prosseguirmos com o teste precisamos ter uma instância do AS 7 em execução. Para isso, entre no diretório AS7_HOME e faça o startup do servidor em modo standalone da seguinte forma:

bin/standalone.sh

Após a conclusão do startup do servidor, conforme ilustra a Figura 2, entre no diretório do exemplo (AS7_HOME/jboss-as-quickstarts-7.1.0.Final/helloworld-osgi/) e faça o build do projeto utilizando a ferramenta Apache Maven.

Conclusão
    do startup do AS 7 em modo standalone
Figura 2. Conclusão do startup do AS 7 em modo standalone.

Caso ainda não possua o Maven instalado em sua estação de trabalho, faça o download da ferramenta no site da Apache [9] e em seguida efetue a instalação padrão.

Na raiz do diretório AS7_HOME/jboss-as-quickstarts-7.1.0.Final/helloworld-osgi, execute o comando:

mvn package jboss-as:deploy

Durante o primeiro build do projeto o Maven realiza o download de várias bibliotecas (dependências). Esse processo pode levar certo tempo dependendo de sua conexão com a Internet. Aguarde a conclusão do processo de build conforme ilustra a Figura 3.

Processo
    de build do bundle helloworld-osgi
Figura 3. Processo de build do bundle helloworld-osgi.

Em seguida observe o console onde o servidor foi iniciado. O log do servidor deve apresentar uma saída semelhante à que mostra a Figura 4, indicando que o bundle jboss-as-helloworld-osgi-7.1.0.Final.jar (gerado pelo processo de build do Maven) foi implantando com sucesso. Note que o subsistema OSGi é inicializado sob demanda logo após o AS receber o evento de deploy do bundle (indicador “1” na figura). Depois de o subsistema ter sido carregado (indicador “2”), o deploy do bundle helloworld-osgi é iniciado (indicador “3”).

Startup
    do subsistema JBoss OSGi e hotdeploy do bundle helloworld-osgi
Figura 4. Startup do subsistema JBoss OSGi e hotdeploy do bundle helloworld-osgi.

O deployment do bundle também pode ser visualizado ou feito manualmente através do console web, que pode ser acessado pelo endereço http://localhost:9990/. A Figura 5 mostra a visão do deployment do bundle helloworld-osgi que acabamos de fazer.

Gerenciamento
    de deployment do AS 7
Figura 5. Gerenciamento de deployment do AS 7: visualização do bundle helloworld-osgi após o hotdeploy realizado pelo processo de build do Maven.

Para concluir esse tópico, lembramos que o web console do AS 7 permite gerenciar todos os bundles e serviços OSGi implantados no servidor, bem como a própria configuração do framework. A Figura 6 mostra a visão Runtime do subsistema OSGi. Em destaque podemos ver que é possível iniciar ou parar qualquer bundle ou serviço através das ações Start/Stop.

Gerenciamento
    do subsistema OSGi através do console web do AS 7
Figura 6. Gerenciamento do subsistema OSGi através do console web do AS 7.

Pequeno guia para administradores

O JBoss AS 7 traz três novas formas de gerenciar e configurar o servidor de aplicação. Os antigos consoles Admin Console, JMX Console e Web Console foram substituídos por uma interface web bem mais amigável, que chamamos de Web Management Console, ou simplesmente console. O twiddle, script que interage remotamente com o MBean Server do JBoss AS utilizando JMX, também não faz mais parte desta versão. Ele foi substituído por um cliente que pode ser utilizado via linha de comando com um terminal denominado Command Line Interface (CLI). Caso o usuário prefira manter a configuração do servidor de forma mais tradicional, ainda é possível realizar alterações diretamente nos arquivos de configuração em formato XML, o que era bastante comum nas versões anteriores. O usuário pode escolher a opção que mais lhe for conveniente, pois qualquer uma delas terá o mesmo resultado, persistindo as alterações nos arquivos XML.

Para que o leitor possa entender como utilizar essas três opções, bem como conhecer como realizar configurações mais avançadas, faremos uma pequena introdução a cada um delas.

Dynamic Model Representation

Tanto o console quanto o CLI utilizam uma nova sintaxe de representação de objetos Java. Esta é chamada de DMR (Dynamic Model Representation), e todo administrador precisa compreendê-la.

Para demonstrar um exemplo dessa nova sintaxe, iremos comparar a configuração do subsistema de log em um arquivo XML com sua representação DMR exibida no CLI. Esse subsistema, mostrado em nosso exemplo, está disponível no modo standalone, que por padrão utiliza o arquivo AS7_HOME/standalone/configuration/standalone.xml. Veja a Listagem 2.

Listagem 2. Subsistema de log em arquivo XML.
<subsystem xmlns="urn:jboss:domain:logging:1.1">
        <console-handler name="CONSOLE">
          <level name="INFO"/>
            <formatter>
              <pattern-formatter pattern="%d{HH:mm:ss,SSS} %-5p [%c] (%t) %s%E%n"/>
            </formatter>
          </console-handler>
        ...
      </subsystem>

Antes de qualquer coisa, precisamos de uma instância do servidor em execução. Para isso, inicie o servidor no modo standalone executando o script de inicialização disponível em AS7_HOME/bin.

$ ./standalone.sh

Em nosso exemplo, estamos utilizando um sistema Linux. No entanto, caso esteja utilizando Windows, substitua o arquivo .sh pelo arquivo .bat, também disponível no diretório bin de sua instalação.

Em seguida, inicie o CLI:

$ ./jboss-admin.sh –connect

Uma vez conectado, execute o comando conforme a primeira linha da Listagem 3. Em seguida observe o resultado que aparece entre as chaves ({...}) logo abaixo deste comando.

O conteúdo que aparece entre as chaves ({...}) logo após submeter o comando é sempre o seu resultado.

Listagem 3. Configuração do subsistema de log em sintaxe DMR usando o CLI.
 [standalone@localhost:9999 /] /subsystem=logging/console-handler=CONSOLE:read-resource
      {
          "outcome" => "success",
          "result" => {
              "autoflush" => true,
              "encoding" => undefined,
              "filter" => undefined,
              "formatter" => "%d{HH:mm:ss,SSS} %-5p [%c] (%t) %s%E%n",
              "level" => "INFO",
              "target" => "System.out"
          }
      }

Graças à DMR, qualquer alteração realizada no CLI, ou mesmo via console, será imediatamente refletida nos arquivos XML, e ficarão disponíveis instantaneamente. Como exemplo, execute o comando conforme a primeira linha da Listagem 4 para alterar o nível de log do servidor.

Listagem 4. Alterando o nível de log do servidor para DEBUG.
 [standalone@localhost:9999 /] /subsystem=logging/console-handler=CONSOLE:write-attribute(name=level,value=DEBUG)
      {"outcome" => "success"}

Em seguida, abra o arquivo AS7_HOME/standalone/configuration/standalone.xml e confira a alteração que acabou de realizar. A Figura 7 mostra esta alteração.

Alteração no nível de log
Figura 7. Alteração no nível de log.

Command Line Interface

O CLI traz alguns comandos muito semelhantes aos comandos de um sistema operacional Linux, e permite a navegação nos subsistemas como se fossem diretórios em um sistema de arquivos. Porém, para não confundir os recursos do AS com diretórios, entenda cada recurso como um node (nó). Portanto, ao utilizar CLI, comandos como cd e ls funcionam e permitem a troca de nodes ou listar seu conteúdo. Outro detalhe importante é que o autocomplete com a tecla <tab> também está presente, bem como o histórico de comandos utilizando os cursores das flechas para cima e para baixo. Veja a Figura 8 para um exemplo.

Exemplo de comandos cd, ls e autocomplete com a tecla <tab>
Figura 8. Exemplo de comandos cd, ls e autocomplete com a tecla <tab>.

Na Figura 8 pode-se observar o acesso a um node do tipo subsystem utilizando o recurso de autocomplete – acionado pela tecla <tab> – para listar o seu conteúdo. Deste modo, foram exibidos todos os subsistemas presentes na configuração de standalone. Nesse ponto é possível acessar o node do subsistema datasources, por exemplo, e em seguida listar o seu conteúdo empregando o comando ls.

O comando help pode ser utilizado a qualquer momento para obter a lista completa de operações. Também é possível obter ajuda para um comando específico. Para isso basta executar o comando seguido do parâmetro ‘--help’ (ex. ‘deploy --help’ para obter ajuda sobre o comando ‘deploy’).

Assim como em um sistema de arquivos, a “/” também é adotada para separar níveis. O node “/” representa a raiz dos recursos, ou seja, o ponto inicial da árvore de recursos. Caso queira verificar os recursos disponíveis em um determinado nível ou subsistema, execute o comando :read-resource. Caso prefira ver todos os recursos dos níveis abaixo recursivamente, utilize :read-resource(recursive=true). A Figura 9 traz um exemplo da leitura dos recursos do subsistema datasources. Este comando também pode ser usado em conjunto com a “/” e o caminho completo de onde se deseja ler os recursos. Por exemplo: se você quiser verificar os recursos presentes na raiz, digite “/:read-resource”; e se quiser verificar os recursos de um determinado subsistema, não é necessário acessá-lo utilizando o comando cd, basta informar o caminho completo para o mesmo, como apresentado na Listagem 4.

Para alterar atributos, existe o comando :write-resource(name=<nome-do-atributo>,value=<novo-valor>. Empregamos este comando na Listagem 3 para exemplificar alterações instantâneas em arquivos XML via CLI.

Exemplo do comando read-resource
Figura 9. Exemplo do comando read-resource.

Além disso, alguns subsistemas possuem comandos específicos, sendo possível utilizar o comando :read-operation-names para descobri-los. Veja na Figura 10 os comandos disponíveis para o recurso ExampleDS, presente por padrão no modo standalone. Entre eles, :read-operation-description, que retorna a descrição de uma dada operação.

Comando :read-operation-names
Figura 10. Comando :read-operation-names

Web Management Console

Toda configuração e gerenciamento do JBoss AS 7 também pode ser realizada utilizando o Web Management Console. Este console tem passado por diversas melhorias e evoluções a cada nova release, tornando a gerência do AS ainda mais fácil e amigável.

Antes de iniciar o exemplo, abra o arquivo standalone.xml e verifique os valores padrão do datasource ExampleDS e do subsistema de log. Depois de executar os passos descritos a seguir, abra novamente este arquivo e compare os resultados.

Para exercitar e também conhecer um pouco mais das funcionalidades disponíveis no console, faremos algumas mudanças na configuração de dois subsistemas. No subsistema de log, faremos a alteração do nível de log, e no subsistema de datasources faremos alterações no pool de conexões JDBC do datasource ExampleDS (disponível por padrão no AS 7). Deste modo, utilizando a mesma instância dos exemplos do CLI, acesse o console através da URL http://localhost:9990/console/. Em seguida clique no menu Profile, localizado no canto superior direito, expanda a opção Core, localizada no menu lateral esquerdo, e por fim clique em Loggers. Feito isso, você terá acesso ao subsistema de log, conforme mostra a Figura 11.

Agora clique no botão Edit para entrar no modo edição, selecione o nível de log na lista Log Level (no nosso caso, escolha o nível DEBUG) e clique em Save. Após realizar esta operação, abra o arquivo AS7_HOME/standalone/configuration/standalone.xml (exibido na Listagem 5) e verifique o resultado da alteração.

Editando o nível de log via console
Figura 11. Editando o nível de log via console.
Listagem 5. Configuração do nível de log após alterações via console.
<subsystem xmlns="urn:jboss:domain:logging:1.1">
      ...
       <root-logger>
        <level name="DEBUG"/>
         <handlers>
         <handler name="CONSOLE"/>
         <handler name="FILE"/>
         </handlers>
       </root-logger>
      </subsystem>

Neste momento faremos a alteração no pool de conexões do datasource ExampleDS. Um datasource gerencia as conexões abertas com um determinado banco de dados e o pool de conexões é simplesmente o número de conexões disponíveis para uso neste datasource. É sempre interessante delimitar o número máximo de conexões que podem ser abertas para evitar que a aplicação tente utilizar mais conexões que o banco possa suportar.

Para realizar esta configuração, clique em Datasources, que está localizado no menu lateral esquerdo dentro da opção Connector. Note que será exibido o datasource ExampleDS. Assim, clique na aba Pool e depois no botão Edit para entrar no modo edição. Em seguida, basta preencher os campos Min Pool Size e Max Pool Size com os novos valores para o pool de conexões. A Figura 12 mostra esses passos.

Alterando o pool de conexões do datasource ExampleDS
Figura 12. Alterando o pool de conexões do datasource ExampleDS.

Após salvar as alterações, observe no canto superior direito (Figura 13) o espaço de notificação do console (Messages). Note que há duas mensagens disponíveis no momento. Para visualizar estas mensagens clique no link Messages para abrir o painel de notificações. Nesse momento ele informa que as propriedades do datasource ExampleDS foram atualizadas e salvas com sucesso.

Histórico de operações
Figura 13. Histórico de operações.

Há várias outras funcionalidades disponíveis no console de gerenciamento do AS 7. Além das configurações do núcleo do servidor, praticamente todos os subsistemas podem ser configurados e/ou gerenciados visualmente sem que haja necessidade de intervenção manual e direta nos arquivos XML. Além da configuração do profile, o console permite a visualização do estado corrente do servidor e seus subsistemas através da visão Runtime. Nessa visão também é possível encontrar informações como: métricas da JVM, propriedades do sistema operacional, utilização do pool de conexões dos datasources etc. Por exemplo, para visualizar informações sobre o estado da JVM, acesse o console conforme mostra a Figura 14. Infelizmente não é possível cobrirmos todas as funcionalidades disponíveis no console, no entanto temos certeza de que não levará muito tempo para que o leitor se acostume com elas em seu dia-a-dia.

Estado
    da Máquina Virtual Java em Runtime
Figura 14. Estado da Máquina Virtual Java em Runtime.

Conclusão

Como foi visto na primeira parte do artigo, tanto o modo standalone quanto o modo domain do JBoss AS 7 podem possuir um conjunto predefinido de subsistemas chamado de profile. Cada subsistema fornece suporte à determinada tecnologia ou especificação da plataforma Java EE, além de outras funcionalidades. Um exemplo dessas funcionalidades adicionais é o suporte oferecido ao framework OSGi apresentado aqui.

Nesta segunda parte do artigo mostramos alguns conceitos introdutórios sobre modularidade e sobre o framework OSGi. Também foi demonstrado como realizar o deploy de um simples bundle OSGi. Em seguida descrevemos um guia prático de administração do servidor utilizando os novos consoles de gerência (CLI e Web Console).

Como pôde ser notado, a última release do AS 7 trouxe grandes melhorias e ainda mais opções de gerência a partir dos novos consoles. Contudo, além da constante inovação oferecida a cada nova release, podemos afirmar que o desempenho e a facilidade de gerência do servidor também são prioridades da equipe responsável pelo seu desenvolvimento.

Para concluir esta série, encorajamos o leitor a fazer o download do último release do JBoss AS 7 juntamente com o pacote de exemplos quickstarts [10] e testar este incrível servidor de aplicação. Vale a pena conferir!

Saiu da DevMedia!

  • CDI 2.0: avanços no Java EE e além:
    Injeção de dependências é um pilar do desenvolvimento moderno; com CDI 2.0, esta ferramenta será disponível para desenvolvedores Java SE. A nova versão de CDI também traz avanços para programação assíncrona, que é um tópico muito relevante para a performance de uma aplicação.
  • O que é JWT?:
    Você sabe o que é JWT? Talvez este seja um dos termos que você mais tenha escutado nos últimos meses, não é verdade? Mas, por que JWT? Qual a importância dele no desenvolvimento de software hoje em dia? Onde o JWT é utilizado?
  • Vale a pena ver CSS de novo:
    O programador está sempre preocupado em utilizar bem o seu tempo. Com isso em mente, saiba que os recursos mais modernos do CSS3 podem nos ajudar a nos dedicarmos mais ao back-end da aplicação, como veremos neste DevCast.

Saiba mais sobre jBoss ;)

  • Curso de JBoss: Introdução e Aplicação MVC completa:
    Neste curso de JBoss, composto por uma sequência de video aulas, iremos desvendar este que é um dos mais conhecidos e utilizados servidores de aplicação java do mercado opensource. Vamos passear por dentro deste poderoso servidor de aplicativos (application server) e demonstrar em detalhes seu funcionamento.
  • JBoss ESB:
    Este artigo apresenta uma visão geral sobre o JBoss ESB, possibilitando que desenvolvedores de todos os níveis possam ter um primeiro contato com a forma de utilização e conceitos a respeito de Arquitetura Orientada a Serviços – SOA, entre eles: Enterprise Services Bus - ESB.

Links

http://openjdk.java.net/projects/jigsaw
[1] Jigsaw Project – OpenJDK.

http://jcp.org/en/jsr/detail?id=277
[2] JSR 277: Java Module System.

http://jcp.org/en/jsr/detail?id=294
[3] JSR 294: Improved Modularity Support in the Java Programming Language.

http://www.osgi.org/About/HomePage
[4] OSGi Alliance.

http://www.oracle.com/technetwork/java/javaee/community/jboss-ee6-full-compat-1525034.html
[5] Oracle Java EE Compatibility.

http://www.osgi.org/Release4/HomePage
[6] OSGi Service Platform Release 4.

http://cr.openjdk.java.net/~mr/jigsaw/notes/jigsaw-big-picture-01
[7] Project Jigsaw: The Big Picture — DRAFT 1.

http://www.jboss.org/jbossas/osgi
[8] JBoss OSGi.

http://maven.apache.org/
[9] Apache Maven.

https://docs.jboss.org/author/display/AS7/Getting+Started+Developing+Applications+Guide
[10] The Getting Started Developing Applications Guide.