Oracle数据库升级向来是一门纷繁复杂的工程,DBA需要为产品数据库的升级耗费大量时间精力在准备工作上;因为其升级复杂度高,所以即便做了较为充分的准备仍可能在升级过程中遇到意想不到的问题,为了更高效地完成升级任务和减少停机时间,我们有必要为升级工作营造一种”舒适的”防御式的数据库”氛围”:


1.为了保障升级后的数据库性能,我们有必要在升级前有效地收集数据库的性能统计信息,以便升级后若发生性能问题可以做出对比:

(1)    为了保证性能统计信息真实有效,有必要在数据库升级前的一个月即开展收集工作

(2)    收集的性能统计信息应当尽可能的精确真实

(3)    在Oracle 8i/9i中使用Statspack性能报表,将快照级别设置为6或更高,设置快照间隔为30分钟,在具体升级前将perfstat用户使用exp工具导出,参考Metalink文档​​Note:466350.1​​介绍了若何对比升级前后的Statspack快照

(4)    在Oracle 10g/11g中使用AWR自动负载仓库性能报告,保证采集30天左右的快照,快照间隔最好为30-60分钟;之后可以使用dbms_swrf_internal.awr_extract存储过程将AWR导出到dumpfile文件,在升级完成后载入这部分AWR信息,并可以使用DBMS_WORKLOAD_REPOSITORY.AWR_DIFF_REPORT_HTML函数对比升级前后的性能


2.正式升级前的防御性措施:


(1)过多的审计信息可能会导致升级速度下降,可以在升级前将审计数据导出,并清理审计字典基表:

截断SYS.AUD$基表:

SQL>TRUNCATETABLE SYS.AUD$;


Oracle 11g 的审计,更多内容参考:


(2)同样的有必要清理10g后出现的回收站:

清理DBA回收站:

SQL>purge DBA_RECYCLEBIN;


(3)移除一些”过期”的参数,设置这些参数的原因很有可能是为了修正原版本上的一些问题,例如我们都会做的设置event参数;但在新版本中这些参数是否仍有必要设置是一个值得讨论的问题,当然你完全可以就此事去提交一个SR:

这些"过期"参数可能包括:过老的如optimizer_features_enable=8.1.7.4,_always_semi_join=off,_unnest_subquery=false

或者event ="10061 trace name context forever, level 10",如此之类等等。


有关参数是否过时,可以从V$OBSOLETE_PARAMETER视图查看。


(4)为数据库中的数据字典收集统计信息:

在Oracle 9i中可以执行以下过程收集数据字典统计信息,

