Автономна транзакция в Oracle PL / SQL

⚡ Умно обобщение

Отчети за контрол на транзакциите в Oracle PL/SQL, а именно COMMIT, ROLLBACK и SAVEPOINT, решават дали чакащите DML промени да бъдат запазени или отхвърлени. Автономната транзакция се изпълнява като независима подпрограма, която извършва commit или rollback отделно от основната транзакция.

  • 💾 ИЗПЪЛНЕНИЕ: Прави всички чакащи DML промени постоянни, прекратява транзакцията, освобождава заключванията и изтрива всяка точка на запазване.
  • ↩️ ВРЪЩАНЕ: Отменя чакащите промени, или цялата транзакция, или обратно към посочена точка на запазване.
  • 📌 ТОЧКА НА ЗАПАЗВАНЕ: Маркира точка в транзакцията, така че по-късен ROLLBACK TO може да отмени само част от работата.
  • 🔀 Автономна транзакция: Директивата PRAGMA AUTONOMOUS_TRANSACTION позволява на подпрограмата да извърши самостоятелна регистрация (commit) или отмяна (rollback).
  • 🧾 Случаи на употреба: Автономните транзакции са подходящи за одит и регистриране на грешки, които трябва да се запазят, дори ако основната работа бъде отменена.
  • 🤖 AI помощ: Асистенти с изкуствен интелект, като например GitHub Copilot, изготвят блокове COMMIT, ROLLBACK и PRAGMA и маркират липсващи коммити.

Автономна транзакция в Oracle PL/SQL с COMMIT и ROLLBACK

Какво представляват TCL изразите в PL/SQL?

TCL е съкращение от Transaction Control Statements (Оператори за контрол на транзакциите). Тези оператори или запазват чакащите транзакции, или ги отменят. Те играят жизненоважна роля, защото освен ако транзакцията не бъде запазена, промените, направени чрез... DML отчети няма да се съхранява постоянно в базата данни. По-долу са различните TCL оператори в PL / SQL.

Изявление Descriptйон
COMMIT Запазва всички чакащи транзакции.
ВРЪЩАНЕ Отхвърля всички чакащи транзакции.
ТОЧКА НА ЗАПИСВАНЕ Създава точка в транзакцията, до която по-късно може да се извърши връщане назад.
ВЪРТАНЕ КЪМ Отхвърля всички чакащи транзакции до посочената точка на запазване.

Транзакцията ще бъде завършена при следните сценарии:

  • Когато бъде издадено някое от горните твърдения (с изключение на SAVEPOINT).
  • Когато се издават DDL оператори (DDL са оператори за автоматично записване).
  • Когато се издават DCL оператори (DCL са оператори за автоматично записване).

Използване на SAVEPOINT и ROLLBACK TO

Таблицата по-горе представя SAVEPOINT и ROLLBACK TO, като заедно те ви дават частичен контрол върху транзакцията. SAVEPOINT маркира именувана точка в текущата транзакция. По-късно ROLLBACK TO тази точка на запазване отменя всяка промяна, направена след нея, като същевременно запазва...ping работата, извършена преди това, е непокътната.

Това е полезно, когато дълга транзакция извършва няколко SQL стъпки и само последната стъпка се проваля. Вместо да отхвърлите цялата транзакция, можете да се върнете до последната добра точка на запазване и да продължите.

Синтаксис:

SAVEPOINT <savepoint_name>;
   -- one or more DML statements
ROLLBACK TO <savepoint_name>;

Ключови моменти, които трябва да се запомнят за точките за запазване:

  • SAVEPOINT съществува само в рамките на текущата транзакция; COMMIT или пълен ROLLBACK изтрива всяка точка на запазване.
  • Когато се върнете към точка на запазване, всички точки на запазване, създадени след нея, се изтриват, но точката на запазване, към която се връщате, се запазва.
  • ROLLBACK TO не прекратява транзакцията; промените, направени преди точката на запазване, остават в очакване, докато не изпълните COMMIT или ROLLBACK.
  • Ако използвате повторно име на точка за запазване, по-новата точка за запазване (SAVEPOINT) премества маркера на по-късна позиция.

Тъй като ROLLBACK TO оставя транзакцията отворена, вие все още решавате накрая дали да COMMIT-вате останалите промени или да ги отхвърлите с пълен ROLLBACK.

Какво е автономна транзакция

