fy>

Clique aqui para ler todos os artigos desta edição

 

ASP.NET

Criando um site para Controle de Projetos com ASP.NET 2.0 - Parte II

 

Na edição anterior, começamos o desenvolvimento de uma aplicação Web, destinada ao controle de projetos de uma Consultoria. A aplicação foi criada em ASP.NET com a utilização do Ajax. Nela criamos todo o processo de autenticação do usuário através do Membership do ASP.NET. Utilizamos Profiles, também do ASP.NET, para armazenarmos o valor hora e o tipo do usuário no sistema. Criamos um DataSet tipado para utilizarmos como camada de persistência. E por fim desenvolvemos uma interface de pesquisa, inclusão, alteração e exclusão de clientes.

Agora vamos dar continuidade criando o restante da aplicação. Ficaram faltando criar as interfaces responsáveis por dar manutenção nos Projetos, Apontamentos de Horas e Lançamento de Despesas.

É muito importante que você tenha lido o artigo anterior, e que tenha realizado os exemplos para que possamos dar continuidade. De qualquer forma você encontra o projeto do artigo anterior para download no site da DevMedia. Vamos ao trabalho!

 

Metodologia

Nossa aplicação será desenvolvida utilizando o modelo conhecido como 5 camadas (interface, ações, bussiness objects, persistência e dados). A interface e ações serão desenvolvidas em páginas e controles ASP.NET. Os Business Objects serão as DataTables e DataRows de um DataSet tipado. A camada de persistência serão os TableAdapters gerados no DataSet, e os dados serão tabelas de um database no SQL Server. Adicionalmente, neste exemplo estaremos implementando segurança transacional na camada de persistência. O diagrama abaixo representa a arquitetura da solução:

Transação

Se recapitularmos tudo o que fizemos no artigo anterior, veremos que basta aplicarmos as mesmas técnicas que usamos na página de Clientes que poderemos facilmente criar as páginas Projetos.aspx, Apontamentos.aspx e Despesas.aspx.

Mas pensando melhor, se fizermos desse jeito ficará muito fácil e não veremos nada de novo nessa segunda parte do artigo. Dessa forma vamos tentar fazer algo diferente para a inclusão e manutenção dos Projetos, Apontamentos e Despesas.

Um amigo leitor, recentemente me cobrou de um tema que gostaria de ver publicado em artigos, mas que raramente é abordado. Ele gostaria de ver um exemplo com operações de inclusão e alteração em várias tabelas ao mesmo tempo.

Ou seja, a clássica transação de Pedidos, onde temos que incluir ou alterar um registro em uma tabela principal (ex: Pedidos), e vários registros em tabelas relacionadas (ex: Itens do Pedido). Como sabemos, temos um relacionamento desse tipo neste nosso exemplo, entre as tabelas Projetos, Apontamentos e Despesas. Para não decepcionar o meu amigo, vamos desenvolver uma única interface para manutenção de registros de Projetos, Despesas e Apontamentos.

Um ponto muito importante a salientar é a questão transacional que envolve operações desse tipo. Ou seja, quando temos em uma única interface uma ação (ex: Click do botão Salvar) que dispara vários comandos em sequência no banco, temos que perguntar: “E se ocorrer uma falha em um desses comandos? O que devemos fazer?”.

Existem várias abordagens para tratar o problema, que dependerão exclusivamente das regras da própria aplicação. Mas de maneira geral, utilizamos o conceito de transação para disparar vários comandos no banco.

Uma transação permite ações como Commit e Rollback. Um Commit é executado pela transação quando todos os comandos são executados com sucesso. Já uma operação Rollback significa que, caso um dos comandos da transação falhe, os comandos que foram anteriormente concluídos com êxito serão “desfeitos”, para que a ação como um todo seja anulada.

Essa é uma das abordagens possíveis com transações, popularmente conhecida como “Tudo ou Nada”: Todos os comandos são executados, ou nenhum será. Essa é uma prática muito comum no desenvolvimento de aplicações com acesso a banco.

Mais do ASP.NET Ajax

Outro assunto que podemos aprofundar neste artigo é o Ajax. Na primeira parte utilizamos apenas o UpdatePanel do Ajax. Vamos utilizar neste artigo alguns controles que são distribuídos na versão CTP do Ajax.

A última versão CTP disponível até a finalização deste artigo é a de Janeiro, e você encontra para download no site do ASP.NET Ajax: ajax.asp.net. Para utilizar a versão CTP basta fazer o download e instalar em seu computador, em seguida habilite o projeto para que possa utilizar os controles da versão CTP.

Primeiramente abra no Visual Studio 2005 o projeto criado no artigo anterior. Vá até a Solution Explorer, clique com o botão direito sobre o projeto e escolha a opção Add Reference. Na aba Browse, localize a seguinte pasta: C:\Arquivos de programas\Microsoft ASP.NET\ASP.NET 2.0 AJAX Futures January CTP\v1.0.61025.

Essa é a pasta onde a versão CTP é instalada. Dentro da pasta você encontrará o assembly Microsoft.Web.Preview.dll (Figura 1), selecione-o e clique em OK.

 

Figura 1. Adicionando referência ao assembly da versão CTP do ASP.NET Ajax

 

Observação

Este exemplo usa controles da versão CTP do ASP.NET Ajax. Como o próprio nome diz, versões CTP (Community Technical Preview) são um preview de funcionalidades que ainda estão em desenvolvimento, e podem ser modificadas no futuro. Portanto tome cuidado ao utilizar esses controles nos projetos em produção.

 

Em seguida precisamos realizar uma pequena alteração no arquivo Web.config. Abra-o e localize a tag que fica dentro de . Nela você encontrará apenas uma referência ao namespace System.Web.Extensions.

Temos que adicionar mais duas referências aos namespaces Microsoft.Web.Preview e Microsoft.Web.Preview.UI. A seção pages do Web.config deve ficar como mostra a Listagem 1.

 

Listagem 1. Seção pages do Web.config

...

<pages>

  <controls>

    <add tagPrefix="asp" namespace="System.Web.UI"

      assembly="System.Web.Extensions, Version=1.0.61025.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35"/>

    <add tagPrefix="asp"    

      namespace="Microsoft.Web.Preview.UI"

      assembly="Microsoft.Web.Preview"/>

    <add tagPrefix="asp"

     namespace="Microsoft.Web.Preview.UI.Controls"   

     assembly="Microsoft.Web.Preview"/>

  controls>

pages>

...

Página Projetos.aspx

Assim como fizemos com o cadastro de Clientes, vamos colocar na página de projetos um GridView onde listaremos todos os projetos existentes. Abra a página Projetos.aspx que foi criada no artigo anterior e desenhe o seu layout de forma que fique como demonstrado na Figura 2.

 

Figura 2. Layout da Página Projetos.aspx

Veja que é um layout bem simples, temos apenas um GridView e três botões que realizarão as operações de inclusão, alteração e exclusão dos Projetos.  Vamos codificar nossa página para que mostre todos os projetos que temos cadastrados no banco.  Vá ao código da página e inclua o código da Listagem 2.

 

Listagem 2. Código da classe Projetos

...

using ProjetosDataSetTableAdapters;

 

public partial class Projetos : System.Web.UI.Page

{

  private ProjetosDataSet ProjetosData

  {

    set { Session["ProjetosData"] = value; }

    get

    {

      object obj = Session["ProjetosData"];

      if (obj == null)

        return new ProjetosDataSet();

      else

        return (ProjetosDataSet)Session[

          "ProjetosData"];

    }

  }

 

  protected void Page_Load(object sender, EventArgs e)

  {

    if (!Page.IsPostBack)

      this.SelectProjetos();

  }

 

  private void SelectProjetos()

  {

    ClientesTableAdapter CliAdapter = new

      ClientesTableAdapter();

    ProjetosTableAdapter ProAdapter = new

      ProjetosTableAdapter();

    try

    {

      ProjetosDataSet Pro = new ProjetosDataSet();

      CliAdapter.Fill(Pro.Clientes);

      ProAdapter.Fill(Pro.Projetos);

      this.ProjetosData = Pro;

      Grid.DataSource = this.ProjetosData.Projetos;

      Grid.DataBind();

    }

    catch (Exception ex)

    {

      throw (new Exception(ex.ToString()));

    }

    finally

    {

      CliAdapter.Dispose();

      ProAdapter.Dispose();

    }

  }

}

 

Observe primeiramente que importamos o namespace ProjetosDataSetTableAdapters para que possamos utilizar os TableAdapters criados no DataSet tipado. Em seguida criamos uma propriedade chamada ProjetosData que armazenará em uma Session, o ProjetosDataSet.

Porque usar uma Session em vez de usar ViewState? Estamos usando Session, pois queremos que os dados do DataSet estejam disponíveis fora da página. Você entenderá mais adiante o que estou querendo dizer.

No Page_Load, caso não seja um postback, estamos chamando o SelectProjetos. No método recuperamos todos os projetos e todos os clientes da nossa base. Você pode estar se perguntando o porquê de recuperar todos os clientes, não seria melhor recuperar somente os projetos?

