Transação Delphi 2010
Salve salve galera, to com um problema que ta me tirando o sono, é o seguinte:
Tenho uma aplicação que to construindo em Delphi 2010 com Firebird 2.5, ta indo que é uma maravilha, mas me deparei com um problema, eu tenho uma função que Inicia uma trasação:
//-- Função para iniciar a transação em SQL.
function fgIniTran: Boolean;
begin
//-- Caso ja não tenha uma transação aberta inicia uma.
if not dmDados.sqlcBD.InTransaction then
begin
//-- Variável para controle da transação.
dmDados.vbsgStTran := TRUE; //-- Inicia a transação.
dmDados.vosgIdTran := dmDados.sqlcBD.BeginTransaction(TDBXIsolations.ReadCommitted);
result := TRUE;
end else
begin
pgMsg('ERRO',
'Já existe uma transação iniciada.' + #13 +
'Contate o administrador do sistema.',
'');
result := FALSE;
end;
end; E tenho uma que finalizo a transação: //-- Função para encerra a trasação.
function fgEncTran(pbRollBack: Boolean):Boolean;
begin
//-- Verifica se é so pra fazer rollback.
if pbRollBack then
begin
//-- Caso tenha uma transação aberta fecha.
if dmDados.sqlcBD.InTransaction then
begin
//-- Desfaz qualquer alteração em caso de erro.
dmDados.sqlcBD.RollBackFreeAndNil(dmDados.vosgIdTran); result := TRUE;
end else
begin
pgMsg('ERRO',
'Não há transações abertas.' + #13 +
'Contate o administrador do sistema.',
''); result := FALSE;
end; exit;
end; //-- Caso tenha uma transação aberta fecha.
if dmDados.sqlcBD.InTransaction then
begin
//-- Verifica se não houve nenhum erro na transação e commita.
if (dmDados.vbsgStTran) then
begin
try
//-- Tenta dar o Commit no banco.
dmDados.sqlcBD.CommitFreeAndNil(dmDados.vosgIdTran);
result := TRUE;
except
On E : Exception do
Begin
//-- Desfaz qualquer alteração em caso de erro.
dmDados.sqlcBD.RollBackFreeAndNil(dmDados.vosgIdTran); pgMsg('ERRO',
'Não foi possível concluir as operações,' + #13 +
'todas as operações foram desfeitas!' + #13 +
'Contate o administrador do sistema.',
E.Message); result := FALSE;
end;
end;
end else
begin
//-- Desfaz qualquer alteração em caso de erro.
dmDados.sqlcBD.RollBackFreeAndNil(dmDados.vosgIdTran); pgMsg('ERRO',
'Não foi possível concluir as operações,' + #13 +
'todas as operações foram desfeitas!' + #13 +
'Contate o administrador do sistema.',
''); result := FALSE;
end;
end else
begin
pgMsg('ERRO',
'Não há transações abertas.' + #13 +
'Contate o administrador do sistema.',
''); result := FALSE;
end;
end; Então, eu abra a transação, faço quantos SQL (Insert, Update, Delete...) precisar e depois mando finalizar, se não deu nenhum problema ela finaliza e pronto, caso contrario da rollback em tudo. Até ai tudo bem, o problema é que tenho uma função para quando dar erro gerar um log no banco, e como não posso usar a mesma transação, pq se não vai da rollback no log, preciso cria outra, to tentando cria outra transação, mais n ta dando certo, essa é a parte de geração do LOG: //-- Inicia a transação separada para o log.
voIdTran := dmDados.sqlcBD.BeginTransaction(TDBXIsolations.ReadCommitted); //-- gera novo log.
fgSqlQuery(' INSERT INTO CADLOG01 (' +
' CODIGO, ' +
' DATLOG, ' +
' TIPO, ' +
' IP, ' +
' CODJAN, ' +
' TITJAN, ' +
' TABELA, ' +
' CHAVE1, ' +
' CHAVE2, ' +
' DESCRICAO, ' +
' SQL, ' +
' DADOANTERIOR, ' +
' DADONOVO, ' +
' CODUSU, ' +
' CODEMP) ' +
' VALUES (' +
inttostr(fgGeraCodTabela('CADLOG01')) + ', ' +
' current_timestamp, ' +
QuotedStr(psTipo) + ', ' +
QuotedStr('') + ', ' +
QuotedStr(psCodJan) + ', ' +
QuotedStr(psTitJan) + ', ' +
QuotedStr(psTabela) + ', ' +
inttostr(pnChave1) + ', ' +
inttostr(pnChave2) + ', ' +
QuotedStr(psDescri) + ', ' +
QuotedStr(psSql) + ', ' +
QuotedStr(psDadoAnt) + ', ' +
QuotedStr(psDadoNov) + ', ' +
inttostr(dmDados.vnsgCodUsuario) + ', ' +
inttostr(dmDados.vnsgCodEmpresa) + ') '); //-- Tenta comitar a transação
try
//-- Tenta dar o Commit na trasanção.
dmDados.sqlcBD.BeginTransaction(TDBXIsolations.ReadCommitted); except
On E : Exception do
Begin
//-- Desfaz qualquer alteração caso de erro.
dmDados.sqlcBD.RollBackFreeAndNil(voIdTran); pgMsg('ERRO',
'Erro interno ao tentar gerar LOG (ERRO)!' + #13 +
'Contate o administrador do sistema.',
E.Message);
end;
end; Alguém tem alguma idéia ai? Meu pensamento é o sequinte, se eu abro outra transação, e logo seguida executo uma query, ela vai ser feita nessa nova transação, mesmo que tenha outra aberta, é isso mesmo???
function fgIniTran: Boolean;
begin
//-- Caso ja não tenha uma transação aberta inicia uma.
if not dmDados.sqlcBD.InTransaction then
begin
//-- Variável para controle da transação.
dmDados.vbsgStTran := TRUE; //-- Inicia a transação.
dmDados.vosgIdTran := dmDados.sqlcBD.BeginTransaction(TDBXIsolations.ReadCommitted);
result := TRUE;
end else
begin
pgMsg('ERRO',
'Já existe uma transação iniciada.' + #13 +
'Contate o administrador do sistema.',
'');
result := FALSE;
end;
end; E tenho uma que finalizo a transação: //-- Função para encerra a trasação.
function fgEncTran(pbRollBack: Boolean):Boolean;
begin
//-- Verifica se é so pra fazer rollback.
if pbRollBack then
begin
//-- Caso tenha uma transação aberta fecha.
if dmDados.sqlcBD.InTransaction then
begin
//-- Desfaz qualquer alteração em caso de erro.
dmDados.sqlcBD.RollBackFreeAndNil(dmDados.vosgIdTran); result := TRUE;
end else
begin
pgMsg('ERRO',
'Não há transações abertas.' + #13 +
'Contate o administrador do sistema.',
''); result := FALSE;
end; exit;
end; //-- Caso tenha uma transação aberta fecha.
if dmDados.sqlcBD.InTransaction then
begin
//-- Verifica se não houve nenhum erro na transação e commita.
if (dmDados.vbsgStTran) then
begin
try
//-- Tenta dar o Commit no banco.
dmDados.sqlcBD.CommitFreeAndNil(dmDados.vosgIdTran);
result := TRUE;
except
On E : Exception do
Begin
//-- Desfaz qualquer alteração em caso de erro.
dmDados.sqlcBD.RollBackFreeAndNil(dmDados.vosgIdTran); pgMsg('ERRO',
'Não foi possível concluir as operações,' + #13 +
'todas as operações foram desfeitas!' + #13 +
'Contate o administrador do sistema.',
E.Message); result := FALSE;
end;
end;
end else
begin
//-- Desfaz qualquer alteração em caso de erro.
dmDados.sqlcBD.RollBackFreeAndNil(dmDados.vosgIdTran); pgMsg('ERRO',
'Não foi possível concluir as operações,' + #13 +
'todas as operações foram desfeitas!' + #13 +
'Contate o administrador do sistema.',
''); result := FALSE;
end;
end else
begin
pgMsg('ERRO',
'Não há transações abertas.' + #13 +
'Contate o administrador do sistema.',
''); result := FALSE;
end;
end; Então, eu abra a transação, faço quantos SQL (Insert, Update, Delete...) precisar e depois mando finalizar, se não deu nenhum problema ela finaliza e pronto, caso contrario da rollback em tudo. Até ai tudo bem, o problema é que tenho uma função para quando dar erro gerar um log no banco, e como não posso usar a mesma transação, pq se não vai da rollback no log, preciso cria outra, to tentando cria outra transação, mais n ta dando certo, essa é a parte de geração do LOG: //-- Inicia a transação separada para o log.
voIdTran := dmDados.sqlcBD.BeginTransaction(TDBXIsolations.ReadCommitted); //-- gera novo log.
fgSqlQuery(' INSERT INTO CADLOG01 (' +
' CODIGO, ' +
' DATLOG, ' +
' TIPO, ' +
' IP, ' +
' CODJAN, ' +
' TITJAN, ' +
' TABELA, ' +
' CHAVE1, ' +
' CHAVE2, ' +
' DESCRICAO, ' +
' SQL, ' +
' DADOANTERIOR, ' +
' DADONOVO, ' +
' CODUSU, ' +
' CODEMP) ' +
' VALUES (' +
inttostr(fgGeraCodTabela('CADLOG01')) + ', ' +
' current_timestamp, ' +
QuotedStr(psTipo) + ', ' +
QuotedStr('') + ', ' +
QuotedStr(psCodJan) + ', ' +
QuotedStr(psTitJan) + ', ' +
QuotedStr(psTabela) + ', ' +
inttostr(pnChave1) + ', ' +
inttostr(pnChave2) + ', ' +
QuotedStr(psDescri) + ', ' +
QuotedStr(psSql) + ', ' +
QuotedStr(psDadoAnt) + ', ' +
QuotedStr(psDadoNov) + ', ' +
inttostr(dmDados.vnsgCodUsuario) + ', ' +
inttostr(dmDados.vnsgCodEmpresa) + ') '); //-- Tenta comitar a transação
try
//-- Tenta dar o Commit na trasanção.
dmDados.sqlcBD.BeginTransaction(TDBXIsolations.ReadCommitted); except
On E : Exception do
Begin
//-- Desfaz qualquer alteração caso de erro.
dmDados.sqlcBD.RollBackFreeAndNil(voIdTran); pgMsg('ERRO',
'Erro interno ao tentar gerar LOG (ERRO)!' + #13 +
'Contate o administrador do sistema.',
E.Message);
end;
end; Alguém tem alguma idéia ai? Meu pensamento é o sequinte, se eu abro outra transação, e logo seguida executo uma query, ela vai ser feita nessa nova transação, mesmo que tenha outra aberta, é isso mesmo???
Francisco Gimenez
Curtidas 0
Respostas
Francisco Gimenez
14/06/2010
Ixi, desencana galera, acabei de ver a meleca que tava fazendo...
No log ae, em vez de tentar da commit tava abrindo outra e tava virando uma salada só.... uhauahuahuauha.
Vo testa aki e ja falo se deu certo, fica ai a dica pra quem precisa faze algo semelhante.
GOSTEI 0
Francisco Gimenez
14/06/2010
Era isso mesmo galera, segue o trecho com erro na função de gerar o log:
//-- Tenta comitar a transação
try
//-- Tenta dar o Commit na trasanção.
//dmDados.sqlcBD.BeginTransaction(TDBXIsolations.ReadCommitted);
dmDados.sqlcBD.CommitFreeAndNil(voIdTran); except
On E : Exception do
Begin
//-- Desfaz qualquer alteração caso de erro.
dmDados.sqlcBD.RollBackFreeAndNil(voIdTran); pgMsg('ERRO',
'Erro interno ao tentar gerar LOG (ERRO)!' + #13 +
'Contate o administrador do sistema.',
E.Message);
end; Até deixei comentado a meleca " //dmDados.sqlcBD.BeginTransaction(TDBXIsolations.ReadCommitted);", culpa da correria e do famoso CTRL + C, CTRL + V.... uhauauauhuahua Abraços a todos(as)....
try
//-- Tenta dar o Commit na trasanção.
//dmDados.sqlcBD.BeginTransaction(TDBXIsolations.ReadCommitted);
dmDados.sqlcBD.CommitFreeAndNil(voIdTran); except
On E : Exception do
Begin
//-- Desfaz qualquer alteração caso de erro.
dmDados.sqlcBD.RollBackFreeAndNil(voIdTran); pgMsg('ERRO',
'Erro interno ao tentar gerar LOG (ERRO)!' + #13 +
'Contate o administrador do sistema.',
E.Message);
end; Até deixei comentado a meleca " //dmDados.sqlcBD.BeginTransaction(TDBXIsolations.ReadCommitted);", culpa da correria e do famoso CTRL + C, CTRL + V.... uhauauauhuahua Abraços a todos(as)....
GOSTEI 0
Francisco Gimenez
14/06/2010
Falta descobri como fecha o tópico agora... uhauhauahuaha
GOSTEI 0
Francisco Gimenez
14/06/2010
...
GOSTEI 0
Carlos Mazzi
14/06/2010
rsrsrs, boa guenta ae, vou verificar com a galera da Devmedia, pra fechar pra ti...
Obrigado amigao...
GOSTEI 0