Commit X Rollback

Delphi

26/10/2006

[u:af77a16a4b]Situação:[/u:af77a16a4b]
Numa determinada operação, possuo 8 instruções sql para serem executadas no banco, uma a uma, com tabelas diferentes, em qq uma delas q resultar um erro, devo desfazer todas.

[u:af77a16a4b]Ocorrencia:[/u:af77a16a4b]
Tenho 3 instruções inserts e 5 updates, executo todas, porem uma a uma com um SQLQuery, inserindo a instrução e efetuando um ExecSql.

[u:af77a16a4b]Exemplo: [/u:af77a16a4b]
****************************************
qTmp := TSQLQuery.Create(nil);
qTmp.SQLConnection := DMPrincipal.sql_conn;
with qTmp do begin
Close;
Sql.Clear;
Sql.Add(´update tb_tabela set compo=:par where codigo=:cod´);
ParamByName(´par´).DataType := ftInteger;
ParamByName(´cod´).DataType := ftInteger;
ParamByName(´par´).AsInteger := valor1;
ParamByName(´cod´).AsInteger := valor2;
try
ExecSQL();
except
on E: Exception do begin
MessageDlg(E.Message, mterror, [mbok],0);
// desfazendo toda a transação
DMPrincipal.sql_conn.Rollback(TransDesc);
abort;
end;
end;
Close;
Free;
end;
******************
assim sucessivamente com todas as 8 instruções, seja de insert ou de update.

[u:af77a16a4b]Problema:[/u:af77a16a4b]

Antes da 1ª instrução, eu abro uma transação, e depois da ultima eu fecho com o commit, até aí td bem, ele executa perfeitamente, mas ao inves de fechar com um commit, resolvi colocar um rollback pra testar se ele iria desfazer todas as 8, e algo me incomodou, na primeira instrução INSERT q ele executa, dali pra baixo no codigo ele desfaz, os anteriores ao INSERT não, por exemplo, havia deixado na sequencia todos os updates depois os inserts, e no final dava o rollback, na teoria teria q desfazer td, porem os 5 updates e o 1º insert ele nao desfaz, aí troquei, coloquei primeiro os inserts e depois os updates, aí ele nao desfaz o 1º insert, o restante, desfez td, ai inverti a posição dos inserts, pois tenho 3, e qq um deles q eu colocar em 1º no codigo, esse ele nao desfaz, não consegui entender a razão.

Uso Delphi 7 e firebird 1.5 e DBExpress, se alguém puder me ajudar, agradeço.


Rocetti

Rocetti

Curtidas 0

Respostas

Motta

Motta

26/10/2006

Deveria desfazer tudo.

Alguma tabela dispara trigger ou stored procedure e nesta tem um commit solto ?


GOSTEI 0
Tnaires

Tnaires

26/10/2006

Olá
Pra evitar isso, você deve iniciar a transação explicitamente chamando um StartTransaction antes de executar a primeira instrução. Assim, o Rollback voltará para esse ponto, independentemente de outras instruções serem ´acidentalmente´ executadas via trigger.
Abraços


GOSTEI 0
Motta

Motta

26/10/2006

Só aventei a hipotese de alguma instrução COMMIT perdida em algum ponto, o rollback defaz inclusive as instruções disparadas por triggers, claro.


GOSTEI 0
Rocetti

Rocetti

26/10/2006

Antes da 1ª instrução eu abro a transação:

TransDesc.TransactionID := transact;
TransDesc.IsolationLevel := xilREADCOMMITTED;
DMPrincipal.sql_conn.StartTransaction(TransDesc);

e no final de todas as instruções fecho a transação, pois é um bloco só, ou é tudo ou é nada.

Agora sobre disparar triggers, vou ver aki.


GOSTEI 0
Rocetti

Rocetti

26/10/2006

Realmente possuo um trigger na 1ª instrução, a de autoincremento.

CREATE TRIGGER TRG_INS_NF FOR TB_NF
ACTIVE BEFORE INSERT POSITION 0
as
begin
if (new.nf_controle is null) then
new.nf_controle = gen_id(gen_nf, 1);
end

mas essa trigger executa o commit sozinha ????


GOSTEI 0
Tnaires

Tnaires

26/10/2006

Essa trigger não executa o commit sozinha. O que acontece é que o valor do generator não é recuperado quando um Rollback é efetuado.


GOSTEI 0
Rocetti

Rocetti

26/10/2006

Ok caro Tarso, isso quer dizer que a trigger nao esta interferindo em nada, ou seja, ele executa, mas o rollback desfaz sem problemas. O q pode estar acontecendo intaum ???


GOSTEI 0
POSTAR