Devido às necessidades do projeto, usei o Delphi para escrever uma DLL que conecte o banco de dados para exportar os dados ao arquivo SQL, que usa o componente TadoQuery.
Existe apenas um método de exportação:
função dataExport (path, ini_path: pchar): inteiro;
Depois de escrever, escrevi um teste.exe com Delphi para testes e descobri que ele poderia ser usado normalmente.
Então ele entregou a DLL a seu colega e pediu que ele o chamasse no PowerBuilder. Depois de tomá -lo, meu colega descobriu que, uma vez que o DataExportPB é chamado, é relatado que a DLL de destino não pode ser aberta. Eu acho que pode ser porque os ambientes em execução de ambos os lados são diferentes, então copiei o test.exe e tentei. Estranhamente, test.exe funciona bem.
Para determinar onde o problema realmente ocorre, usei o Python e o C# para testá -lo novamente.
Coinitialize () não é chamado
Depois de revisar as informações, descobri que, se o componente ADO for usado na DLL de Delphi, o método do Coinitialize do ActiveX precisará ser chamado antes do uso. Depois de conhecer o problema, fica muito mais fácil.
Eu pensei que o PowerBuilder deveria estar bem, mas quem sabia que seria o mesmo problema. Não consigo descobrir agora. O módulo Ctypes em Python usa o método de chamada em C e o método de passagem de parâmetros deve ser o mesmo que o PowerBuilder, mas por que ainda não é possível no PB? Meu colega me pediu para escrever um método de saída extra na DLL para experimentá -lo.
Teste de função: PChar;
Começar
Resultado: = 'String de teste do teste';
fim;
O método de teste foi chamado com sucesso em PB, e então o colega tentou ligar para o DataExport novamente, e foi bem -sucedido! ! ? ? Por que? Esse método de teste apenas produz uma string fixa. Estou muito intrigado.
Mas outro problema ocorreu neste momento.
Verifiquei cuidadosamente o código Delphi e descobri usando a figura se ele não foi lançado.
função dataExport (path, ini_path: pchar): inteiro;
var
Consulta: TadoQuery;
Começar
.........
Coinitialize ();
consulta: = tadoquery.create (nil);
.........
query.close;
query.free;
Counitialize ();
.........
fim;
Nada errado! Em desespero, dividi o Coinitialize () e o Counitialize () em dois métodos independentes.
função init: número inteiro;
Começar
tentar
Coinitialize ();
resultado: = 1;
exceto
na exceção:
resultado: = 0;
fim;
fim;
função não ininit: Inteiro;
Começar
tentar
Counitialize ();
resultado: = 1;
exceto
na exceção:
resultado: = 0;
fim;
fim;
Em seguida, deixe o colega ligar para o init primeiro no evento de inicialização do formulário e, em seguida, feche o evento para chamar a não -ing. Problema resolvido. Tudo é normal.
Embora o problema tenha sido resolvido, ainda não entendo por que faço isso.