Oracle 12cR2, primi test con gli Application Container

Dopo aver letto un po’ di documentazione sull’argomento “application container” in Oracle 12cR2 sono passato a dei “test sul campo”. Ho recuperato una installazione fatta qualche mese fa e ho cominciato a fare un po’ di prove. Va premesso che l’argomento è abbastanza complesso, nel senso che le cose che si possono fare sono tante, io mi limito a riportare delle semplici prove che credo siano utili per cominciare a “entrare” nell’argomento.

L’ambiente di partenza era una installazione 12.2.0.1, siccome c’è stato un cambio di macchina per la precisione ho spostato il database da una macchina ad un’altra. Il database era stato gia creato come CDB (se non ho capito male non c’è modo di passare da non-CDB a CDB se non creando un nuovo database, qui si parla di qualcosa di simile). In quel CDB avevo gia creato un PDB che poi era stato usato per un breve test di una funzionalità.

Tramite la query:

select * from database_properties where property_name=’LOCAL_UNDO_ENABLED’;

ho verificato che il database era gia in modalità “LOCAL UNDO”, infatti è il default.

A questo punto ho creato il mio primo application container:

12:45:46 SQL> CREATE PLUGGABLE DATABASE test122ac AS APPLICATION CONTAINER ADMIN USER psystem IDENTIFIED BY manager ROLES = (DBA)
FILE_NAME_CONVERT = (‘/u01/app/oracle/oradata/test122/pdbseed/’, ‘/u01/app/oracle/oradata/test122/test122ac/’);12:45:54 2

Pluggable database created.

Elapsed: 00:00:16.18

select name,open_mode,application_root,local_undo from v$pdbs;
12:51:48 SQL> select name,open_mode,application_root,local_undo from v$pdbs;

NAME OPEN_MODE APP LOCAL_UNDO
——————– ———- — ———-
PDB$SEED READ ONLY NO 1
TEST122P1 READ WRITE NO 1
TEST122AC MOUNTED YES 1

 

Bene, a questo punto volevo portare dentro l’application container il PDB esistente (test122p1). Quindi i passi fatti sono brevemente:

  • avvio application container test122ac
  • arresto PDB test122p1
  • unplug PDB test122p1
  • drop PDB test122p1
  • plug PDB test122p1 in test122ac

Ecco, fin qui non ho avuto problemi, sono passato alla creazione di un nuovo PDB sotto lo stesso application container test122ac:

SQL> CREATE PLUGGABLE DATABASE svil122p1 ADMIN USER psystem IDENTIFIED BY manager ROLES = (DBA)
FILE_NAME_CONVERT = (‘/u01/app/oracle/oradata/test122/pdbseed/’, ‘/u01/app/oracle/oradata/test122/svil122p1/’); 2

Pluggable database created.

A questo punto sono andato a dare un’occhiata all’alert.log e vi ho trovato questo messaggio:

TEST122P1(5):Database Characterset for TEST122P1 is AL32UTF8
2018-08-29T16:06:53.458517+02:00
TEST122P1(5):Opatch validation is skipped for PDB TEST122P1 (con_id=0)
TEST122P1(5):***************************************************************
TEST122P1(5):WARNING: Pluggable Database TEST122P1 with pdb id – 5 is
TEST122P1(5): altered with errors or warnings. Please look into
TEST122P1(5): PDB_PLUG_IN_VIOLATIONS view for more details.
TEST122P1(5):***************************************************************

In effetti interrogando la vista PDB_PLUG_IN_VIOLATIONS ho trovato questo messaggio:

Non-Application PDB plugged in as an Application PDB, requires pdb_to_apppdb.sql be run

Come utente SYS ho eseguito lo script pdb_to_apppdb.sql, sulla vista PDB_PLUG_IN_VIOLATIONS la colonna STATUS è passata da “PENDING” a “RESOLVED” (quindi il record rimane li) e il problema è rientrato.

Ora è arrivato il momento di testare la creazione di una applicazione. Qui la cosa secondo me si fa complessa perché occorre tenere conto di un po’ di vincoli, legati al fatto che un’applicazione che viene definita sull’application container poi verrà in qualche modo “replicata” o installata sui vari PDB. Questo implica che occorre fare attenzione che il “contesto” si replicabile. Un primo esempio, con la spiegazione di un limite di cui tenere conto viene ben descritto in questo post, come l’autore spiega nel post di aggiornamento infatti  se la definizione dell’applicazione prevede la creazione di tablespace allora si è vincolati a usare la struttura OMF, come ha fatto Tim Hall nel suo eccellente articolo. Ora, io sono partito con una prova molto più semplice, in cui nell’applicazione creavo solo una tabella, solo che l’ho fatto con l’utenza PSYSTEM creata assieme all’application container. Ecco qui ho incontrato il primo problema, quando sono andato su TEST122p1 ed ho cercato di fare la sincronizzazione. Infatti anche utilizzando l’utenza SYS (prima avevo provato sempre con PSYSTEM) ottenevo sempre l’errore di privilegi insufficenti:

