В последнее время к мне, один за другим, обратилось уже три крупных российских ISV-разработчика приложений с вопросами по технологии Edition Base Redefinition [EBR].
Причем все они разрабатывают ПО для банков. Я думаю, что Вы поняли, чем вызван их интерес. Ведь каждое обновление приложения - это вынужденный простой для заказчика, что особенно болезненно для банковского сектора. Вообще говоря, минимизация плановых простоев - это важная задача в любой организации.
Технология версионирования PL/SQL-объектов Edition Base Redefinition появилась в Oracle Database версии 11.2.
EBR позволяет проводить обновление приложения (вернее изменять код его хранимых процедур) "на лету", без остановки приложения. При этом, компиляция новой версии PL/SQL-объекта (пакета, объектного типа, функции или процедуры) производится в новой версии; работающие в этот момент пользователи НЕ получают исключение "ORA-04068 existing state of packages has been discarded", а продолжают работу с старой версией PL/SQL-кода.
Помимо чисто технических вопросов, главные вопросы, которые задавали мне представители этих компаний, звучали примерно так: "Есть ли примеры крупных внедрений этой технологии, что будет с этой технологией в дальнейшем, и можно ли воообще полагаться на нее?".
Что касается примеров использования этой технологии.
В сентябре этого года была выпущена новая версия ERP-системы от Oracle - Oracle E-Business Suite 12.2.
Начиная с версии 12.2, процедура "наката" обновлений на Oracle EBS происходит без остановки, на уровне БД это достигается с помощью технологии EBR. Oracle EBS - это очень сложное приложение, которое содержит десятки тысяч таблиц и миллионы строк PL/SQL-кода. На мой взгляд, использование EBR в таком приложении, говорит о зрелости технологии. Конечно, поставщик технологии (то есть Oracle Corp.), а EBR не является готовым продуктом, а представляет собой базовую технологию, не использовал бы ее в своем основном приложении, если бы не был уверен в ее надежности и не имел бы планов по ее дальнейшему развитию.
Рис.1 Дистрибутив Oracle EBS 12.2 доступен на сайте edelivery.oracle.com
По поводу дальнейшего развития технологии EBR.
В недавно вышедшей СУБД Oracle Database 12c R1, технология EBR получила свое дальнейшее развитие - в ней появились очень полезные новые возможности.
Давайте рассмотрим их более подробно.
1. Потенциальная версионируемость отдельного объекта, а не всех объектов схемы.
1.1 В Oracle Database 11g версионируемость включается для всех объектов схемы
В версии Oracle Database 11.2 потенциальная версионируемость включалась на уровне всей схемы.
То есть, когда Вам нужно было включить версионирование объектов, это производилось на уровне всей схемы:
[oracle@**** ~]$ sqlplus / as sysdba
SQL*Plus: Release 11.2.0.3.0 Production on Sun Nov 1 12:50:56 2013
Copyright (c) 1982, 2011, Oracle. All rights reserved.
Connected to:
Oracle Database 11g Enterprise Edition Release 11.2.0.3.0 - 64bit Production
With the Partitioning, OLAP, Data Mining and Real Application Testing options
rem --Включаем возможность версионирования в схеме RSCOTT: в 11gR2 включается для всех объектов схемы!
SQL> ALTER USER rscott ENABLE EDITIONS;
User altered.
Таким образом, при помощи команды "
ALTER USER <имя_схемы> ENABLE EDITIONS" версионируемость включалась для всех объектов схемы!
Как Вы помните, неверсионируемый объект не может зависеть от версионируемого объекта.
Если, например, мы создадим объектный тип PL/SQL в схеме, для которой включена потенциальная версионируемость, то мы не сможем создать таблицы с столбцом этого объектного типа (поскольку таблицы не версионируются!):
SQL> conn rscott/rtiger
Connected.
SQL> CREATE TYPE TMyType AS OBJECT
2 (
3 Id NUMBER(9)
4 );
5 /
Type created.
SQL> CREATE TABLE MyTable
2 (
3 Id TMyType
4 );
CREATE TABLE MyTable
*
ERROR at line 1:
ORA-38818: illegal reference to editioned object RSCOTT.TMYTYPE
В вышеприведенном примере объектный тип TMyType потенциально может иметь другие версии, поэтому невозможно использовать его в качестве типа для столбца таблицы, несмотря на то, что мы не собираемся иметь другие версии этого типа. Это происходит потому-что потенциальная версионируемость была включена для всех объектов схемы RSCOTT.
По этой причине, кстати, в версии 11.2 нельзя было создавать очереди Advanced Queuing с типом из схемы для которой включено версионирование:
SQL> BEGIN
dbms_aqadm.create_queue_table(queue_table => 'MY_QUEUE',
queue_payload_type => 'TMyType');
END;
/
BEGIN
*
ERROR at line 1:
ORA-38818: illegal reference to editioned object RSCOTT.TMYTYPE
ORA-06512: at "SYS.DBMS_AQADM", line 81
ORA-06512: at line 2
Для решения вышеописанной проблемы, в Oracle Database 11.2 приходилось использовать обходной путь (workaround), заключающийся в выводе НЕверсионируемых объектов в отдельную схему, для которой версионируемость не включалась:
[oracle@**** ~]$ sqlplus / as sysdba
SQL*Plus: Release 11.2.0.3.0 Production on Sun Nov 1 13:11:26 2013
Copyright (c) 1982, 2011, Oracle. All rights reserved.
Connected to:
Oracle Database 11g Enterprise Edition Release 11.2.0.3.0 - 64bit Production
With the Partitioning, OLAP, Data Mining and Real Application Testing options
rem -- Создаем отдельную схему для неверсионируемых объектов:
SQL> CREATE USER rscott_nonvers IDEBTIFIED BY rtiger_nonvers;
User created.
SQL> GRANT connect, resource, create synonym TO rscott_nonvers;
Grant succeeded.
rem --Создаем неверсионируем тип TMyType
SQL> CONN rscott_nonvers/rtiger_nonvers
Connected.
SQL> CREATE TYPE TMyType AS OBJECT
2 (
3 Id NUMBER(9)
4 );
5 /
Type created.
rem -- Не забываем дать права на этот тип пользователю RSCOTT
SQL> GRANT execute ON TMyType TO rscott;
Grant succeeded.
SQL> CONN rscott/rtiger
Connected.
SQL>
rem -- Для удобства создаем локальный синоним на тип TMyType в схеме RSCOTT_nonvers
SQL> CREATE SYNONYM TMyType FOR rscott_nonvers.TMyType;
Synonym created.
rem -- Наконец, успешно создаем таблицу c столбцом неверсионируемого типа TMyType!
SQL> CREATE TABLE MyTable
2 (
3 Id TMyType
4 );
Table created.
SQL>
1.2 В Oracle Database 12с версионируемость включается для уровне объекта
Начиная с Oracle Database версии 12.1 в вышеприведенных дополнительных действиях нет необходимости, поскольку теперь потенциальная версионируемость PL/SQL-объекта может включаться для отдельного объекта. При создании PL/SQL-объекта указывается ключевое слово EDITIONABLE, если объект потенциально может версионироваться, NONEDITIONABLE - если объект не будет версионироваться:
[oracle@****]$ sqlplus rscott/rtiger
SQL*Plus: Release 12.1.0.1.0 Production on Mon Nov 2 11:09:43 2013
Copyright (c) 1982, 2013, Oracle. All rights reserved.
Last Successful login time: Mon Nov 02 2013 11:08:16 +04:00
Connected to:
Oracle Database 12c Enterprise Edition Release 12.1.0.1.0 - 64bit Production
With the Partitioning, OLAP, Advanced Analytics and Real Application Testing options
SQL>
rem -- Cоздаем неверсионируемый тип
SQL> CREATE NONEDITIONABLE TYPE TMyType AS OBJECT
2 (
3 Id NUMBER(9)
4 );
5 /
Type created.
rem -- Cоздаем таблицу c столбцом неверсионируемого типа TMyType!
SQL> CREATE TABLE MyTable
2 (
3 Id TMyType
4 );
Table created.
2. Ограничение версий для выражений вычисляемых столбцов в таблицах и материализованных представлениях
2.1 Особенности использования виртуальных столбцов в Oracle Database 11g
Еще начиная с версии 11g Release 1, в СУБД Oracle появилась поддержка виртуальных столбцов, то есть столбцов, которые заданы вычисляемым выражением.
В выражении виртуального столбца также могут участвовать хранимые PL/SQL-функции, как например в следующем случае:
[oracle@**** ~]$ sqlplus rscott/rtiger
SQL*Plus: Release 11.2.0.4.0 Production on Wed Nov 6 16:31:47 2013
Copyright (c) 1982, 2013, Oracle. All rights reserved.
Connected to:
Oracle Database 11g Enterprise Edition Release 11.2.0.4.0 - 64bit Production
With the Partitioning and Real Application Testing options
SQL> CREATE OR REPLACE FUNCTION getMyId RETURN NUMBER
DETERMINISTIC IS
BEGIN
RETURN 1;
END;
/
Function created.
rem --создаем таблицу с виртуальным столбцом в выражении которого участвует PL/SQL-функция
SQL> CREATE TABLE myTable
(
Id NUMBER(9),
MyId as (getMyId())
);
Table created.
Обратите внимание, что нам удалось создать неверсионируемый объект (таблицу), который зависит от версионируемого объекта (PL/SQL-функции).
Поскольку значение виртуального столбца на диске не сохраняется, мы смогли это сделать!
Занесем одну строку в таблицу и проверим значение виртуального столбца:
SQL> INSERT INTO MyTable(Id) VALUES(0);
1 row created.
SQL> SELECT * FROM MyTable;
ID MYID
---------- ----------
0 1
SQL>
Как Вы наверно догадались, наc подстерегает одна очевидная опасность: при смене версии функции, виртуальный столбец изменит свое значение!
Например:
SQL> conn / as sysdba
Connected.
rem -- Создаем новую версию
SQL> CREATE EDITION MyVersion1 AS CHILD OF ORA$BASE;
Edition created.
SQL> GRANT USE ON EDITION MyVersion1 TO RSCOTT;
Grant succeeded.
Понятно, что если если наша функция
getMyId изменит свое поведение в новой версии, то значение виртуального столбца будет зависеть от текущей версии в сессии пользователя:
SQL> conn rscott/rtiger
Connected.
SQL> ALTER SESSION SET EDITION=MyVersion1;
Session altered.
SQL> create or replace function getMyId return number
deterministic is
begin
return 2;
end;
/
Function created.
SQL> SELECT * FROM MyTable;
ID MYID
---------- ----------
0 2
rem -- Переключаемся в старую версию:
SQL> ALTER SESSION SET EDITION=ORA$BASE;
Session altered.
SQL> SELECT * FROM MyTable;
ID MYID
---------- ----------
0 1
SQL>
2.2 Определение доступных версий для виртуальных столбцов в Oracle Database 12c
Начиная с Oracle Database 12c для виртуальных столбцов можно задавать
различные ограничения на используемые версии.
С помощь модификатора
EVALUATE USING CURRENT EDITION мы жестко фиксируем версию для виртуального столбца на версию, которая была в момент создания таблицы (либо в момент выдачи оператора ALTER TABLE):
[oracle@**** ~]$ sqlplus rscott/rtiger
SQL*Plus: Release 12.1.0.1.0 Production on Wed Nov 6 14:12:11 2013
Copyright (c) 1982, 2013, Oracle. All rights reserved.
Last Successful login time: Wed Nov 06 2013 14:07:51 -05:00
Connected to:
Oracle Database 12c Enterprise Edition Release 12.1.0.1.0 - 64bit Production
With the Partitioning, Real Application Clusters, Automatic Storage Management, OLAP,
Advanced Analytics and Real Application Testing options
SQL> CREATE TABLE myTable
(
Id NUMBER(9),
MyId as (getMyId()) EVALUATE USING CURRENT EDITION
);
/
Table created.
SQL> INSERT INTO MyTable(Id) VALUES(0);
1 row created.
SQL> SELECT * FROM MyTable;
ID MYID
---------- ----------
0 1
SQL> ALTER SESSION SET EDITION=MyVersion1;
Session altered.
SQL> SELECT * FROM MyTable;
ID MYID
---------- ----------
0 1
SQL>
Как видите, несмотря на переключение версий, виртуальный столбец всегда использует версию которая была в момент выдачи DDL-оператора.
Также мы можем явно указать используемую версию для виртуального столбца:
SQL> ALTER TABLE myTable MODIFY MyId as (getMyId())
EVALUATE USING EDITION MyVersion1;
/
Table altered.
SQL> ALTER SESSION SET EDITION=ORA$BASE;
Session altered.
SQL> SELECT * FROM MyTable;
ID MYID
---------- ----------
0 2
Если для виртуального столбца указать
EVALUATE USING NULL EDITION, то поведение виртуального столбца будет как в Oracle 11gR2 - значение будет вычисляться в текущей версии в которой происходит обращение к столбцу. Это поведение будет работать по умолчанию, - если фраза
EVALUATE USING для столбца не задана:
SQL> ALTER TABLE myTable MODIFY MyId as (getMyId())
EVALUATE USING NULL EDITION;
/
Table altered.
Дополнительно, c помощью фразы UNUSABLE BEGINNING WITH указывается версия, начиная с которой в иерархии версий, будет запрещено использование виртуального столбца:
SQL> CREATE TABLE myTable
(
Id NUMBER(9),
MyId as (getMyId()) UNUSABLE BEGINNING WITH EDITION MyVersion1
);
Table created.
SQL> INSERT INTO myTable(Id) VALUES(1);
1 row created.
SQL> COMMIT;
Commit complete.
SQL> SELECT * FROM mytable;
ID MYID
---------- ----------
1 1
SQL> ALTER SESSION SET EDITION=myversion1;
Session altered.
SQL> SELECT * FROM mytable;
SELECT * FROM mytable
*
ERROR at line 1:
ORA-00904: "RSCOTT"."GETMYID": invalid identifier
Наоборот, c помощью фразы
UNUSABLE BEFORE, можно указать версию, для всех родительских версий которой будет запрещено использование виртуального столбца.
2.3 Поддержка версионированных PL/SQL-функций в материализованных представлениях в Oracle Database 12c
До Oracle Database 12c было запрещено использование версионированных PL/SQL-функций в материализованных представлениях:
[oracle@**** ~]$ sqlplus / as sysdba
SQL*Plus: Release 11.2.0.3.0 Production on Sun Nov 11 15:02:16 2013
Copyright (c) 1982, 2011, Oracle. All rights reserved.
Connected to:
Oracle Database 11g Enterprise Edition Release 11.2.0.3.0 - 64bit Production
With the Partitioning, OLAP, Data Mining and Real Application Testing options
SQL> CREATE MATERIALIZED VIEW mymview AS
2 SELECT * FROM all_objects
3 WHERE getMyId=1;
CREATE MATERIALIZED VIEW mymview AS
*
ERROR at line 1:
ORA-38818: illegal reference to editioned object RSCOTT.GETMYID
Начиная с Oracle Database 12c стало возможным обращение к версионируемым PL/SQL-объектам внутри материализованного представления. Для этого необходимо при создании материализованного представления указать фразу
EVALUATE USING ..., либо фразу
UNUSABLE BEGINNING .... Назначение этих модификаторов установки версии для PL/SQL-вызовов внутри материализованных представлений, полностью совпадает с их назначением в рассмотренных ранее примерах версионированиия виртуальных столбцов:
[oracle@**** ~]$ sqlplus rscott/rtiger
SQL*Plus: Release 12.1.0.1.0 Production on Wed Nov 13 13:11:08 2013
Copyright (c) 1982, 2013, Oracle. All rights reserved.
Last Successful login time: Wed Nov 13 2013 13:07:37 -05:00
Connected to:
Oracle Database 12c Enterprise Edition Release 12.1.0.1.0 - 64bit Production
With the Partitioning, Real Application Clusters, Automatic Storage Management, OLAP,
Advanced Analytics and Real Application Testing options
SQL> CREATE MATERIALIZED VIEW mview
2 EVALUATE USING EDITION MyVersion1 AS
3 SELECT * FROM all_objects
4 WHERE getmyid=1;
Materialized view created.
В вышерассмотренном примере, для вызова функции getMyId жестко устанавливается версия MyVersion1.
Как Вы могли заметить, установка версии действует на все PL/SQL-вызовы внутри материализованного представления: в вычисляемых столбцах, и в предикатах фразы WHERE.
3 Версионирование для публичных синонимов (public synonym)
В Oracle Database 11g Release 2 (11.2) публичный синоним не мог ссылаться на версионируемый объект:
[oracle@**** ~]$ sqlplus / as sysdba
SQL*Plus: Release 11.2.0.3.0 Production on Sun Nov 11 16:23:16 2013
Copyright (c) 1982, 2011, Oracle. All rights reserved.
Connected to:
Oracle Database 11g Enterprise Edition Release 11.2.0.3.0 - 64bit Production
With the Partitioning, OLAP, Data Mining and Real Application Testing options
SQL> CREATE PUBLIC SYNONYM getMyId FOR getMyId;
CREATE PUBLIC SYNONYM getMyId FOR getMyId;
*
ERROR at line 1:
ORA-38818: illegal reference to editioned object RSCOTT.GETMYID
В версии 12с эта проблема решена и теперь публичный синоним может версионироваться. Для создания версионируемого синонима при его создании необходимо указать ключевое слово EDITIONABLE
[oracle@**** ~]$ sqlplus rscott/rtiger
SQL*Plus: Release 12.1.0.1.0 Production on Wed Nov 13 13:54:07 2013
Copyright (c) 1982, 2013, Oracle. All rights reserved.
Last Successful login time: Wed Nov 13 2013 13:11:08 -05:00
Connected to:
Oracle Database 12c Enterprise Edition Release 12.1.0.1.0 - 64bit Production
With the Partitioning, Real Application Clusters, Automatic Storage Management, OLAP,
Advanced Analytics and Real Application Testing options
SQL> CREATE EDITIONABLE PUBLIC synonym getMyId FOR getMyId;
Synonym created.
Заключение
В новейшей версии СУБД Oracle Database - 12c, технология обновления PL/SQL-кода без остановки - Edition Base Redefinition, получила свое дальнейшее развитие. Появились такие мощные возможности, как потенциальное версионирование на уровне отдельного объекта, версионирование виртуальных столбцов, версионирование кода в материализованных представлениях. Также следует отметить очень полезную новую возможность - версионирование публичных синонимов.