可传输表空间 -电脑资料

电脑资料 时间:2019-01-01 我要投稿
【www.unjs.com - 电脑资料】

    oracle2271


    对于可传输表空间有一个重要概念:自包含(Self-Contained),

可传输表空间

    在表空间传输的中,要求表空间集为自包含的,自包含表示用于传输的内部表空间集没有引用指向外部表空间集。自包含分为两种:一般自包含表空间集和完全(严格)自包含表空间集。

    常见的以下情况是违反自包含原则的:

     索引在内部表空间集,而表在外部表空间集(相反地,如果表在内部表空间集,而索引在外部表空间集,则不违反自包含原则)。

     分区表一部分区在内部表空间集,一部分在外部表空间集(对于分区表,要么全部包含在内部表空间集中,要么全不包含)。

     如果在传输表空间时同时传输约束,则对于引用完整性约束,约束指向的表在外部表空间集,则违反自包含约束;如果不传输约束,则与约束指向无关。

     表在内部表空间集,而lob列在外部表空间集,则违反自包含约束。

    通常可以通过系统包DBMS_TTS来检查表空间是否自包含,验证可以以两种方式执行:非严格方式和严格方式。

    以下是一个简单的验证过程,假定在eygle表空间存在一个表eygle,其上存在索引存储在USERS表空间:

SQL> create table eygle as select rownum id ,username from dba_users;

    Table created.

    SQL> create index ind_id on eygle(id) tablespace users;

    Index created.

    以SYS用户执行非严格自包含检查(full_check=false):

SQL> connect / as sysdba

    Connected.

    SQL> exec dbms_tts.transport_set_check(‘EYGLE‘, TRUE);

    PL/SQL procedure successfully completed.

    SQL> SELECT * FROM TRANSPORT_SET_VIOLATIONS;

    no rows selected

    执行严格自包含检查(full_check=true):

SQL> exec dbms_tts.transport_set_check(‘EYGLE‘, TRUE, True);

    PL/SQL procedure successfully completed.

    SQL> SELECT * FROM TRANSPORT_SET_VIOLATIONS;

    VIOLATIONS

    --------------------------------------------------------------------------------------

    Index EYGLE.IND_ID in tablespace USERS points to table EYGLE.EYGLE in tablespace EYGLE

    反过来对于USERS表空间来说,非严格检查也是无法通过的:

SQL> exec dbms_tts.transport_set_check(‘USERS‘, TRUE);

    PL/SQL procedure successfully completed.

    SQL> SELECT * FROM TRANSPORT_SET_VIOLATIONS;

    VIOLATIONS

    ----------------------------------------------------------------------------------------

    Index EYGLE.IND_ID in tablespace USERS points to table EYGLE.EYGLE in tablespace EYGLE

    但是可以对多个表空间同时传输,则一些自包含问题就可以得到解决:

SQL> exec dbms_tts.transport_set_check(‘USERS,EYGLE‘, TRUE, True);

    PL/SQL procedure successfully completed.

    SQL> SELECT * FROM TRANSPORT_SET_VIOLATIONS;

    no rows selected

    官方解释如下:

    There may be logical or physical dependencies between objects in the transportable set and those outside of the set. You can only transport a set of tablespaces that is self-contained. In this context "self-contained" means that there are no references from inside the set of tablespaces pointing outside of the tablespaces. Some examples of self contained tablespace violations are:

An index inside the set of tablespaces is for a table outside of the set of tablespaces.

    Note:

It is not a violation if a corresponding index for a table is outside of the set of tablespaces.

A partitioned table is partially contained in the set of tablespaces.

    The tablespace set you want to copy must contain either all partitions of a partitioned table, or none of the partitions of a partitioned table. If you want to transport a subset of a partition table, you must exchange the partitions into tables.

A referential integrity constraint points to a table across a set boundary.

    When transporting a set of tablespaces, you can choose to include referential integrity constraints. However, doing so can affect whether or not a set of tablespaces is self-contained. If you decide not to transport constraints, then the constraints are not considered as pointers.

A table inside the set of tablespaces contains a LOB column that points to LOBs outside the set of tablespaces.