SQL> exec DBMS_STATS.GATHER_SCHEMA_STATS

    ('SYS', options => 'GATHER',estimate_percent =>

     DBMS_STATS.AUTO_SAMPLE_SIZE, method_opt => 'FOR

     ALL COLUMNS SIZE AUTO', cascade => TRUE);


在Oracle10g/11g中收集字典统计信息可以由GATHER_DICTIONARY_STATS存储过程来完成:

SQL> execDBMS_STATS.GATHER_DICTIONARY_STATS;


这个脚本在Oracle11g升级前的检查脚本(utlu112i.sql)中也会推荐我们执行。


(5)为策万全,我们有必要为回退数据库升级任务做好准备,10g以前只能通过备份恢复来完成,10g以后我们可以利用闪回数据库的还原点特性来回退数据库,但需要注意以下几点:

(1)    利用还原点要求数据库处于归档且打开flashback database的模式下

(2)    在特性仅在版本10.2之后可用

(3)    必须保证闪回回复区flashback recovery area有足够的磁盘空间

(4)    注意在升级后不要立即修改compatible参数,restore point无法跨越compatible工作


有关FlashbackRestore Points的更多说明和示例,参考我的Blog:


(6)下载最新版本的预升级检查脚本(pre-upgrade checkscript),如utlu102i.sql/ utlu111i.sql / utlu112i.sql;Metalink文档​​Note:884522.1​​ <Howto Download and Run Oracle’s Database Pre-Upgrade Utility> 指出了各版本utluxxx脚本的下载地址

       在11g中自带了这个脚本,不需要下载。


/* 将升级信息spool到日志文件中 */

SQL> SPOOL /tmp/UPGRADE/utlu112i.log

SQL> @/tmp/UPGRADE/utlu112i.sql



(7)需要关注SYS和SYSTEM用户模式下的失效对象,有必要在升级前修复所有的失效对象:

SELECT UNIQUE object_name, object_type,owner

 FROM dba_objects

 WHERE status = 'INVALID';


(8) 在升级完成后推荐执行utlrp.sql脚本以重新编译(Recompile)对象,从11.1.0.7开始升级前后的失效对象将自动对比,执行?/rdbms/admin/utluiobj.sql脚本可以列出对比信息,同时基表registry$sys_inv_objs和registry$nonsys_inv_objs分别列出了数据库中失效的sys或非sys对象:


SQL> @?/rdbms/admin/utluiobj.sql

.

Oracle Database 11.1 Post-Upgrade InvalidObjects Tool 03-05-2012 16:52:29

.

This tool lists post-upgrade invalidobjects that were not invalid

prior to upgrade (it ignores pre-existingpre-upgrade invalid objects).

.

Owner                     Object Name                     Object Type

.

SYS                   DBMS_CUBE_EXP                    PACKAGE BODY

SYS         DBMS_NETWORK_ACL_ADMIN                   PACKAGE BODY

SYS   DBMS_XS_PRINCIPAL_EVENTS_INT                    PACKAGE BODY

SYS                     KUPW$WORKER                    PACKAGE BODY

SYS                 XS$CATVIEW_UTIL                    PACKAGE BODY


PL/SQL procedure successfully completed.


3.解决升级过程中失效的组件(component)

(1)    确保该部分组件确实被link到目前的Oracle软件2进制可执行文件或库文件中

(2)    如果确认不会用到某些组件(component),想要通过手动彻底移除这部分组件(亦或者希望reinstall重新安装这部分组件),那么可以参考以下文档:


Note:472937.1 Information On InstalledDatabase Components/Schemas

Note.300056.1 Debug and Validate InvalidObjects

Note:753041.1 How to diagnose Componentswith NON VALID status

Note.733667.1 How to Determine if XDB isBeing Used in the Database?


组件升级失败实例1:

数据库从10.2升级到11.2,在10g的环境中Database Vault组件已经安装,Database Vault组件在升级relink前被turned off,在升级到11.2的过程中XDB组件升级失败;其原因在于安装或切换Database Vault将使得XDB组件失效,或者由Bug 8942758引起。

解决方案:在升级前执行utlrp.sql脚本重新编译失效对象和组件,在此例中执行utlrp.sql可以使XDB组件valid.


组件升级失败实例2:

数据库从10.2.0.4升级到11.1.0.7,在升级过程中"ORACLE SERVER"组件失效;其原因在于DMBS_SQLPA包引用了某个不存在的列,该问题可以参考metalink文档782735.1和Notes:605317.1/736353.1。


有效的解决方案是:

(1).在升级前将SYS.PLAN_TABLE$基表或者同义词PUBLIC.PLAN_TABLE DROP掉

(2).若已执行了升级操作并遭遇了该问题,那么可以使用以下手段修复该问题:

@catplan.sql -- recreate the plan table

@dbmsxpln.sql -- reload dbms_xplan spec

@prvtxpln.plb -- reload dbms_xplanimplementation

@prvtspao.plb -- reload dbms_sqlpa

alter package SYS.DBMS_SUMADVISOR compile ;

alter package SYS.DBMS_SUMADVISOR compilebody;



4. 使用例如AIX上的slibclean等命令清理操作系统环境,在少数专有平台上不清理载入的共享库文件可能导致升级失败


5.在执行catupgrd.sql脚本正式升级前打开sqlplus的echo输出,将升级过程中所有的输出信息转储到日志文件中:

SQL> set echo on

--默认为off,设为on 会显示执行的sql语句,而不仅仅是结果。

SQL> SPOOL /tmp/upgrade.log

SQL> @catupgrd.sql

SQL> spool off


DBUA图形化升级工具默认使用spool和”echo”输出,这些日志可以在$ORACLE_HOME/cfgtoollogs/dbua//upgrade/目录下找到。