alter pluggable database application appcri1 sync
*
ERROR at line 1:
ORA-01031: insufficient privileges

Non ci sono arrivato subito, è nel tentativo di risolvere quel problema che sono incappato prima nel problema oggetto del mio post precedente e poi nel post di Anju Garg che ho citato prima. Per farla breve il problema era che il role PDB_DBA su TEST122p1 non aveva il role DBA. In mezzo avevo provato disperatamente a dare anche SYSDBA a PSYSTEM e comunque non funzionava. In realtà questo prova che nel definire un’applicazione occorre usare un approccio come quello esemplificato da Tim Hall, quindi creando anche tablespace (per cui però occorre usare OMF) e utenti/schemi.

Ho quindi testato la funzionalità di disinstallazione di una applicazione da un application container, ho lanciato questi comandi:

alter pluggable database application appcri2 begin uninstall;
drop table common_table_appcri2;
alter pluggable database application appcri2 end uninstall;

Ritengo interessante riportare un estratto dell’alert.log da cui si vede ciò che i comandi sopra hanno scatenato, ovvero la creazione un clone dell’application root che permette di mantenere la versione dell’applicazione com’era prima della disintallazione:

TEST122AC(4):alter pluggable database application appcri2 begin uninstall
CREATE PLUGGABLE DATABASE “F1450013744_4_1” AS APPLICATION CONTAINER from “TEST122AC” CREATE_FILE_DEST=’/u01/app/oracle/oradata/test122/test122ac/’
2018-08-30T12:47:51.000009+02:00
TEST122AC(4): APEX_050000.WWV_FLOW_ADVISOR_CHECKS (CHECK_STATEMENT) – CLOB populated
2018-08-30T12:48:05.018535+02:00
F1450013744_4_1(6):Endian type of dictionary set to little
****************************************************************
Pluggable Database F1450013744_4_1 with pdb id – 6 is created as UNUSABLE.
If any errors are encountered before the pdb is marked as NEW,
then the pdb must be dropped
local undo-1, localundoscn-0x00000000000000e0
****************************************************************
F1450013744_4_1(6):Media Recovery Start
2018-08-30T12:48:05.263003+02:00
F1450013744_4_1(6):Serial Media Recovery started
2018-08-30T12:48:05.323789+02:00
F1450013744_4_1(6):Recovery of Online Redo Log: Thread 1 Group 3 Seq 144 Reading mem 0
F1450013744_4_1(6): Mem# 0: /u01/app/oracle/oradata/test122/redo03.log
2018-08-30T12:48:05.361129+02:00
F1450013744_4_1(6):Incomplete Recovery applied until change 6934636 time 08/30/2018 12:48:04
2018-08-30T12:48:05.368956+02:00
F1450013744_4_1(6):Media Recovery Complete (test122)
F1450013744_4_1(6):Autotune of undo retention is turned on.
2018-08-30T12:48:06.332381+02:00
F1450013744_4_1(6):[20290] Successfully onlined Undo Tablespace 2.
2018-08-30T12:48:06.370038+02:00
F1450013744_4_1(6):Undo initialization finished serial:0 start:3099160625 end:3099160912 diff:287 ms (0.3 seconds)
F1450013744_4_1(6):Database Characterset for F1450013744_4_1 is AL32UTF8
F1450013744_4_1(6):JIT: pid 20290 requesting stop
Completed: CREATE PLUGGABLE DATABASE “F1450013744_4_1” AS APPLICATION CONTAINER from “TEST122AC” CREATE_FILE_DEST=’/u01/app/oracle/oradata/test122/test122ac/’
ALTER PLUGGABLE DATABASE “F1450013744_4_1” OPEN
F1450013744_4_1(6):Autotune of undo retention is turned on.
F1450013744_4_1(6):Endian type of dictionary set to little
2018-08-30T12:48:07.583580+02:00
F1450013744_4_1(6):[20290] Successfully onlined Undo Tablespace 2.
F1450013744_4_1(6):Undo initialization finished serial:0 start:3099161622 end:3099162160 diff:538 ms (0.5 seconds)
F1450013744_4_1(6):Deleting old file#16 from file$
F1450013744_4_1(6):Deleting old file#17 from file$
F1450013744_4_1(6):Deleting old file#18 from file$
F1450013744_4_1(6):Adding new file#30 to file$(old file#16)
F1450013744_4_1(6):Adding new file#31 to file$(old file#17)
F1450013744_4_1(6):Adding new file#32 to file$(old file#18)
****************************************************************
Post plug operations are now complete.
Pluggable database F1450013744_4_1 with pdb id – 6 is now marked as NEW.
****************************************************************
F1450013744_4_1(6):Database Characterset for F1450013744_4_1 is AL32UTF8
F1450013744_4_1(6):Opatch validation is skipped for PDB F1450013744_4_1 (con_id=0)
2018-08-30T12:48:13.067787+02:00
F1450013744_4_1(6):Opening pdb with no Resource Manager plan active
Pluggable database F1450013744_4_1 opened read write
Completed: ALTER PLUGGABLE DATABASE “F1450013744_4_1” OPEN
ALTER PLUGGABLE DATABASE “F1450013744_4_1” CLOSE
F1450013744_4_1(6):JIT: pid 20290 requesting stop
2018-08-30T12:48:14.643037+02:00
Pluggable database F1450013744_4_1 closed
Completed: ALTER PLUGGABLE DATABASE “F1450013744_4_1” CLOSE
ALTER PLUGGABLE DATABASE “F1450013744_4_1” OPEN READ ONLY INSTANCES=ALL
F1450013744_4_1(6):Autotune of undo retention is turned on.
F1450013744_4_1(6):Endian type of dictionary set to little
F1450013744_4_1(6):Undo initialization finished serial:0 start:3099169330 end:3099169330 diff:0 ms (0.0 seconds)
F1450013744_4_1(6):Database Characterset for F1450013744_4_1 is AL32UTF8
F1450013744_4_1(6):Opatch validation is skipped for PDB F1450013744_4_1 (con_id=0)
F1450013744_4_1(6):Opening pdb with no Resource Manager plan active
Pluggable database F1450013744_4_1 opened read only
Completed: ALTER PLUGGABLE DATABASE “F1450013744_4_1” OPEN READ ONLY INSTANCES=ALL
TEST122AC(4):Completed: alter pluggable database application appcri2 begin uninstall
2018-08-30T12:49:02.396116+02:00
TEST122AC(4):alter pluggable database application appcri2 end uninstall
TEST122AC(4):Completed: alter pluggable database application appcri2 end uninstall