В PL/SQL всички модификации, извършени върху данни, се наричат ​​транзакция. Транзакцията се счита за завършена, когато към нея се приложи команда за запазване или изхвърляне. Ако не е дадена команда за запазване или изхвърляне, транзакцията не се счита за завършена и модификациите, извършени върху данните, няма да бъдат направени постоянни на сървъра.

По подразбиране PL/SQL третира всички модификации по време на сесия като една единствена транзакция и запазването или отхвърлянето на тази транзакция засяга всяка чакаща промяна в сесията. Автономната транзакция предоставя на разработчика възможността да прави промени в отделна транзакция и да запазва или отхвърля тази конкретна транзакция, без да засяга основната транзакция на сесията.

  • Автономна транзакция може да бъде зададена на ниво подпрограма.
  • За да направите всяка подпрограма работят в различна транзакция, ключовата дума PRAGMA AUTONOMOUS_TRANSACTION трябва да бъде дадена в декларативната секция на този блок.
  • Това инструктира компилатора да третира това като отделна транзакция и запазването или изхвърлянето в този блок няма да се отрази в основната транзакция.
  • Издаването на COMMIT или ROLLBACK е задължително преди напускане на тази автономна транзакция и връщане към основната транзакция, защото по всяко време само една транзакция може да бъде активна.
  • Така че, след като е стартирана автономна транзакция, тя трябва да бъде запазена и завършена, преди контролът да може да се върне към основната транзакция.

Синтаксис:

DECLARE
PRAGMA AUTONOMOUS_TRANSACTION;
.
BEGIN
<execution_part>
[COMMIT|ROLLBACK]
END;
/

В горния синтаксис блокът е направен автономна транзакция.

Пример 1: В този пример ще разберем как работи една автономна транзакция.

Снимката на екрана по-долу показва този пример за автономна транзакция и нейния резултат в Oracle.

Пример за автономна транзакция, която записва вложен блок, докато основната транзакция се отменя Oracle PL / SQL

DECLARE
   l_salary   NUMBER;
   PROCEDURE nested_block IS
   PRAGMA autonomous_transaction;
    BEGIN
     UPDATE emp
       SET salary = salary + 15000
       WHERE emp_no = 1002;
   COMMIT;
   END;
BEGIN
   SELECT salary INTO l_salary FROM emp WHERE emp_no = 1001;
   dbms_output.put_line('Before Salary of 1001 is'|| l_salary);
   SELECT salary INTO l_salary FROM emp WHERE emp_no = 1002;
   dbms_output.put_line('Before Salary of 1002 is'|| l_salary);    
   UPDATE emp 
   SET salary = salary + 5000 
   WHERE emp_no = 1001;

nested_block;
ROLLBACK;

 SELECT salary INTO  l_salary FROM emp WHERE emp_no = 1001;
 dbms_output.put_line('After Salary of 1001 is'|| l_salary);
 SELECT salary INTO l_salary FROM emp WHERE emp_no = 1002;
 dbms_output.put_line('After Salary of 1002 is '|| l_salary);
end;

Продукция

Before:Salary of 1001 is 15000 
Before:Salary of 1002 is 10000 
After:Salary of 1001 is 15000 
After:Salary of 1002 is 25000

Code Обяснение:

  • Code ред 2: Деклариране на l_salary като NUMBER.
  • Code ред 3: Деклариране на процедурата nested_block.
  • Code ред 4: Превръщане на процедурата nested_block в АВТОНОМНА_ТРАНЗАКЦИЯ.
  • Code ред 7-9: Увеличаване на заплатата за служител номер 1002 с 15000.
  • Code ред 10: Извършване на автономната транзакция.
  • Code ред 13-16: Отпечатване на данните за заплатите на служители 1001 и 1002 преди промените.
  • Code ред 17-19: Увеличаване на заплатата за служител номер 1001 с 5000.
  • Code ред 20: Извикване на процедурата nested_block.
  • Code ред 21: Отхвърляне на основната транзакция.
  • Code ред 22-25: Отпечатване на данните за заплатите на служители 1001 и 1002 след промените.

Увеличението на заплатата за служител номер 1001 не е отразено, защото основната транзакция е била отхвърлена. Увеличението на заплатата за служител номер 1002 е отразено, защото този блок е направен като отделна транзакция и е запазен в края.

Така че, независимо от запазването или отхвърлянето в основната транзакция, промените в автономната транзакция се запазват, без да засягат основната транзакция.

Кога да използвате автономни транзакции

