Fórum Design Parttern (Singleton / Factory / DAO) #134883

14/04/2010

0

Boa tarde   Estou começando a desenvolver orientado a objetos no Delphi 2009, e estou implementando o padrão DAO para persistência de dados. Encontrei pouquíssimo material sobre o assunto na internet, e estou me baseando no material de Ricardo Coelho na edição 115 onde fala muito bem sobre o assunto. Fiz o exemplo dele, e quase tudo estava funcionando, só fiz algumas correções de sintaxe. O botão alterar, e excluir estão funcionando, exceto o de incluir, quando tento incluir algo recebo uma exceção. Depurei a o erro acontece exatamente no código abaixo. Que erro é este?   Tentei atribuir o código do usuário para o novo cliente desta forma TCliente(pCliente).UsuarioCadastro.Id := 1; , mas também não funcionou. Tenho que instanciar o usuário no meu formulário?
Grato   Denivaldo Junior      -----------------------------------   Evento OnClick do botão Novo:
  Cliente := TCliente.Create;
  Cliente.State := sdNew;
  BtnGravar.Enabled := true;
  BtnCancelar.Enabled := True;
  BtnExcluir.Enabled := false;
  BtnEditar.Enabled := false;
  BtnNovo.Enabled := false;

Evento OnClick do botão Gravar:
  ViewToModel(Cliente);
  if(Cliente.State = sdNew)then
  begin
    Cliente.UsuarioCadastro :=  TAplicacao.GetInstance.UsuarioLogado;
    Dao.Insert(cliente);
  end
  else if(Cliente.State = sdEdit)then
    Dao.Update(cliente);

Procedure ViewToModel:
  pCliente.Id := StrToInt(edtID.Text);
  pCliente.Nome := edtNome.Text;
  pCliente.Idade := StrToInt(edtIdade.Text);
  pCliente.Bairro := EdtBairro.Text;
  pCliente.DiaCadastro := DateOf(now);
  pCliente.HoraCadastro := TimeOf(now);

Procedimento Insert da Classe ClienteDao
procedure TClienteDao.Insert(pCliente:TBaseDomain);
var Qry:TSQLQuery;
    Transacao : TDBXTransaction;
begin
  Qry := TSQLQuery.Create(nil);
  Qry.SQLConnection := TConexaoBD.GetInstance.ConexaoBD;
  try
    Transacao := Qry.SQLConnection.BeginTransaction;
    Qry.SQL.Add('INSERT INTO CLIENTE(ID, NOME, IDADE, BAIRRO, ID_USUARIO) VALUES ');
    Qry.SQL.Add('(:pID, :pNOME, :pIDADE, :pBAIRRO, :pID_USUARIO)');
    Qry.ParamByName('pID').AsInteger := TCliente(pCliente).ID;
    Qry.ParamByName('pNOME').AsString := TCliente(pCliente).Nome;
    Qry.ParamByName('pIDADE').AsInteger := TCliente(pCliente).Idade;
    Qry.ParamByName('pBAIRRO').AsString := TCliente(pCliente).Bairro;
>>    Qry.ParamByName('pID_USUARIO').AsInteger := TCliente(pCliente).UsuarioCadastro.Id;;
    Qry.ExecSQL();
    pCliente.State := sdBrowse;
    Qry.SQLConnection.CommitFreeAndNil(Transacao);
  except
    Qry.SQLConnection.RollbackFreeAndNil(Transacao);
    Application.MessageBox('Um erro aconteceu operação cancelada!', 'ERRO!', MB_APPLMODAL + MB_ICONEXCLAMATION + MB_OK+MB_DEFBUTTON1);
  end;
end;
Denivaldo Junior

Denivaldo Junior

Responder

Posts

14/04/2010

Wesley Yamazack

Olá amigo, foi até bom você ter comentado sobre o DAO, vou fazer umas quick tips sobre DAO.
Agora voltando a sua dúvida, qual seria o erro ?

Um abraço

Wesley Y
Responder

Gostei + 0

14/04/2010

Denivaldo Junior

Olá

Primeiramente se puder postar algum artigo sobre DAO vai ser de grande utilidade.

O erro é "Access violation at address 0048512C in module apoo.exe. write of address 00004".
Se eu passar um inteiro para query abaixo funciona.

Qry.ParamByName('pID_USUARIO').AsInteger := 1;

Acho que é na hora que ele busca o ID do usuário.


Obrigado desde já pela atenção.

Denivaldo Junior
Responder

Gostei + 0

15/04/2010

Wesley Yamazack

Olá amigo,
  O Access Violation só acontece em duas situações.
  1 - Você esta tentando acessar um Objeto, que não foi criado.
  2- Você esta tentando acessar um Objeto, que já foi destruido.

Depurando o código qual é a linha que da o erro ? Esta que você mandou ?

Um abraço

Wesley Y
Responder

Gostei + 0

15/04/2010

Denivaldo Junior

Sim, foi esta linha.

Segundo o exemplo, no evento on click do botão INSERIR, o objeto cliente é criado. Acho que falta criar o usuário: Como faço isso?, o exemplo que estou usando é o mesmo que consta na revista 115 da clube delphi de ricardo coelho.

Evento OnClick do botão Novo:
  Cliente := TCliente.Create;
Responder

Gostei + 0

15/04/2010

Wesley Yamazack

Olá amigo,
  Você poderia me mandar o seu código fonte para poder analisar ? Utilize o DiscoVirtual para isso.

Um abraço

Wesley Y
Responder

Gostei + 0

15/04/2010

Denivaldo Junior

Ok, já está lá.

Obrigado
Responder

Gostei + 0

15/04/2010

Wesley Yamazack

Olá amigo, você tem que me passar o link pois eu não tenho acesso ao seu disco virtual, me mande o link para download.

Um abraço

Wesley Y
Responder

Gostei + 0

15/04/2010

Denivaldo Junior

http://video.devmedia.com.br/discovirtual/65275/POO (SINGLETON FACTORY DAO).rar
Responder

Gostei + 0

16/04/2010

Wesley Yamazack

Olá amigo, estou analisando o chamado, observei que você não esta criando o usuario na classe cliente, isso você terá que fazer.

    Agora uma coisa, você conhece o padrão singleton ? Se sim poderia criar um usuario singleton, seria mais pratico, e não precisaria instanciar toda hora o usuário.
   Segunda dúvida, qual motivo da propriedade Usuario na classe Cliente ?

Um abraço

Wesley Y
Responder

Gostei + 0

16/04/2010

Denivaldo Junior

Não conheço bem padrão singleton, estou estudando, e achei que neste exemplo estava sendo usando o singleton, pois o título da matéria de Ricardo Coelho era "singleton / factory / dao".

1. Como faria isto através do singleton? Poderia mandar um exemplo?
2. O objetivo do "usuário" no cliente é associar o usuário que fez o login através da classe TUsuário.

Ou seja, usuario ADM logou, então este mesmo usuário deve estar associado ao novo cliente para saber quem o cadastrou.

Att

Denivaldo Jr
Responder

Gostei + 0

16/04/2010

Wesley Yamazack

Olá amigo, para entender melhor o que é um singleton, baixe esta video aula do amigo Rodrigo Carreiro,

https://www.devmedia.com.br/post-11809-Rad-Studio-2007-DBX4-e-Firebird-2-0-Aplicacao-comercial-de-vendas-do-Inicio-ao-Fim-Parte-24-Padrao-de-Projeto-Singleton.html

Nela você irá ver passa a passo como criar um singleton.

Você disse : 2. O objetivo do "usuário" no cliente é associar o usuário que fez o login através da classe TUsuário.

Com o Singleton você só terá uma instancia do usuário na sua aplicação, com isso o seu usuário já terá referencia, e valores atribuídos como usuário e senha.

Espero que isso lhe ajude.

Um abraço

Wesley Y
Responder

Gostei + 0

19/04/2010

Denivaldo Junior

Ok, já vi o padrão singleton. Mas preciso descobrir o erro?

Att
Denivaldo Junior
Responder

Gostei + 0

19/04/2010

Wesley Yamazack

Olá amigo,
   Se você descobriu o singleton, você verá que não teria como dar access violation, pois você não esta criando o usuáriologado : tusuario na class cliente, você tem que criar o usuário na hora que criar a classe cliente.

  Ou seja implemente o oncreate do cliente, e nele crie o usuário novamente, já que você quer fazer assim, apesar de não estar no padrão. Sacou ?

Um abraço

Wesley Y
Responder

Gostei + 0

21/04/2010

Wesley Yamazack

Olá amigo,

  Eu não consegui resolver teu problema ? lhe ajudar ? Esclarecer tua dúvida ? Você quer realmente resolver o problema do access violation ? Não quer fazer o Singleton da maneira correta ? Se for isso sem problemas eu resolvo o access violation .


Fico no aguardo


Att,

Wesley Y
Responder

Gostei + 0

21/04/2010

Denivaldo Junior

Na verdade acho que o Ricardo tinha criado apenas a classe de conexão no padrão singleton.
Não sei qual foi o padrão da classe TUsuario e TCLiente. Mas apliquei o padrão singleton na classe TUsuario, de forma que corrigi o problema na inserção da seguinte forma:

Classe TClienteDao

    Qry.ParamByName('pID_USUARIO').AsInteger := TUsuario.GetInstance.Id;

Desculpe se marquei como não resolvido, é porque como estou aprendendo oop na prática, fiquei curioso em saber porque estava dando violação de acesso.  Se era algum erro de sintaxe ou onde estava deixando de criar o usuário, ou quem sabe onde eu estava destruindo o objeto, pois como você respondeu, esse erro só dá quando um objeto já foi destruído ou não foi criado.
Mas enfim, o problema foi resolvido sim. Obrigado pelas dicas e pela atenção.
Com certeza vou postar mais dúvidas, porque esse exemplo de padrão DAO / Singleton foi apenas um ponta pé pra comecar meu sistema.
Sabe de alguma video aula sobre o padrão factory? Preciso identificar ele neste exemplo.


Att
Denivaldo Junior
Responder

Gostei + 0

Utilizamos cookies para fornecer uma melhor experiência para nossos usuários, consulte nossa política de privacidade.

Aceitar