In verità non mi sembra sia possibile ripristinare una applicazione disintallata… però il clone serve a gestire il fatto che ci siano PDB collegati all’application container su cui non è stata fatta la sincronizzazione e quindi l’applicazione rimane installata.

Come avevo scritto nel mio post di introduzione agli “application container” ho testato la possibilità di creare più applicazioni su uno stesso application container; è possibile quindi, seppur non so quanto abbia senso, creare più applicazioni su uno stesso application container.

Dopo il primo test di base ho quindi disinstallato entrambe le applicazioni che avevo creato trovandomi con due cloni della application root. Ho quindi fatto un nuovo test cercando di creare un’applicazione “completa”, quindi sulla base dell’esempio di Tim Hall creando tablespace e schema al cui interno poi creare gli oggetti. Mi sono trovato un po’ in difficoltà a capire i privilegi necessari, negli esempi, anche  sui manuali si utlizza l’utenza SYS, però mi sembra un po’ eccessivo dover utilizzare una utenza superprivilegiata per installare delle applicazioni. Ho deciso di rimandare l’approfondimento sul tema privilegi ad  un’altra occasione e sono andato avanti con l’utenza SYS per creare una nuova applicazione con queste istruzioni:

alter session set db_create_file_dest=’/u01/app/oracle/oradata/test122/test122ac’;
alter pluggable database application appcri3 begin install ‘1.0’;
create tablespace apptbs1 datafile size 1 M autoextend on maxsize 2 g;
create user app1user identified by app1user default tablespace apptbs1 quota unlimited on apptbs1 container=ALL;
grant create session, create table to app1user;
create table app1user.apptable1 sharing=extended data (a number,b varchar2(100 char));
insert into app1user.apptable1 (a,b) values (1,’a’);
commit;
alter pluggable database application appcri3 end install;

Ho fatto una scelta un po’ bizzarra, ho usato OMF ma ho impostato il parametro DB_CREATE_FILE_DEST a livello di sessione, questo comporta occorrerà fare attenzione in fase di sincronizzazione dell’applicazione sui PDB, infatti se non si setta prima della sincronizzazione opportunamente il parametro accade questo:

SYS@//svil122p1 AS SYSDBA> alter pluggable database application appcri3 sync;
alter pluggable database application appcri3 sync
*
ERROR at line 1:
ORA-02236: invalid file name