Автономните транзакции са мощни, така че е полезно да знаете кога са подходящи. Запазете ги за работа, която трябва да успее или да се провали независимо от основната транзакция, а не за основната бизнес логика. Често срещани случаи на употреба включват:

  • Регистриране на одит: Записвайте кой е променил чувствителни данни, кога, както и старите и новите стойности, така че логът да оцелее, дори ако основната транзакция бъде отменена.
  • Регистриране на грешки: Запишете запис за грешка вътре в изключение обработчик и го COMMIT, така че диагностичните детайли се запазват, докато неуспешната транзакция се отхвърля.
  • Броячи и статистика: Задайте брояч на употреба или брой попадения, който трябва да се запази, независимо от резултата на повикващия.
  • COMMIT вътре в тригер: Тригерът не може да издаде COMMIT директно; автономна транзакция е единственият поддържан начин за това.

Избягвайте автономни транзакции за обикновени актуализации, които би трябвало да споделят съдбата на основната транзакция. Прекомерната им употреба може да скрие данни зад независими коммити и да затрудни отстраняването на грешки. Като правило, всеки автономен блок трябва да завършва с изричен COMMIT или ROLLBACK.

Автономни срещу редовни транзакции

Разликата между обикновена (основна) транзакция и автономна транзакция се свежда до обхвата и независимостта. Таблицата по-долу ги сравнява.

Аспект Редовна транзакция Автономна транзакция
Обхват Споделя една сесийна транзакция Изпълнява се като отделна дъщерна транзакция
Ефект на COMMIT / ROLLBACK Засяга всички предстоящи промени в сесията Засяга само автономния блок
Декларация Поведение по подразбиране PRAGMA AUTONOMOUS_TRANSACTION в декларативния раздел
Ефект от връщането на родителски настройки Промените се губят Запазват се извършените автономни промени
Типична употреба Основна бизнес логика Одит и регистриране на грешки

За разлика от обикновения вложен блок, чиито промени винаги споделят резултата от обхващащата го транзакция, автономният блок съществува самостоятелно. Разбирането на тази разлика ви помага да решите кога един блок трябва да бъде независим и кога трябва да споделя резултата от основната транзакция.

Въпроси и Отговори

Oracle Повиква ORA-06519 и отменя автономната работа. Всяка автономна транзакция трябва да завърши с изричен COMMIT или ROLLBACK, преди контролът да се върне към основната транзакция, защото е разрешена само една активна транзакция в даден момент.

Не директно. Нормален тригер не може да издаде COMMIT или ROLLBACK. Декларирането на тригера или процедурата, която той извиква, с PRAGMA AUTONOMOUS_TRANSACTION му позволява да commit собствените си промени, независимо от оператора, който е задействал тригера.

Не. След като родителят бъде спрян, автономната транзакция се изпълнява независимо и не може да вижда некомитираните промени на родителя. Тя вижда само данни, които вече са коммитирани в базата данни, така че чакането на заключване на родител може да доведе до безизходица.

Да. Всеки DDL оператор, като CREATE, ALTER или DROP, издава имплицитен COMMIT преди и след изпълнението си. Всеки чакащ DML оператор в сесията се commitва автоматично, така че DDL операторът не може да бъде отменен след това.

Автономен блок може да извика друг и всеки управлява свой собствен COMMIT или ROLLBACK. Oracle Ограничава броя на активните едновременно транзакции чрез параметъра за инициализация TRANSACTIONS, така че много дълбокото влагане на автономни блокове може да се провали.

Не. COMMIT прави промените постоянни, освобождава заключванията и изтрива точките за запазване, така че не може да бъде отменено с ROLLBACK. За да върнете потвърдените данни, трябва да изпълните нов DML. Използвайте SAVEPOINT и ROLLBACK TO за частично отменяне преди потвърждаване.

Да. Копилот на GitHub създава логиката COMMIT и ROLLBACK, блоковете SAVEPOINT и процедурите PRAGMA AUTONOMOUS_TRANSACTION от коментар. RevВижте разположението на коммита и обработката на грешки, тъй като неправилно поставен коммит може да повреди границите на транзакцията.

Асистентите с изкуствен интелект сканират процедурите за липсващи или неправилно поставени оператори COMMIT и ROLLBACK, commits вътре в цикли и незатворени автономни блокове. Този преглед с машинно обучение сигнализира за грешки в транзакциите и предлага по-безопасни граници, преди кодът да достигне до производствена среда.

Обобщете тази публикация с: