viernes, 18 de julio de 2014

Arquitectura de alta disponibilidad con Oracle Standard Edition (SE)

Como configurar una arquitectura de alta disponibilidad con Oracle Standard Edition (SE)
Hace un tiempo un cliente me pidio armar una arquitectura de alta disponibilidad de forma tal de que la base de datos productiva tuviera un "espejo" y que, por ejemplo, ante un fallo de hardware severo del nodo principal pudiera activarse
el nodo de respaldo con la base "espejo" y que esto no dejara mas de unos pocos minutos al sistema corporativo sin base de datos.

Este esquema no provee la robustez de un DATA GUARD pero se acerca bastante. Como voy a explicar mas adelante, con este modelo de no podemos asegurar que no se pierda lo que se persistio los últimos minutos, pero dado que el negocio podía contemplar esta perdida se decidió implementar la arquitectura que propuse. A continuación voy a explicar paso a paso, llamaré NODO1 al nodo principal y activo y NODO2 al nodo secundario o stand-by que esta en modalidad pasiva.

1. Instalar el motor de base de datos en el NODO 2. Asegurarse que el S.O sea el mismo que el instalado en el NODO 1, debe tener el mismo nivel de parches, misma arquitectura (32 ó 64 bits) y la base debe tener la misma versión y nivel de parches
que la base productiva.

2. La base de producción (NODO1) deberá estar en modo archiving (esto para mi es excluyente para cualquier base productiva asi que lo
tomo como algo obvio). Copiar con RMAN los datafiles de la siguiente manera:

$rman target / no catalog

RMAN>report schema; <-- br="" copiar.="" datafiles="" los="" necesitamos="" para="" que="" ver="">
Una vez que tengo el listado de los datafiles de la base de datos se van copiando uno por uno a un directorio de backups,
por ejemplo para copiar el datafile system01.dbf:

RMAN>copy datafile '/u01/oradata/ROP102/system01.dbf' to '/u01/bkp/ROP102/system01.dbf';

3. Crear el control file standby desde la base de datos primaria (NODO1)

SQLPLUS> ALTER DATABASE CREATE STANDBY CONTROLFILE AS '/u01/bkp/ROP102/control_stdy.ctl';

4. Copiar los datafiles respaldados con el comando copy de rman (paso 2), el control file standby creado en el paso 3
y el archivo de parametros de la base productiva al NODO 2, por ejemplo para pasar los datafiles:

$scp /u01/bkp/ROP102/*.dbf nodo2:/u01/oradata/ROP102/.

Si tenemos distinta estructura de directorios donde van los datafiles entre el NODO1 y el NODO2 tenemos que editar el archivo
de parametros y agregar el siguiente parametro:

DB_FILE_NAME_CONVERT='/u01/oradata/ROP102','u02/oradata/ROP102'

5. Ahora ya tenemos todos los archivos que necesitamos para levantar la base standy en el NODO2.

Se levanta la base en modo nomount usando el archivo de parametros copiado:

SQLPLUS>startup nomount pfile=/u01/app/oracle/products/10.2.0.1/db_1/dbs/iniROP102.ora

Se monta la base en modalidad standby:

SQLPLUS>alter database mount standby database;

6. Una vez que tenemos la base montada en standby solo resta realizar recover de la base en modo AUTO para poner los
datafiles en modo consistente.

SQLPLUS>recover standby database;
AUTO

7. Para chequear que nuestra base standby esta ok, podemos abrirla en modo read only:

SQLPLUS>alter database open read only;


Scripting necesario para la configuración inicial

En NODO 1 - Base de Datos Primaria

El siguiente script se encarga de transferir al nodo standby (NODO 2) las novedades, es decir los
archivelogs que se hayan generado desde la ultima transferencia.

-- move_stdby.sh
rsync -t -e ssh -Pazv /u01/oradata/ROP102/arch/ oracle@dbprod2:/u01/oradata/ROP102/arch/

Para purgar los archivos que ya no se necesiten usamos:

-- purge_arch_nodo1.sh
find /u01/oradata/ROP102/arch/*.arc -mtime +2 -exec rm {} \;

Una posible programación de los scripts del nodo 1 podria ser:

0,30 * * * * /home/oracle/move_stdby.sh <-- 1="" 2="" 30="" al="" br="" cada="" del="" mueven="" nodo="" se="">0 7 * * * /home/oracle/purge_arch.sh <-- 7am="" a="" archives="" borran="" br="" dias="" las="" los="" se="" todos="">

En NODO 2 - Base de Datos StandBy


Para aplicar los nuevos archives tranferidos:

-- apply_redo_stdby.sh
export ORACLE_SID=ROP102
export ORACLE_HOME=/u01/app/oracle/product/10.2.0
$ORACLE_HOME/bin/sqlplus -s "/ as sysdba" << EOF
recover standby database;
AUTO
exit
EOF

Para levantar la base en modo standby y preparada para aplicar archives:

-- manual_stdby.sh
sqlplus -s "/ as sysdba" << EOF
shutdown immediate;
startup nomount pfile=/u01/app/oracle/product/10.2.0/dbs/initROP102_stdby.ora
alter database mount standby database;
exit
EOF

Para levantar la base en modo solo lectura

-- readonly_stdby.sh
sqlplus -s "/ as sysdba" << EOF
alter database open read only;
exit
EOF

Para purgar los archives copiados al nodo standby

-- purge_arch_nodo2.sh

find /u01/oradata/ROP102/arch/*.arc -mtime +6 -exec rm {} \;
[oracle@dbprod2 ~]$

Una posible programación de los scripts del nodo 1 podria ser:

0,30 * * * * /home/oracle/apply_redo_stdby.sh <-- 30="" a="" aplican="" base="" br="" cada="" cambios="" la="" los="" se="" standby="">0 7 * * * /home/oracle/purge_arch.sh <-- 7am="" a="" archives="" borran="" br="" dias="" las="" los="" se="" todos="">

La base standby esta continuamente aplicando archives, eso se puede chequear en el alert. Cuando la base standby esta en modo solo lectura no puede aplicar nuevos archives. En ciertas ocasiones resulta util tener la base standby en modo read only para realizar reportes y así evitar sobrecargar la base primaria.


Como hacer el switchover en el caso de que falle la base de datos primaria

Si la base primaria falla y no puede recomponerse (por ejemplo por un problema serio de HW) hay que activar la base standby. Para que pueda cumplir el rol de base primaria tendremos que levantarla en modo read write y hacer los siguiente:

1. Aplicar todos los archives que que aun no se hayan aplicado y que hayan pasado al nodo 2.

2. Hacer backup to trace del control file con la base standby en modo read only.

SQLPLUS> alter database backup controlfile to trace as '/u01/oradata/ROP102/control.txt'

3. Levantar la base standby en modo nomount y crear el control file usando en script del control file creado en el paso 2.

SQLPLUS> startup nomount pfile=/u01/app/oracle/product/10.2.0/dbs/initROP102_stdby.ora

Editar el archivo control.txt y dejar solo la ultima sentencia de creación del controlfile. Comentar todas las otras lineas

SQLPLUS>@/u01/oradata/ROP102/control.txt

4. Montar la base usando el nuevo controlfile

Editar el archivo de parametros y cambiar el nombre del controlfile para que se referencie el controlfile recien creado

SQLPLUS>startup mount pfile=/u01/app/oracle/product/10.2.0/dbs/initROP102_stdby.ora

5. Abrir la base en modo resetlogs

SQLPLUS>alter database open resetlogs;

martes, 1 de julio de 2014

LIMPIAR BASELINES

 select * from DBSNMP.BSLN_BASELINES;
      DBID INSTANCE_NAME    BASELINE_ID BSLN_GUID TI A STATUS       LAST_COMP
---------- ---------------- ----------- -------------------------------- -- - ---------------- ---------
2150325182 orcl      0 6451AA8D042DB3D952214555174DC9DA HX Y ACTIVE       02-FEB-14
2150325182 orcl      0 4C22FDB287A43E1D9BD50E06047E35F7 NX Y ACTIVE       02-FEB-14
 delete from DBSNMP.BSLN_BASELINES where INSTANCE_NAME='orcl';
1 row deleted.
> select * from DBSNMP.BSLN_BASELINES;
      DBID INSTANCE_NAME    BASELINE_ID BSLN_GUID TI A STATUS       LAST_COMP
---------- ---------------- ----------- -------------------------------- -- - ---------------- ---------
2150325182 orcl      0 6451AA8D042DB3D952214555174DC9DA HX Y ACTIVE       02-FEB-14
> commit;
Commit complete.
> exec dbms_scheduler.run_job('BSLN_MAINTAIN_STATS_JOB',false);
PL/SQL procedure successfully completed.
> select log_date,status from dba_scheduler_job_run_details where job_name='.BSLN_MAINTAIN_STATS_JOB. '';  ;