Se invece si imposta prima il parametro DB_CREATE_FILE_DEST tutto fila liscio; mi sembra chiaro che se si vuole gestire in modo efficiente è utile impostare il parametro a livello di system root, quindi usare OMF per la gestione degli application container e dei PDB.

Ho fatto poi un banale test di aggiornamento dell’applicazione con questi comandi:

alter pluggable database application appcri3 begin upgrade ‘1.0’ to ‘1.1’;
create table app1user.apptable2 sharing=metadata (a number,b varchar2(100 char));
insert into app1user.apptable2 (a,b) values (2,’b’);
commit;
alter pluggable database application appcri3 end upgrade;

Mi sono trovato quindi con tre cloni della application root. A questo punto mi sono chiesto se è possibile contenere la prolificazione di questi cloni. In effetti un metodo c’è ed è l’impostazione del livello di compatibilità. Lanciando questo comando:

alter pluggable database application appcri3 set compatibility version ‘1.1’;

Sull’alert.log ho trovato questo:

TEST122AC(4):alter pluggable database application appcri3 set compatibility version ‘1.1’
ALTER PLUGGABLE DATABASE “F1450013744_23_1” CLOSE
2018-08-31T14:43:06.003621+02:00
F1450013744_23_1(8):JIT: pid 20697 requesting stop
Pluggable database F1450013744_23_1 closed
Completed: ALTER PLUGGABLE DATABASE “F1450013744_23_1” CLOSE
DROP PLUGGABLE DATABASE “F1450013744_23_1” INCLUDING DATAFILES
TEST122AC(4):Deleted Oracle managed file /u01/app/oracle/oradata/test122/test122ac/TEST122/74A7AB8E0E337014E0533B00640AEA9C/datafile/o1_mf_apptbs1_frhtnv92_.dbf
TEST122AC(4):Deleted Oracle managed file /u01/app/oracle/oradata/test122/test122ac/TEST122/74A7AB8E0E337014E0533B00640AEA9C/datafile/o1_mf_temp_frhtnv92_.dbf
TEST122AC(4):Deleted Oracle managed file /u01/app/oracle/oradata/test122/test122ac/TEST122/74A7AB8E0E337014E0533B00640AEA9C/datafile/o1_mf_undotbs1_frhtnv92_.dbf
TEST122AC(4):Deleted Oracle managed file /u01/app/oracle/oradata/test122/test122ac/TEST122/74A7AB8E0E337014E0533B00640AEA9C/datafile/o1_mf_sysaux_frhtnv91_.dbf
TEST122AC(4):Deleted Oracle managed file /u01/app/oracle/oradata/test122/test122ac/TEST122/74A7AB8E0E337014E0533B00640AEA9C/datafile/o1_mf_system_frhtnv90_.dbf
Completed: DROP PLUGGABLE DATABASE “F1450013744_23_1” INCLUDING DATAFILES
TEST122AC(4):Completed: alter pluggable database application appcri3 set compatibility version ‘1.1’

E in effetti il clone è stato rimosso:

SYS@//test122ac AS SYSDBA> select con_id,name,APPLICATION_ROOT_CON_ID,APPLICATION_ROOT_Clone from v$containers;

CON_ID NAME APPLICATION_ROOT_CON_ID APP
———- —————— ———————– —
1 CDB$ROOT NO
2 PDB$SEED NO
3 SVIL122P1 4 NO
4 TEST122AC NO
5 TEST122P1 4 NO
6 F1450013744_4_1 4 YES
7 F1450013744_3_1 4 YES

Esiste anche l’opzione di impostare il livello di compatibilità al valore “corrente”:

alter pluggable database application appcri1 set compatibility version current;

In questo modo anche i cloni creati in seguiti alla disinstallazione delle applicazioni sono stati rimossi, cosa che mi è piaciuta. Nel dizionario dati, come scritto sulla documentazione rimangono comunque le informazioni sulle applicazioni:

SYS@//test122ac AS SYSDBA> select * from DBA_APP_PDB_STATUS;

CON_UID APP_NAME APP_ID APP_VERSION APP_STATUS
———- ——————– ———- —————————— ———–
4143301262 APP$7491A9CF30E3674F 2 1.0 NORMAL
E0533B00640A0B7F

1030522367 APP$7491A9CF30E3674F 2 1.0 NORMAL
E0533B00640A0B7F

4143301262 APPCRI3 23 1.1 NORMAL
1030522367 APPCRI3 23 1.1 NORMAL
4143301262 APPCRI1 3 1.0 UNINSTALLED
1030522367 APPCRI1 3 1.0 UNINSTALLED
1030522367 APPCRI2 4 1.0 UNINSTALLED
4143301262 APPCRI2 4 1.0 UNINSTALLED

8 rows selected.

Lascia un commento