Ir para conteúdo
  • Cadastre-se

dev botao

  • Este tópico foi criado há 1646 dias atrás.
  • Talvez seja melhor você criar um NOVO TÓPICO do que postar uma resposta aqui.

Recommended Posts

Olá queridos companheiros, pesquisei muito sobre uma forma de tratar erros inesperados que causam o fechamento da aplicação e acabei descobrindo (ou inventando kkk), um modo de tratar todos os erros que não foram tratados, vi uma postagem de mais de um ano aq no forum mas não puder dar sequencia nela por estar fechada.

Nesse post vi a sugestão do componente TApplicationProperties, para usar seu evento OnException, mas ao tentar usar ele,  disparava 3 vezes, sem contar que ao colocar um componente em um form e herda-lo, ele componente fica aparecendo em todos os forms e eu só meio xarope e isso me incomoda. 😅 

Seguinte.... Eu uso um FormPadrao no qual estão todas procedures (ferramentas) criadas por mim e algumas outras facilidades como mudar de campo com Enter, fechar as janelas com Esc, etc. E derivo todos os meus outros forms desse para herdarem essas funções e propriedades. Nele eu criei o seguinte procedimento.

//================================== Inicio do Procedimento ==================================\\

procedure TFormPadrao.OnException(Sender: TObject; E: Exception);
var
  auxLog: TextFile;
begin
  try
    AssignFile(auxLog, 'Log_Exceptions.txt');

    if (FileExists('Log_Exceptions.txt')) then
    begin
      Append(auxLog);
    end
    else
    begin
      Rewrite(auxLog);
      WriteLn(auxLog, 'Log de Erros!');
      WriteLn(auxLog, '');
    end;
    WriteLn(auxLog, FormatDateTime('dd/MM/yyyy - hh:mm:ss',now) +
    ' => Origem: ' + Sender.ToString + ' => Erro: ' + E.Message);
  finally
    CloseFile(auxLog);
  end;

  Riba.Aviso('Origem: ' + Sender.ToString + ' => Erro: ' + E.Message);

  if(Sender is TForm)then
    (Sender as TForm).Close;
end;

 

//================================== Fim do Procedimento ==================================\\

E no evento onCreate eu digitei essa linha que associa um procedimento ao um evento

Application.OnException := @OnException;

 

Agora todo erro não tratado é mostrado na tela, fecha só o form que deu o erro e faz um log dos erros.

obs. Esse Riba.Aviso é pra mostrar mensagens na tela do meu jeito. 😁

 

Se eu fiz algo errado no post me corrijam por favor pois é meu primeiro post compartilhando informação.

DEUS abençoe a todos.

 

Editado por RibaSoft
  • Curtir 1
Link para o comentário
Compartilhar em outros sites

  • Administradores

Boa tarde.

Obrigada por compartilhar sua solução.

Att.

  • Curtir 1
Consultora SAC ACBr

Juliana Tamizou

Gerente de Projetos ACBr / Diretora de Marketing AFRAC
Ajude o Projeto ACBr crescer - Seja Pro

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.  Discord

Projeto ACBr - A maior comunidade Open Source de Automação Comercial do Brasil


Participe de nosso canal no Discord e fique ainda mais próximo da Comunidade !!

Link para o comentário
Compartilhar em outros sites

  • Consultores

Olá.

   Eu particularmente gosto de analisar sugestões criativas como a sua. Acho que nos acrescenta muito. Dito isso, tenho os seguintes comentários:

4 horas atrás, RibaSoft disse:

Nesse post vi a sugestão do componente TApplicationProperties, para usar seu evento OnException, mas ao tentar usar ele,  disparava 3 vezes, sem contar que ao colocar um componente em um form e herda-lo, ele componente fica aparecendo em todos os forms e eu só meio xarope e isso me incomoda. 😅 

   hmm... talvez o seu problema esteja em colocar o TApplicationproperties no seu FormPadrao. Você deve ter apenas uma instância do TApplicationProperties na sua aplicação. Geralmente coloca-se num DataModule que não vai ser criado e destruído mais de uma vez.

4 horas atrás, RibaSoft disse:

E no evento onCreate eu digitei essa linha que associa um procedimento ao um evento

Application.OnException := @OnException;

   O problema ao fazer isso é que cada form criado sobrepõe o Application.OnException do Form anterior. Isso pode levar a uma inconsistência.

   Acredito que se você criar um dois forms em sequência, o segundo for destruído e então o primeiro gerar uma exception você terá um AccessViolation.

 

  • Curtir 2

[]'s

Consultor SAC ACBr

Elton
Profissionalize o ACBr na sua empresa, conheça o ACBr Pro.

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Um engenheiro de Controle de Qualidade(QA) entra num bar. Pede uma cerveja. Pede zero cervejas.
Pede 99999999 cervejas. Pede -1 cervejas. Pede um jacaré. Pede asdfdhklçkh.
Link para o comentário
Compartilhar em outros sites

Boa noite fico muito contente pelas suas explicações, vou tentar coloca-las em prática.

Só para entender melhor, meu form padrão nunca é criado (instanciado),  ele serve apenas para que os forms herdeiros herdem seus eventos e propriedades, o meu form que é instanciado junto com o sistema é o formPrincipal que também é herdeiro do form padrão,  minha duvida é:

Se esse evento o Application.OnException que é herdado pode dar problemas, o meus outros eventos herdados tambem podem dar problemas? tipo o onKeyPress que uso para fechar todos os forms com o ESC?

Sou autodidata por isso não tenho tanta experiência, acho que não venho usando corretamente a herança de classes. Preciso estudar mais. 😅

Editado por RibaSoft
Link para o comentário
Compartilhar em outros sites

  • Consultores
36 minutos atrás, RibaSoft disse:

Só para entender melhor, meu form padrão nunca é criado (instanciado),  ele serve apenas para que os forms herdeiros herdem seus eventos e propriedades, o meu form que é instanciado junto com o sistema é o formPrincipal que também é herdeiro do form padrão,  minha duvida é:

Não quis dizer que o "form padrão" fosse criado, mas sim os forms que herdam dele que possuem o mesmo evento onCreate que você descreveu acima. Dito isso:

38 minutos atrás, RibaSoft disse:

Se esse evento o Application.OnException que é herdado pode dar problemas, o meus outros eventos herdados tambem podem dar problemas? tipo o onKeyPress que uso para fechar todos os forms com o ESC?

Creio que não, porque esses outros eventos são de cada form. Mas o evento Application.OnException é da aplicação (Application).

Application é na verdade uma variável global da aplicação. Por isso, toda vez que você faz:

7 horas atrás, RibaSoft disse:

Application.OnException := @OnException;

Você está na verdade sobrescrevendo o mesmo evento com uma procedure do form que foi criado agora.

  • Curtir 1

[]'s

Consultor SAC ACBr

Elton
Profissionalize o ACBr na sua empresa, conheça o ACBr Pro.

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Um engenheiro de Controle de Qualidade(QA) entra num bar. Pede uma cerveja. Pede zero cervejas.
Pede 99999999 cervejas. Pede -1 cervejas. Pede um jacaré. Pede asdfdhklçkh.
Link para o comentário
Compartilhar em outros sites

Arrumei conforme vc falou, testei no DataModulo e no FormPrincipal, o ruim de fazer assim é que não vem o nome do Form no Sender, dai meu log não vai registrar da onde veio o erro, e nem consigo fechar aquele form especifico, mas se fica mais estável vou seguir seu conselho e deixar como está, pelo menos não aparece mais o abort que o cliente sempre clica e fecha toda a aplicação.

DEUS abençoe pela ajuda. 

  • Curtir 1
Link para o comentário
Compartilhar em outros sites

  • Consultores
Em 13/09/2019 at 01:15, RibaSoft disse:

Arrumei conforme vc falou, testei no DataModulo e no FormPrincipal, o ruim de fazer assim é que não vem o nome do Form no Sender, dai meu log não vai registrar da onde veio o erro, e nem consigo fechar aquele form especifico,

Hmm... Acho que estamos com ideias diferentes. Eu não vejo o Application.onException com o objetivo de tratar erros num form específico. Eu o vejo como um modo pra tratar exceptions que fugiram todos os tratamentos nos forms.

Nesses casos, o ideal é você registrar o CallStack da exception, de modo que você vai saber exatamente não só onde aconteceu, mas também o percurso que o código fez pra gerar o erro.

 

Em 13/09/2019 at 01:15, RibaSoft disse:

mas se fica mais estável vou seguir seu conselho e deixar como está

Fica mais estável porque você estava sobrescrevendo o Application.onException. Você pode remover o código que faz isso e daí usar um TApplicationEvents para cada form como queria.

O detalhe é que nesse caso, todos os forms abertos vão receber o evento. Daí você deve usar o método CancelDispatch para impedir a propagação pros próximos forms.

Queria acrescentar que esse modelo eu nunca trabalhei... mas não me parece vantajoso.

  • Curtir 2

[]'s

Consultor SAC ACBr

Elton
Profissionalize o ACBr na sua empresa, conheça o ACBr Pro.

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Um engenheiro de Controle de Qualidade(QA) entra num bar. Pede uma cerveja. Pede zero cervejas.
Pede 99999999 cervejas. Pede -1 cervejas. Pede um jacaré. Pede asdfdhklçkh.
Link para o comentário
Compartilhar em outros sites

Não devo ter me espessado direito, mas é exatamente o que preciso, tratar erros que não foram tratados e criar um log que me ajude a identificar a origem do erro, não tenho palavras pra agradecer sua ajuda em me orientar, vou pesquisar sobre o callstack pois não sei como funciona, e quanto ao segundo modo citado, realmente não parece haver vantagens. DEUS abençoe pela ajuda. 🙏

Link para o comentário
Compartilhar em outros sites

Eureca!!!

Ficou assim...

No DataModulo

//Adiciona a procedure ao evento

Application.OnException := @OnException;  //Forms 

//============================= ON EXCEPTION =================================\\
procedure TDataModulo.OnException(Sender: TObject; E: Exception);
var
  auxLog: TextFile;
begin
  try
    AssignFile(auxLog, 'Log_Exceptions.txt');

    if (FileExists('Log_Exceptions.txt')) then
    begin
      Append(auxLog);
    end
    else
    begin
      Rewrite(auxLog);
      WriteLn(auxLog, 'Log de Erros!');
      WriteLn(auxLog, '');
    end;

    WriteLn(auxLog, FormatDateTime('dd/MM/yyyy - hh:mm:ss',now) +
    '=> Erro: ' + E.ClassName + ' - ' + E.Message);

//Aqui é onde registra os detalhes do erro
    DumpExceptionBackTrace(auxLog);
    WriteLn(auxLog, '======================================================='+
    '================================');

  finally
    CloseFile(auxLog);
  end;

  Riba.Aviso('Erro: ' + E.ClassName + ' - '  + E.Message);
end;          

//=============================== RESULTADO DO LOG

17/09/2019 - 00:40:48=> Erro: EConvertError - " " is an invalid integer
  $00501536
  $0045C6C7  TFORMCLIENTES__EDITBUSCARCHANGE,  line 290 of unitClientes.pas
  $005DB395  TCUSTOMEDIT__CHANGE,  line 652 of ./include/customedit.inc
  $005DB33A  TCUSTOMEDIT__TEXTCHANGED,  line 644 of ./include/customedit.inc
  $005BCD6B  TCONTROL__CMTEXTCHANGED,  line 1203 of ./include/control.inc
  $0040E828
  $005B4801  TWINCONTROL__WNDPROC,  line 5419 of ./include/wincontrol.inc
  $005DAF03  TCUSTOMEDIT__WNDPROC,  line 528 of ./include/customedit.inc
  $006525CF  DELIVERMESSAGE,  line 112 of lclmessageglue.pas
  $0059B5BD  TWINDOWPROCHELPER__DOWINDOWPROC,  line 2515 of win32callback.inc
  $0059BC8B  WINDOWPROC,  line 2677 of win32callback.inc
  $006491ED  GROUPBOXWINDOWPROC,  line 576 of win32wsstdctrls.pp
  $75E96238
  $75E968EA
  $75E9CD1A
  $75E9CD81
  $72596508
=======================================================================================       

//Na segunda linha mostra o nome do form, o evento, a linha do erro e o nome da unit onde ocorreu o erro.

Muito bom, brigadão EMBarbosa, perfeito!!!

 

Link para o comentário
Compartilhar em outros sites

  • Consultores
58 minutos atrás, qqqoq disse:

Obrigado!

No teu caso você está programando no lazaruz, FPC, eu estou programando no Delphi, daí não encontrei, parece que não tem na verdade para o Delphi, somente solução de terceiros =/

Com a JCL é possível fazer isso. Tem artigos na internet.

  • Curtir 1

[]'s

Consultor SAC ACBr

Elton
Profissionalize o ACBr na sua empresa, conheça o ACBr Pro.

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Um engenheiro de Controle de Qualidade(QA) entra num bar. Pede uma cerveja. Pede zero cervejas.
Pede 99999999 cervejas. Pede -1 cervejas. Pede um jacaré. Pede asdfdhklçkh.
Link para o comentário
Compartilhar em outros sites

  • Este tópico foi criado há 1646 dias atrás.
  • Talvez seja melhor você criar um NOVO TÓPICO do que postar uma resposta aqui.

Crie uma conta ou entre para comentar

Você precisar ser um membro para fazer um comentário

Criar uma conta

Crie uma nova conta em nossa comunidade. É fácil!

Crie uma nova conta

Entrar

Já tem uma conta? Faça o login.

Entrar Agora
×
×
  • Criar Novo...

Informação Importante

Colocamos cookies em seu dispositivo para ajudar a tornar este site melhor. Você pode ajustar suas configurações de cookies, caso contrário, assumiremos que você está bem para continuar.

The popup will be closed in 10 segundos...