An XML DB schema (*.xsd) that was registered by user A imports a global schema that was registered by user B, and the following is true: the default tablespace for user A is tablespace A, the default tablespace for user B is tablespace B, and only tablespace A is included in the set of tablespaces.

    To determine whether a set of tablespaces is self-contained, you can invoke the TRANSPORT_SET_CHECK procedure in the Oracle supplied package DBMS_TTS. You must have been granted the EXECUTE_CATALOG_ROLE role (initially signed to SYS) to execute this procedure.

    When you invoke the DBMS_TTS package, you specify the list of tablespaces in the transportable set to be checked for self containment. You can optionally specify if constraints must be included. For strict or full containment, you must additionally set the TTS_FULL_CHECK parameter to TRUE.

    The strict or full containment check is for cases that require capturing not only references going outside the transportable set, but also those coming into the set. Tablespace Point-in-Time Recovery (TSPITR) is one such case where dependent objects must be fully contained or fully outside the transportable set.

    For example, it is a violation to perform. TSPITR on a tablespace containing a table t but not its index i because the index and data will be inconsistent after the transport. A full containment check ensures that there are no dependencies going outside or coming into the transportable set. See the example for TSPITR in the Oracle Database Backup and Recovery User‘s Guide.

    incl_constraints

    TRUE if you want to count in referential integrity constraints when examining if the set of tablespaces is self-contained. (Theincl_constraints parameter is a default so that TRANSPORT_SET_CHECK will work if it is called with only the ts_list argument.)

    full_check

    Indicates whether a full or partial dependency check is required. If TRUE, treats all IN and OUT pointers (dependencies) and captures them as violations if they are not self-contained in the transportable set. The parameter should be set to TRUE for TSPITR or if a strict version of transportable is desired. By default the parameter is set to false. It will only consider OUT pointers as violations.

   


    1.3.5可传输表空间

    在很多Oracle文档中,可能大家都注意过Oracle用来进行测试的一个表空间,这个表空间中有一系列预置的用户和数据,可以用于数据库或BI的很多测试实验。

    这个表空间在使用模板建库时是可以选择的,在如图1-22所示的这个界面中,可以选择建库时包含这个范例表空间(缺省是未选择的)。

    vcWxvr2ru+HT0Mv5uMSx5KOs1vfSqtT2vNPBy8jnz8LT777ko7o8L3A+CjwvYmxvY2txdW90ZT4KPGJsb2NrcXVvdGU+CmNvbm5lY3QgJnF1b3Q7U1lTJnF1b3Q7LyZxdW90OyZhbXA7JmFtcDtzeXNQYXNzd29yZCZxdW90OyBhcyBTWVNEQkE8YnI+CkBDOlxvcmFjbGVcMTAuMi4wXGRlbW9cc2NoZW1hXG1rcGx1Zy5zcWwgJmFtcDsmYW1wO3N5c1Bhc3N3b3JkIGNoYW5nZV9vbl9pbnN0YWxsIGNoYW5nZV9vbl9pbnN0YWxsIDxicj4KY2hhbmdlX29uX2luc3RhbGwgY2hhbmdlX29uX2luc3RhbGwgY2hhbmdlX29uX2luc3RhbGwgY2hhbmdlX29uX2luc3RhbGwgQzpcb3JhY2xlXDEwLjIuMFxhc3Npc3RhbnRzXGRiY2FcdGVtcGxhdGVzXGV4YW1wbGUuZG1wIEM6XG9yYWNsZVwxMC4yLjBcYXNzaXN0YW50c1xkYmNhXHRlbXBsYXRlc1xleGFtcGxlMDEuZGZiIEM6XG9yYWNsZVxvcmFkYXRhXGV5Z2xlXGV4YW1wbGUwMS5kYmYgQzpcb3JhY2xlXGFkbWluXGV5Z2xlXHNjcmlwdHNcICZxdW90Ow=="SYS/&&sysPassword as SYSDBA‘";

    看到这里,再次引用了模板目录中的文件:

C:\>dir C:\oracle\10.2.0\assistants\dbca\templates\ex*

    驱动器 C 中的卷是 SYSTEM

    卷的序列号是 8C88-D1B4

    C:\oracle\10.2.0\assistants\dbca\templates 的目录

    2005-09-07 13:02 983,040 example.dmp

    2005-09-07 13:02 20,897,792 example01.dfb

    2 个文件 21,880,832 字节

    0 个目录 915,578,880 可用字节

    通过mkplug.sql脚本来加载这个范例表空间,来看一下这个脚本的主要内容,

