数据库

位置:IT落伍者 >> 数据库 >> 浏览文章

忘却Oracle的5个方面


发布日期:2021年01月28日
 
忘却Oracle的5个方面

新版本可以给软件带来更高效率的技术现在我们可以忘却Oracle数据库的个方面

只有DBA可以恢复数据

以SQL数据库——DBAs直接工作的人们以及IT资讯人员都可以因为一个不匹配的命令而导致数据库的破坏或者数据的丢失事实上对于Oracle用户的错误操作是导致数据库停止工作的主要原因从数据库而不是开发过程得到的一个表单可以造成程序及其所有用户操作的瘫痪而且一个不合适的更新也有可能破坏数据库操作的结果

直到现在从这些错误中恢复数据是一个极其耗时的差事并且只有DBA可以实现但自从Oracle i以来用户可以通过SQL命令来修正很多这样的错误其中的机制是引入了新的Oracle i的名为闪回查询(Flashback Query)的特性

这里是一个在SCOTT schema中操作的范例范例中一个职工记录被删除并提交更改结果

DELETE FROM emp WHERE empno = ;

COMMIT;

代码行丢失了SELECT语句而且一个ROLLBACK也不能恢复这一行然而一个闪回查询可以显示分钟之前的表单内容

SELECT * FROM emp

AS OF TIMESTAMP (SYSTIMESTAMP – INTERVAL MINUTE)

WHERE empno = ;

SELECT语句可以使用INSERT语句的子查询来载入被删除的数据然而请注意到这一INSERT操作必须受限于表单中的约束

为了将整个会话返回到特定的时间可以使用DBMS_FLASHBACK包

EXEC DBMS_FLASHBACKENABLE_AT_TIME(TIMESTAMP yyyymmddhh:mi:ss);

在一个闪回查询过程中被访问的数据不能被更改只能被读取这有点象科幻小说中的时间追蹤你可以访问过去但你不改变过去为了获得过去的会话可以键入

EXEC DBMS_FLASHBACKDISABLE;

为了使得闪回查询得以工作数据库必须使用自动删除管理(AUM Automated Undo Management)并建立一个删除表用户可以闪回的时间限度取决于undo_retention参数和删除表大小的初始化

虽然这一特性对于IT咨询者来说是福音但是Oracle的主要目的是使得用户直接键入SQL就可以从他或她的错误中得以恢复闪回查询是一个很好的功能所以它可以通过系统权限来恢复单一表单或者所有表单

FLASHBACK ANY TABLE

但是你还可以等待在Oracle g会做得更好i版本中闪回查询受限于数据操作语言(DMLData Manipulation Language)命令比如SELECT INSERT UPDATE and DELETE但在g中即使一个dropped表也可以通过闪回来恢复

Oracle不能保存小数点的时间

Oracle的DATE数据类型只能以秒来存储时间数据需要更精确时间的开发人员只能使用NUMBER数据类型这一操作使得时间间隔的计算更加困难

自从i版本之后Oracle包含了一个与 SQL相互兼容的时间/日期数据类型为了声明诸如一个时间列可以使用TIMESTAMP数据类型并显示需要的小数点个数(缺省情况下为)

CREATE TABLE event_ts (

event_idNUMBER()

event_name VARCHAR()

start_time TIMESTAMP()

elapsed_time TIMESTAMP()

);

对于一个TIMESTAMP字面意义比如DATE必须被一个单引号包括以下的字面代表着March 在午夜的半秒时刻

TIMESTAMP ::

虽然标准的DATE字面意义没有包含时间而一个TIMESTAMP字面意义的标准格式却需要包含时间NLS_TIMESTAMP_FORMAT参数控制格式同样NLS_DATE_FORMAT设定了标准DATE格式一个新的转换函数即TO_TIMESTAMP可以从其它输入格式建立一个TIMESTAMP并且TO_CHAR函数可用于显示一个TIMESTAMP的组成

为了以TIMESTAMP格式获得当前日期和时间可以使用SYSTIMESTAMP函数而不是使用SYSDATE函数例如

SELECT SYSTIMESTAMP FROM DUAL;

一个损坏的块就需要放弃一个对象

