A1Criando um módulo de negócio Capítulo 27 Aplicação dividida em módulos - Introdução Como já foi muito bem detalhado no Capítulo IV, o jcompany Developer Suite pode ser compreendido como uma solução de reuso em nível arquitetural. Essa arquitetura foi muito bem explicada e detalhada ao longo do livro. O padrão "MVC" ajuda-nos a compreender e separar camadas de nossa aplicação de uma forma que, independentes de frameworks ou tecnologias utilizadas, consigamos definir o papel de cada uma e se necessário, substituir o conteúdo de uma camada sem que as outras sofram conseqüências. Essa definição de arquitetura que podemos de chamar de "vertical" (camada sobre camada) é muito bem entendida e trabalhada em todo o jcompany Developer Suite. Quando a aplicação cresce a tal ponto que parece haver várias "sub-aplicações" dentro dela, é a hora de dividir aplicação em módulos. Então vem a pergunta: A arquitetura "MVC" já não divide a aplicação? Sim, mas divide em um nível de camadas "vertical". Então que divisão modular seria essa? Essa divisão passa ser em um nível "horizontal", uma divisão dentro da própria camada, uma divisão com módulos de negócios, que são independentes entre si e reutilizáveis para o todo. - Módulos de Negócios A divisão de um programa ou camada de uma arquitetura de programa em partes menores deve ter o tamanho suficiente para ser compreendida isoladamente, em paralelo a isso, a arquitetura da aplicação deve ser simples o suficiente para que compreendamos como as peças se encaixam. Podemos definir um módulo de negócio como uma decomposição de um sistema em subsistema. Modularizar ajuda a lidar com a dimensão e complexidade de sistemas, facilitando o design, entendimento, testes, tudo através de encapsulamento e abstração. Seguem alguns conceitos que ajudanos a entender mais a necessidade de modularizar os nossos negócios: o o o Separação de Interesses e Ponto Único de Referência: Responsabilidades diferentes e não relacionadas devem ser separadas num sistema, itens e lógicas de negócios correlatos são declarados e definidos em um único ponto. Divisão e Conquista: Dividir todo o negócio em pequenas partes é essencial para lidar com a complexidade. Encapsulamento e Abstração: Agrupamento dos elementos definindo barreiras delimitadas entre abstrações, provendo assim, uma concepção conceitual clara do negócio. Outro ponto que podemos citar com relação à abstração é que determinadas lógicas podem ser "protegidas" em um módulo, onde o mesmo disponibiliza apenas interfaces para acesso aos seus métodos. Criando um módulo de negócios - Definição do problema Vamos criar um módulo de negócios que vai cuidar da contabilidade da empresa. A lógica de negócio de uma contabilidade é idêntica para qualquer ramo, na visão mais simples de uma contabilidade temos lançamentos que envolvem uma conta contábil e um valor. Em um primeiro momento esse módulo vai ser utilizado para contabilizar o salário líquido dos funcionários da nossa "Folha de Pagamento" e em outras situações futuras para contabilizar todos os lançamentos da "Folha de Pagamento" e de aplicações de pagadoria (contas a pagar), recebimento de clientes, dentre outras. A especificação de nosso Caso de Uso pode ser vista no diagrama da Figura G27.1
Figura G27.1. Caso de Uso "Gerência Contábil" Definimos apenas uma classe de entidade denominada "Lancamento". Decidimos dessa forma para fins didáticos do módulo de negócios. É claro que em uma situação real teríamos mais entidades, como cadastro de contas, centro de custos, histórico contábil e outros. - Criando o módulo O jcompany já disponibiliza um wizard para criação do módulo de negócios, criando a aplicação, pacotes definindo a separação da arquitetura e já configurando uma aplicação "Mestre" que vai utilizar esse módulo. 2. No Eclipse use o atalho "Ctrl+n" e selecione "Criar novo módulo de negócio jcompany" dentro de "Powelogic jcompany Code Generator".
Capítulo G27 Figura G27.2. Acionando o wizard do jcompany para criação do módulo 3. Clique em "Next" e preencha os dados conforme Figura G27.3. Figura G27.3. Criando o módulo de negócios. #1. Defina o nome do módulo como "rhtutorial_contabil". Nome muito sugestivo para o nosso propósito. #2. Por padrão usaremos o pacote base "com.empresa.rhtutorial_contabil". #3. Arquivo de template de base para geração de um módulo de negócio. #4. Sigla para nosso módulo. Nesta documentação nós vamos definir "ctb" sigla de contábil.
#5. Selecione a "aplicação principal" de nosso módulo de negócios, no nosso caso o projeto rhtutorial. Este campo é um facilitador do wizard para configurarmos uma primeira aplicação mestre, entretanto o módulo pode participar de várias aplicações. Para configurar o módulo manualmente, basta incluir sua declaração de módulo no arquivo "pom.xml" da aplicação parent conforme mostra a Figura G27.4 e sua declaração de dependência no arquivo "pom.xml" nas aplicações que a referenciam conforme Figura G27.5. * Figura G27.4. Incluindo módulo na aplicação principal. Figura G27.5. Declarando a dependência pelo módulo. - Criando a entidade do módulo de negócio Agora que criamos o módulo de negócio na aplicação "rhtutorial", vamos fazer a configuração do mesmo. Para começar devemos seguir os passos abaixo para criar a entidade. 4. Clique com o botão direito sobre o pacote "com.empresa.rh_tutorial.entity", vá em "New" e crie uma nova classe com o nome "Lancamento". Figura G27.6. Criando a entidade Lancamento. 5. Vamos acionar o wizard do jcompany de Mapeamento Objeto-Relacional. Preencha os dados conforme a Figura G27.7 e clique em "Finish". * Lembrando que esse passo só é necessário para configurar a dependência do módulo de negócios manualmente em diversas aplicações. Na aplicação mestre selecionada no wizard de criação do módulo esse passo não é necessário.
Capítulo G27 Figura G27.7. Gerando mapeamento objeto-relacional. 6. Faça a alteração no campo "DATA" do arquivo "Lancamento.java". Figura G27.8. Alterando anotação de data. 7. Altere o método "tostring" de "LancamentoEntity", ajustando o seu retorno. Figura G27.9. Ajustando método "tostring" - Implementando a camada Modelo 8. Crie uma nova "NamedQuery em "LancamentoEntity". Figura G27.10. NamedQuery para retornar lançamentos sumarizados 9. Crie a classe "LacamentoDAO" conforme o código a seguir. Nela criamos um método para emitir balancete contábil que será invocado após o processamento da folha (ou em qualquer outro momento) e um método para inserir lançamentos contábeis. package com.empresa.rhtutorial_contabil.persistence.jpa; @PlcAggregationDAOIoC(LancamentoEntity.class) @SPlcDataAccessObject @PlcQueryService public class LancamentoDAO extends PlcBaseJpaDAO { @Inject private PlcBaseContextVO context; @Inject @QPlcDefault private PlcIocModelUtil iocmodelutil; @SuppressWarnings("unchecked") public List<Lancamento> emitebalanceteporcentrocusto(date datainicial,
Date datafinal) { Query query = apicreatequery(context, LancamentoEntity.class, annotationpersistenceutil.getnamedquerybyname(lancamentoentity.class, "sumarizalancamentoporradicalcontacentrocusto").query()); return query.setparameter("datainicial", datainicial).setparameter("datafinal", datafinal).getresultlist(); } } public void inserelancamento(string centrocusto, String radicalconta, Date data, BigDecimal valor) { } LancamentoEntity lancamento = new LancamentoEntity(); lancamento.setcentrocusto(centrocusto); lancamento.setradicalconta(radicalconta); lancamento.setdata(data); lancamento.setvalor(valor); super.insert(context, lancamento); Código G27.1 Conteúdo da classe LancamentoDAO - Criando o acesso ao módulo de negócios Para expor o nosso negócio para outras aplicações, devemos disponibilizar nossos métodos através de nossa fachada. O jcompany já gera para nós uma interface padrão em nossa fachada. Vamos editá-la e assinar os dois métodos do nosso "Caso de Uso" 10. Edite a interface "ICtbFacade" conforme Figura G27.11. Figura G27.111. Interface de acesso ao módulo de negócios Contábil. 11. Vamos agora implementar a interface. Edite a classe "CtbFacadeImpl" que também foi criada pelo jcompany e insira o código da Figura G27.122.
Capítulo G27 Figura G27.132. Implementando os métodos da interface. Testando o módulo Para testar o módulo de negócios vamos aproveitar o Caso de Uso "CalculaFolha" que foi implementado em capítulos anteriores. 1. Declare na classe "CalculaFolha" o objeto de fachada de nosso módulo de negócios e crie um método para pegá-lo conforme Código G27.2. public class CalculaFolha { //... @Inject private PlcIocFacadeUtil iocfacadeutil; private ICtbFacade ctbfacade; public ICtbFacade getctbfacade() { if (ctbfacade == null) { ctbfacade = iocfacadeutil.getfacadespecific(ictbfacade.class); } return ctbfacade; } Código G27.3 Conteúdo da classe LancamentoDAO Altere o método "calculafolhafuncionario" da classe "CalculaFolha" para quando incluir um "ProventoDesconto" de salário líquido, incluir também um lançamento contábil. Conforme Figura G27.143 Figura G27.153. Alterando o método "calculafolhaumfuncionario" para inserir lançamento contábil. 2. Realize duas alterações. Adicione um campo em uma "NamedQuery" e em um construtor. Figura G27.16. Alterando "NamedQuery" para retornar a Unidade Organizacional em ProventoDescontoEntity
Figura G27.15. Alterando o construtor em FuncionarioEntity adicionando a Unidade Organizacional. 3. Crie a chamada para emitir o balancete. Edite o MB "CalculaFolhaMB" e declare uma lista para que mostremos os lançamentos contábeis na tela. Veja Figura G27.16. Figura G27.16. Criando uma lista para retornar os lançamentos para exibir na tela. 4. Ao final do método "calularfolha()" faça a chamada para emissão do balancete através do objeto de fachada de nosso módulo de negócios. Veja Figura G27.17 Figura G27.17. Atualizando método "calcularfolha()" para chamar a emissão do balancete. 5. Edite o arquivo "calculafolha.xhmlt" e adicione o trecho de código em destaque na figura abaixo. Nele será exibido o balancete com os lançamentos contábeis realizados.
Capítulo G27 Figura G27.18. Atualizando página calculafolha.xhtml para ao calcular a folha, exibir os lançamentos na tela. #1. Controle visual de renderização dos lançamentos contábeis. Só exibe se a lista de lançamentos não for vazia. #2. Iteração na lista de lançamentos para exibição na tela. #3. Conteúdo do lançamento. 6. Execute agora uma liberação completa para o Tomcat e acessa a aplicação rhtutorial via browser. 7. Acesse o menu "Área de TI Esquema DDL- Geração" e execute o código sql abaixo: create table LANCAMENTO ( ID bigint generated always as identity, DATA_ULT_ALTERACAO timestamp not null, CENTRO_CUSTO varchar(3) not null, RADICAL_CONTA varchar(2) not null, DATA date not null, VALOR numeric(11,2), USUARIO_ULT_ALTERACAO varchar(255) not null, VERSAO integer not null, primary key (ID) ); Código G27.3 Script SQL para criação da tabela LANCAMENTO 8. Acesse o menu "Calcular Folha", informe o mês de referencia,clique em "calcular" e veja o resultado. Além das mensagens sobre os dados de cálculo da folha, foram exibidos os lançamentos contábeis. Figura G27.19. Caso de Uso CalculoFolha agora exibindo os lançamentos contábeis.
Considerações Finais Pudemos comprovar que a implementação de um módulo de negócios pode ajudar muito na manutenção e reuso do código, pois toda a lógica envolvida fica junta em um mesmo lugar. Implementamos um exemplo simples, mas que se mostra bastante poderoso, que pode no futuro atender toda a demanda da empresa a respeito de contabilidade.
Capítulo G27 Sumário Neste capítulo discutimos sobre o conceito de um módulo de negócios, a importância de organização do código e todas as vantagens de trabalhar com essa arquitetura. Para exemplificar, criamos uma demanda de Gerência Contábil. Criamos um módulo Contábil, implementamos um Caso de Uso para gerenciar Lançamentos Contábeis, inserindo e retornando lançamentos totalizados por Unidade Organizacional. Para utilização do módulo refatoramos o Caso de Uso "CalculoFolha" para que o mesmo insira os lançamentos e no final do calculo, exiba-os na tela.