Talvez. Se sua aplicação for comportar um número muito grande de Projetos e Clientes, por questões de performance é melhor você criar um DataTable específico no DataSet que conterá todas as informações necessárias do projeto, mais as informações necessárias da tabela estendida Clientes.

Assim, com um único SELECT você recupera apenas as informações necessárias para preencher o Grid. Mas, como neste exemplo não trabalharemos com uma quantidade muito grande de dados, estamos recuperando tudo em duas DataTables distintas, para que possamos ver adiante como é fácil acessar o Cliente de um determinado projeto, graças aos relacionamentos do DataSet.

Nesse ponto, se você incluir manualmente alguns registros na tabela de Projetos, poderá testar a página Projetos.aspx. Se fizer isso você verá que o Grid listará os registros inseridos, mas na coluna Cliente aparecerá o CNPJ do mesmo.

Para trocarmos o CNPJ pelo Nome do cliente é muito simples. Volte ao Visual Studio, na página Projetos.aspx, clique no GridView e acesse o evento RowDataBound. Basta incluir no evento o código da Listagem 3.

Veja que graças ao relacionamento existente entre o DataTable Clientes com o DataTable Projetos, podemos acessar os dados do cliente através da propriedade ClientesRow.

 

Listagem 3. Substituindo o CNPJ pelo Nome do Cliente.

protected void Grid_RowDataBound(object sender,

  GridViewRowEventArgs e)

{

  if (e.Row.RowType == DataControlRowType.DataRow)

    e.Row.Cells[2].Text =

  this.ProjetosData.Projetos[e.Row.DataItemIndex].

    ClientesRow.cliNome;

}

Web User Control

Um dos benefícios mais importantes que a Orientação a Objetos trouxe é a reutilização. Quanto mais reutilizável for nosso código e componentes, mais produtivo é o desenvolvimento das aplicações. Umas das funcionalidades que mais promovem a reutilização no desenvolvimento de aplicações ASP.NET é o Web User Control.

Com ele podemos desenvolver “parte” do layout de uma página, e reutilizá-lo em quantas páginas quisermos. Que tal criarmos a interface de inclusão e alteração de Projetos em um Web User Control?

É muito simples e similar ao desenvolvimento de uma página comum. Clique com o botão direito sobre o projeto na Solution Explorer e escolha a opção Add New Item. Escolha o item Web User Control, informe “FichaProjeto.ascx” em Name e clique em OK.

Veja que o Web User Control possui uma área de design igual a de uma página comum. Basta desenharmos o layout do controle. Faça isso como mostra a Figura 3

 

Figura 3. Layout do Controle FichaProjeto.ascx

DragOverlayExtender

Veja primeiramente que todo o layout foi desenvolvido dentro do um UpdatePanel, para mantermos a compatibilidade com o Ajax. Dentro do UpdatePanel, o primeiro controle adicionado foi um Panel. Observe as propriedades desse Panel na legenda da figura.

Dentro do Panel foram incluídos os controles necessários para a interface de inclusão/alteração de projetos. Temos basicamente DropDownLists, TextBoxes, Buttons e dois GridViews. Basta incluí-los como mostra a imagem e configurar suas propriedades como estão nas legendas.

Desenhamos toda a interface dentro de um Panel para que o controle tenha o aspecto de uma “janela flutuante”. Para que o controle ganhe o efeito de “clicar e arrastar”, estamos utilizando um componente do Ajax CTP, chamado DragOverlayExtender. Veja que ele foi adicionado logo abaixo do Panel, dentro do UpdatePanel.

Infelizmente, como ele pertence às funcionalidades CTPs do Ajax, não aparece na ToolBox, e portanto temos que adicioná-lo no source da página, adicionando o código da Listagem 4, logo abaixo da tag .

 

Listagem 4. Definição do controle DragOverlayExtender

<asp:DragOverlayExtender

ID="DragExtender1" runat="server" Enabled="true"

ProfileProperty="proJanela"

TargetControlID="pnlProjeto" />

 

Temos a propriedade TargetControlID que aponta para o controle que receberá o efeito “flutuante”, no nosso caso o pnlProjeto. E também temos a propriedade ProfileProperty que aponta para uma propriedade que temos que criar no Profile.

Essa propriedade é necessária para que o DragOverlayExtender possa armazenar a posição na janela, e persistí-la entre os postbacks. Para incluir a propriedade proJanela no Profile, abra o arquivo Web.config e encontre a seção properties que está dentro de profile. Inclua a nova propriedade ...

Quer ler esse conteúdo completo? Tenha acesso completo