电脑资料

可传输表空间》(https://www.unjs.com)。

    同样,最重要的是通过dbms_backup_restore包从example01.dfb文件中恢复数据文件:

    SELECT TO_CHAR(systimestamp, ‘YYYYMMDD HH:MI:SS‘) FROM dual;

    variable new_datafile varchar2(512)

    declare

    done boolean;

    v_db_create_file_dest VARCHAR2(512);

    devicename varchar2(255);

    data_file_id number;

    rec_id number;

    stamp number;

    resetlogs_change number;

    creation_change number;

    checkpoint_change number;

    blksize number;

    omfname varchar2(512);

    real_file_name varchar2(512);

    begin

    dbms_output.put_line(‘ ‘);

    dbms_output.put_line(‘ Allocating device.... ‘);

    dbms_output.put_line(‘ Specifying datafiles... ‘);

    devicename := dbms_backup_restore.deviceAllocate;

    dbms_output.put_line(‘ Specifing datafiles... ‘);

    SELECT MAX(file_id)+1 INTO data_file_id FROM dba_data_files;

    SELECT value INTO v_db_create_file_dest FROM v$parameter WHERE name =‘db_create_file_dest‘;

    IF v_db_create_file_dest IS NOT NULL

    THEN

    dbms_backup_restore.restoreSetDataFile;

    dbms_backup_restore.getOMFFileName(‘EXAMPLE‘,omfname);

    dbms_backup_restore.restoreDataFileTo(data_file_id, omfname, 0,‘EXAMPLE‘);

    ELSE

    dbms_backup_restore.restoreSetDataFile;

    dbms_backup_restore.restoreDataFileTo(data_file_id,‘&data_file_name‘);

    END IF;

    dbms_output.put_line(‘ Restoring ... ‘);

    dbms_backup_restore.restoreBackupPiece(‘&data_file_backup‘, done);

    SELECT max(recid) INTO rec_id FROM v$datafile_copy;

    -- Now get the real file name. It could be also OMF filename

    SELECT name, stamp, resetlogs_change#, creation_change#, checkpoint_change#,block_size

    INTO real_file_name, stamp,resetlogs_change, creation_change, checkpoint_change, blksize

    FROM V$DATAFILE_COPY

    WHERE recid = rec_id and file# = data_file_id;

    -- Uncatalog the file from V$DATAFILE_COPY. This important.

    dbms_backup_restore.deleteDataFileCopy(recid => rec_id,

    stamp => stamp,

    fname => real_file_name,

    dfnumber => data_file_id,

    resetlogs_change => resetlogs_change,

    creation_change => creation_change,

    checkpoint_change => checkpoint_change,

    blksize => blksize,

    no_delete => 1,

    force => 1);

    -- Set the bindvariable to the real filename

    :new_datafile := real_file_name;

    if done then

    dbms_output.put_line(‘ Restore done.‘);

    else

    dbms_output.put_line(‘ ORA-XXXX: Restore failed ‘);

    end if;

    end;

    /

    这个恢复完成之后,接下来最重要的部分就是通过传输表空间技术将example表空间导入到当前的数据库。

    考虑一下这种情况,当进行跨数据库迁移时,需要将一个用户表空间中的数据迁移到另外一个数据库,应该使用什么样的方法呢?最常规的做法可能是通过EXP工具将数据全部导出,然后在目标数据库上IMP导入,可是这种方法可能会比较缓慢。EXP工具同时还提供另外一种技术-可传输表空间技术,可以用于加快这个过程。

    在exp -help的帮助中,可以看到这样一个参数:

    TRANSPORT_TABLESPACE 导出可传输的表空间元数据 (N)

    通过这个选项,我们可以对一组自包含、只读的表空间只导出元数据,然后在操作系统层将这些表空间的数据文件拷贝至目标平台,并将元数据导入数据字典(这个过程称为插入,plugging),即完成迁移。

    对于可传输表空间有一个重要概念:自包含(Self-Contained)。

    在表空间传输的中,要求表空间集为自包含的,自包含表示用于传输的内部表空间集没有引用指向外部表空间集。自包含分为两种:一般自包含表空间集和完全(严格)自包含表空间集。

    常见的以下情况是违反自包含原则的:

     索引在内部表空间集,而表在外部表空间集(相反地,如果表在内部表空间集,而索引在外部表空间集,则不违反自包含原则)。

     分区表一部分区在内部表空间集,一部分在外部表空间集(对于分区表,要么全部包含在内部表空间集中,要么全不包含)。

     如果在传输表空间时同时传输约束,则对于引用完整性约束,约束指向的表在外部表空间集,则违反自包含约束;如果不传输约束,则与约束指向无关。

     表在内部表空间集,而lob列在外部表空间集,则违反自包含约束。

    通常可以通过系统包DBMS_TTS来检查表空间是否自包含,验证可以以两种方式执行:非严格方式和严格方式。

    以下是一个简单的验证过程,假定在eygle表空间存在一个表eygle,其上存在索引存储在USERS表空间:

SQL> create table eygle as select rownum id ,username from dba_users;

    Table created.

    SQL> create index ind_id on eygle(id) tablespace users;

    Index created.

    以SYS用户执行非严格自包含检查(full_check=false):

SQL> connect / as sysdba

    Connected.

    SQL> exec dbms_tts.transport_set_check(‘EYGLE‘, TRUE);

    PL/SQL procedure successfully completed.

    SQL> SELECT * FROM TRANSPORT_SET_VIOLATIONS;

    no rows selected

    执行严格自包含检查(full_check=true):

SQL> exec dbms_tts.transport_set_check(‘EYGLE‘, TRUE, True);

    PL/SQL procedure successfully completed.

    SQL> SELECT * FROM TRANSPORT_SET_VIOLATIONS;

    VIOLATIONS

    --------------------------------------------------------------------------------------

    Index EYGLE.IND_ID in tablespace USERS points to table EYGLE.EYGLE in tablespace EYGLE

    反过来对于USERS表空间来说,非严格检查也是无法通过的:

SQL> exec dbms_tts.transport_set_check(‘USERS‘, TRUE);

    PL/SQL procedure successfully completed.

    SQL> SELECT * FROM TRANSPORT_SET_VIOLATIONS;

    VIOLATIONS

    ----------------------------------------------------------------------------------------

    Index EYGLE.IND_ID in tablespace USERS points to table EYGLE.EYGLE in tablespace EYGLE

    但是可以对多个表空间同时传输,则一些自包含问题就可以得到解决:

SQL> exec dbms_tts.transport_set_check(‘USERS,EYGLE‘, TRUE, True);

    PL/SQL procedure successfully completed.

    SQL> SELECT * FROM TRANSPORT_SET_VIOLATIONS;

    no rows selected

    表空间自包含确认之后,进行表空间传输就很方便了,一般包含如下几个步骤。

    (1) 将表空间设置为只读:

    alter tablespace users read only;

    (2) 导出表空间。在操作系统提示符下执行:

    exp username/passwd tablespaces=users transport_tablespace=y file=exp_users.dmp

    此处的导出文件只包含元数据,所以导出文件很小,导出速度也会很快。

    (3) 转移。将导出的元数据文件(此处是exp_users.dmp)和传输表空间的数据文件(此处是users表空间的数据文件user01.dbf)转移至目标主机(转移过程如果使用FTP方式,应该注意使用二进制方式)。

    (4) 传输。在目标数据库将表空间插入到数据库中,完成表空间传输。在操作系统命令提示符下执行下面的语句:

    imp username/passwd tablespaces=users transport_tablespace=y file=exp_users.dmp datafiles=‘users01.dbf‘

    了解了Oracle的可传输表空间技术后,来看一下example表空间的插入,以下脚本仍然来自mkplug.sql脚本:

--

    -- Importing the metadata and plugging in the tablespace at the same

    -- time, using the restored database file

    --

    DEFINE imp_logfile = &log_path.tts_example_imp.log

    -- When importing use filename got after restore is finished

    host imp "‘sys/&&password_sys AS SYSDBA‘" transport_tablespace=y file=&imp_file log=&imp_logfile datafiles=‘&datafile‘ tablespaces=EXAMPLE tts_owners=hr,oe,pm,ix,sh

    完成plugging之后,这个表空间就被包含在了新建的数据库之中。

最新文章