Esse artigo faz parte da revista Clube Delphi Edição 101. Clique aqui para ler todos os artigos desta edição

collapse; mso-border-alt: solid windowtext .5pt; mso-yfti-tbllook: 480; mso-padding-alt: 0cm 5.4pt 0cm 5.4pt; mso-border-insideh: .5pt solid windowtext; mso-border-insidev: .5pt solid windowtext" cellSpacing=0 cellPadding=0 width=520 border=1>

Neste artigo veremos

·         Arquitetura de aplicações multicamadas;

·         Vantagens do desenvolvimento DataSnap e COM+;

·         Funcionamento do dbExpress e DataSnap;

·         Aplicações client/server com DataSnap local;

·         Aplicações multicamadas com recursos avançados do COM+, como Object Pooling;

Qual a finalidade?

·         Mostrar como construir aplicações multicamadas baseadas em aplicações client/server.

Quais situações utilizam esses recursos?

·         Mesmo aplicações client/server podem fazer bom uso de técnicas multicamadas. Uma aplicação dbExpress bem escrita é uma aplicação DataSnap local. Qualquer aplicação, seja ela planejada para uma solução corporativa ou não, pode fazer uso das técnicas aqui apresentadas.

 

Resumo do DevMan

         O desenvolvimento com o DataSnap no Delphi passou por várias fases. Entender como funciona o DataSnap internamente, suas vantagens e recursos, é essencial para a construção de aplicações corporativas, sejam elas multicamadas ou client/server. O DataSnap permite a construção de soluções mais robustas, com maior escalabilidade e performance, aliado aos poderosos recursos do COM+.

 

  O desenvolvimento multicamadas com o Delphi é algo encantador. Além de todas as facilidades que temos ao usar esse tipo de arquitetura, que cito a seguir, temos a facilidade do ambiente de desenvolvimento RAD do Delphi. Confesso que não vi até hoje um framework tão produtivo quanto o DataSnap para desenvolver soluções para tal propósito.

  O objetivo deste artigo é apresentar técnicas intermediárias e avançadas de desenvolvimento com o DataSnap do Delphi, para que você definitivamente migre sua solução para multicamadas, mesmo que a solução vá rodar em uma única máquina. Apresentarei duas técnicas para este propósito, a de simular um ambiente multi-tier em client/server e como rodar o servidor como uma library.

  Se o leitor lembrar, na edição 97, vimos como construir nossas primeiras aplicações multicamadas com o Delphi, fazendo chamadas remotas de procedimento usando COM+, sem, no entanto usar banco de dados. Neste artigo vou demonstrar técnicas de desenvolvimento DataSnap, ao mesmo tempo que apresento boas práticas de programação para essa arquitetura, usando agora um banco de dados. Partiremos do pressuposto que o leitor tenha uma aplicação client/server tradicional, com uma aplicação cliente Win32 acessando um servidor Firebird.

 

Protocolos

Quando falamos em aplicações multicamadas, estamos falando em diferentes computadores se comunicando. Isso exige um protocolo. O primeiro passo é escolher qual o melhor protocolo para ser utilizado na comunicação. Atualmente, os protocolos suportados pelo DataSnap são:

  DCOM – Você usa DCOM ao utilizar Remote Data Modules, ou Data Modules remotos. Não é uma boa solução pois não é escalável, visto que seus objetos são state-full, ou seja, para cada cliente há um objeto ativo no servidor, respondendo às requisições;

  COM+ - Originado do MTS, o COM+ é a melhor solução para ambientes corporativos (intranet), pois é mais escalável, visto que seus objetos são state-less, ou seja, cada objeto é destruído no servidor após processar a requisição cliente;

  SOAP ­­– O suporte ao Simple Object Access Protocol surgiu no Delphi 6, e é recomendado quando sua solução precisa ter clientes espalhados pela Internet. É mais lento que o COM+ para ambientes corporativos, justamente por utilizar XML para intercâmbio de dados. Para mais informações sobre DataSnap com SOAP, recomendo a leitura do meu artigo na edição 70;

  WebConnection – descontinuado pois desempenha basicamente a mesma função do SOAP;

  CORBA – formato proprietário que teve a intenção de ser multi-plataforma. Descontinuado, recomendo a utilização do SOAP para estes casos;

  BSSBorland Socket Server, baseado no DCOM, também não recomendado para ambientes corporativos por ser state-full. Substituído pelo TDsDataModule no Delphi 2009;

  Em nossa solução, vamos optar pelo melhor e mais óbvio, o COM+.

 

Arquitetura

  Nada melhor que uma ilustração para representar como é formada uma solução DataSnap. Na Figura 1, temos um diagrama da solução que será construída. Ele servirá como nosso “mapa”, sempre que tiver alguma dúvida sobre qual camada está sendo empregado determinado código, consulte a figura.

 