IT资讯人员最害怕这样的Oracle错误信息即ORAOracle data block corrupted(Oracle数据块损坏)其中一个数据库块的内部结构将不能被修正信息可以通过文件数量和块数量来识别块的错误一般而言补救的方法通过运行以下这样的查询

SELECT owner segment_name segment_type

FROM dba_extents

WHERE file_id = <filenumber>

AND <blocknumber> BETWEEN block_id AND block_id + blocks ;

这里<filenumber> 和 <blocknumber>为从错误信息得到的数量这一查询可得到哪些对象包含被损坏的块然后就可以恢复这些损坏的块然而这些恢复要么是直接的(对于索引和临时成分)要么是混乱的(对于表单)要么是十分混乱的(对于动态的roolback部分和部分数据字典)

然而在Oracle i Enterprise Edition中一个名为BLOCKRECOVER的恢复管理器(RMAN)的命令可以正确地修正这些块而不需要放弃和重新建立所涉及的对象当进入RMAN并连接到目标数据库之后键入

BLOCKRECOVER DATAFILE <filenumber> BLOCK <blocknumber>;

一个新的查看名为V$DATABASE_BLOCK_CORRUPTION可以使得在RMAN备份过程中获得更新并且当执行一个BLOCKRECOVER时可以列出块的内容为了恢复所有被损坏的块可以使用以下的RMAN

BACKUP VALIDATE DATABASE;

BLOCKRECOVER CORRUPTION LIST;

如果只需要恢复几个块这一方法非常有用对于大规模的损坏块需要重新存储数据文件的一个先前图像然而恢复整个数据文件这样效率更加高对于任何新的特性在使用到正式的数据库之前请认真地测试这是有必要的

列不能被重命名或者重新组织

重新命名一个表格的列或者改变它的数据类型通常这意味着建立一个新的表格和复制旧的数据到新表格列根本不能重新命名数据类型只有在没有数据(只能为NULL数值)时才能被改变

Oracle i具有两种方法以克服这些限制现在ALTER TABLE命令可以直接地重新命名列

ALTER TABLE books RENAME COLUMN tiitle TO title;

同样一个名为DBMS_REDEFINITION的PL/SQL工具包可以使一个DBA改变表格的列结构这是一个复杂的过程但通常情况下遵循以下的步骤即可实现

使用DBMS_REDEFINITIONCAN_REDEF_TABLE来检查表格满足在线的重新定义并指定重新定义是否遵循主要的键或者遵循行Ids

在相同规划中建立一个空表格但结构是一样的省略你想要放弃的列包含你想要建立的新的列

使用DBMS_REDEFINITIONSTART_REDEF_TABLE来开始重新定义过程这一过程的参数说明了旧的表格新的表格以及如何将现成的列映射到新表格的列

建立任一约束索引

使用DBMS_REDEFINITIONFINISH_REDEF_TABLE来完成这一过程当重新定义在两个表格之间交换时无论原来表格的大小都必须将表格锁定为一小段时间

放弃在重新定义中使用的临时表格而不再使用它

当然重新定义一个表格不会自动地更新任何可以访问表格的程序代码程序必须分开地更新和调试然而DBMS_REDEFINITION does所可以做的就是缩短时间这正是用户的需求

只有表格的主人才能分配使用权限

当我提到Oracle安全特性时客户都无法相信DBA不能将使用权限分配给表格除非表格的主人已经将其分配给DBA然而在以前就是这样的情况这些限制是Oracle设计的一部分但它使管理更加困难在Oracle i一个新的系统权限改变了这一点

现在的DBA具具备一个名为GRANT ANY OBJECT PRIVILEGE的系统权限在过去一个如此的语句

GRANT SELECT ON scottemp TO giselle;

都会无法通过除非SCOTT已经将DBA 的SELECT权限分配给他的表格 WITH GRANT OPTION现在相同的语句却可以正确运行

保持忘却状态

正如Visa的创始人Dee Hock所说的问题不是你如何去获得创新的思想而是如何去忘却旧的东西所以请保持忘却状态

上一篇:详解Oracle数据库中DUAL表的使用

下一篇:oracle11gbug:修改问题