Est-ce que vous donnent des instructions DDL toujours une validation implicite, ou pouvez-vous obtenir une annulation implicite?

StackOverflow https://stackoverflow.com/questions/730621

  •  06-09-2019
  •  | 
  •  

Question

Si vous êtes à la moitié d'une transaction et d'effectuer une instruction DDL, comme tronquer une table, la transaction engage.

Je me demandais si cela a toujours été le cas et par définition, ou est-il un paramètre caché quelque part qui serait rollback la transaction au lieu de commettre.

Merci.

Modifier pour clarifier ...

Je ne cherche pas à rollback après une troncature. Je veux juste confirmer que les déclarations déjà effectuées sont tout à fait toujours va être commis avant une DDL. Je veux juste vous assurer qu'il n'y a pas une propriété système quelque part que quelqu'un pourrait mettre à l'épave mon code.

Je comprends la nécessité d'engager avant et après un DDL, mais sur le plan conceptuel que je l'aurais pensé la même exigence de cohérence pourrait être réalisé avec un rollback avant le DDL et une livraison après.

Était-ce utile?

La solution

Non, il sera toujours engager.

Si vous voulez rollback, vous devrez le faire avant le DDL.

Si vous voulez isoler la transaction de votre DDL existante, vous devrez exécuter dans sa propre transaction séparée.

Autres conseils

LDD effectue une validation avant d'exécuter et après exécution.

Oui même lien de Cookie, mais ceci est un autre aspect de la même question. Il est crucial de comprendre ce n'est pas seulement un commettras, il y a deux et ils se produisent juste avant et juste après.

En fait, il engagera si elle peut. Si elle ne peut pas commettre avec succès, le échouera DDL. Une façon d'arrêter de commettre est d'avoir une contrainte différée violé.

create table fred (id number);
alter table fred add constraint id_ck check (id >0) initially deferred;
insert into fred values (-1);
SQL> create table junk(val number);
create table junk(val number)
*
ERROR at line 1:
ORA-02091: transaction rolled back
ORA-02290: check constraint (GC_REF.ID_CK) violated
SQL> desc junk
ERROR:
ORA-04043: object junk does not exist

Donc, si vous voulez éviter une validation implicite, ont une table factice avec une contrainte différée. Insérer une ligne violant, et vous pouvez vous assurer que la transaction ne peut être engagée jusqu'à ce que la violation soit résolue (par exemple ligne supprimée).

truncate table ou alter table ou create table ne provoquent toujours une validation.

Pourquoi voulez-vous rollback lorsque vous faites une truncate table?

ici est un article AskTom qui peut aider. De l'article:

"Je me demandais pourquoi les déclarations ne sont pas exécutées DDL à l'intérieur d'une transaction autonome (comme les séquences font), ils influencent donc wouldnt toute transaction utilisateur en attente ...

Pouvez-vous préciser?

24 Juin Followup 2003 - 7 heures US / Est:

ce serait comme « confus » de ne pas le faire de cette façon. De toute façon, vous avez ATRANS donc si vous voulez, vous pouvez. «

Donc, si vous avez vraiment besoin, vous pouvez coller votre intérieur d'une transaction DDL autonome et faire ce que vous voulez.

EDIT: Bottom line est que si vous allez à des longueurs explicites « subvertir » Oracle, va DDL effectuer une validation. Cela dit, si vous avez besoin absolument qu'un commit est effectué à un certain point, pourquoi ne pas simplement l'exécuter explicitement?

déclarations DDL effectue autocommit toujours, après l'exécution.

Si vous voulez procéder à la restauration en cas de défaillance (dans le côté serveur), vous pouvez définir certains drapeaux pour indiquer l'échec et de prendre les mesures appropriées.

par exemple: si vous avez créé une table table1. et en même temps vous insérez un enregistrement dans un autre tableau.

mais l'insertion a échoué en raison de certaines raisons (ensemble indicateur = true) .Ensuite, dans ce cas, vous ne pouvez pas créer rollback comme instruction est une instruction ddl, vous pouvez annuler les modifications dans la base de données en laissant tomber la table (tableau 1) en fonction de la valeur du drapeau, par DROP.

Je suis d'accord avec DCookie et Tom sur la transaction autonome. J'allais dire cela aussi.

Exemple pseudocode:

Do some DML
Call autonomous function, that performs DDL
Do some more DML
rollback or commit all the DML - your choice

Je ne vois pas cela comme étant très utile cependant. Si le DML initial et le toucher de la même LDD table / objet, il ne va pas au travail. Vous aurez affirmation lorsque vous essayez d'effectuer la LDD. Tout comme les deux opérations de blocage les uns des autres. Et s'ils sont des objets indépendants, je suppose que je ne vois pas pourquoi les questions d'ordre d'exécution.

« Toujours / jamais » est trop forte. Par exemple, comme CREATE PRIVATE TEMPORARY TABLE de DDL Oracle 18c ne COMMIT votre transaction.

scénario normal:

CREATE TABLE t(i INT);
INSERT INTO t(i) VALUES(21);

CREATE TABLE x(i INT);   -- same for CREATE GLOBAL TEMPORARY TABLE y(i INT); 
ROLLBACK;

SELECT * FROM t;
-- Output:
-- 21

Mais si vous créez table privée:

CREATE TABLE t(i INT);
INSERT INTO t(i) VALUES(21);

CREATE PRIVATE TEMPORARY TABLE ORA$PTT_temp(i INT);  
-- or
CREATE PRIVATE TEMPORARY TABLE ORA$PTT_tab
AS
SELECT 1 AS c FROM dual;

ROLLBACK;
SELECT * FROM t;
-- Output:
-- no data found

db <> violon démo

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top