Figura 1. Solução multicamadas

 

Em uma arquitetura multicamadas, temos vários computadores que desempenham papéis diferentes na solução. É óbvio que você pode usar um único computador para criar a aplicação DataSnap, porém as camadas físicas ainda existirão. Cada processo que roda em diferentes máquinas é também conhecido como camada. Em nossa figura, podemos identificar 3 camadas:

Camada de Dados – é o banco de dados em si, nesse caso, estamos utilizando o Firebird. Para acesso ao banco, o engine utilizado aqui é o dbExpress (nada impede que se utilize outro, como ADO, IBX, Zeos, BDE etc., desde que o DataSet suporte a interface IProviderSupport, discutida a seguir). Uma outra boa solução que recomendo, principalmente para novos projetos, é utilizar o SQL Server com ADO, pois se integra melhor ao COM+;

Camada Lógica de Negócios – também conhecido como Servidor de Aplicação (ou simplesmente AppServer para os mais íntimos), responsável por concentrar o acesso ao banco de dados e hospedar os componentes COM+. As aplicações cliente NÃO enxergam diretamente o BD, apenas se comunicam com o servidor de aplicação através de uma interface COM. É nessa camada que você centralizará as regras de negócio da aplicação, como por exemplo, validar uma compra, verificar a disponibilidade de um produto em estoque (consultando o BD), calcular algum imposto, realizar alguma validação etc. É nessa camada que residem os componentes do dbExpress e DataSetProviders;

  Camada de Apresentação – é nessa camada que está a menor parte do código. Digo menor porque você basicamente criará telas para exibir os dados oriundos do servidor de aplicação e database. Essa camada não vê o BD, não tem dbExpress nem qualquer acesso direto ao servidor Firebird. Tudo é feito através da chamada de métodos COM ao servidor de aplicação. Por esse motivo, aplicações clientes em uma arquitetura DataSnap são também conhecidas como Thin-Clients (clientes leves ou magros);

  Como comentei, a comunicação entre as camadas exige um protocolo. Do servidor de aplicação para o BD, o protocolo utilizado é o TCP/IP, normal de uma comunicação client/server com o Firebird. O tipo de BD independe da solução, você pode usar SQL Server, DB2, Oracle etc.

  A comunicação do thin-client com o servidor de aplicação é mais interessante. Ela usa um protocolo chamado COM (Component Object Model), através de uma interface. Imagine uma interface COM como um controle remoto de um DVD Player. Você apenas aciona comandos através dele, mas todo o processamento ocorre remotamente. O cliente precisa apenas conhecer a interface do servidor para se comunicar com ele, não toma conhecimento sobre como funcionam seus processos internos, como cálculos, validações e processamento de regras de validação, muito menos sobre o BD que está utilizando e como é feita a comunicação. No DataSnap, a interface base para a comunicação se chama IAppServer.

 

IAppServer

A interface IAppServer surgiu no Delphi 5, para substituir as então interfaces IProvider e IDataBroker. O motivo da substituição foi a inclusão do suporte a servidores state-less, como o caso do MTS/COM+. Além disso, houve uma falha de arquitetura ao se planejar o antigo MIDAS (versões 1 e 2). Para quem lembrar, cada DataSetProvider utilizado em um Data Module remoto exigia a criação de um novo método COM, o que obrigava a modificação da interface e a necessidade de um novo registro.

  IAppServer resolve esse problema elegantemente, com uma solução simples: o nome do DataSetProvider é passado como parâmetro nas chamadas dos métodos COM, o que não exige um novo método para cada tabela que você queira acessar no banco. Além disso, a modificação de interfaces fere um dos princípios básicos da orientação a objetos, que diz que interfaces são imutáveis.

  A interface IAppServer possui 7 métodos, e apenas 7, que fazem basicamente tudo o que você precisa em um servidor de aplicação, como solicitar dados, efetuar atualizações etc. A Listagem 1 apresenta a referida interface.

 

Listagem 1. IAppServer

  IAppServer = interface(IDispatch)

    ['{1AEFCC20-7A24-11D2-98B0-C69BEB4B5B6D}']

    function AS_ApplyUpdates(const ProviderName: WideString; Delta: OleVariant; MaxErrors: Integer; out ErrorCount: Integer; var OwnerData: OleVariant): OleVariant; safecall;

    function AS_GetRecords(const ProviderName: WideString; Count: Integer; out RecsOut: Integer; Options: Integer; const CommandText: WideString; var Params: OleVariant; var OwnerData: OleVariant): OleVariant; safecall;

    function AS_DataRequest(const ProviderName: WideString; Data: OleVariant): OleVariant; ...

Quer ler esse conteúdo completo? Tenha acesso completo