前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Oracle Directory目录的知识

Oracle Directory目录的知识

作者头像
bisal
发布2019-01-29 11:33:47
2.1K0
发布2019-01-29 11:33:47
举报

在上一章介绍expdp/impdp时曾使用过DIRECTORY这个概念,下面再简单说明下DIRECTORY的点点滴滴。

MOS上对DIRECTORY的解释(266875.1):

(1)、基于服务端 vs 基于客户端

DIRECTORY变量指出了expdp导出数据泵或impdp导入数据泵将dump文件、log文件以及SQL文件(仅适用于impdp)写到什么路径。

因为导出数据泵和导入数据泵都是基于服务端的,不是基于客户端的,因此输出文件的路径都是相对于服务端目录的路径。数据泵要求将目录路径作为一个目录对象。一个目录对象将文件系统的一个目录路径映射为一个名称。

(2)、如何创建一个目录对象?

为了创建目录,必须具有DBA角色或者赋予了CREATE ANY DIRECTORY权限。

示例:

Window平台

CONNECT system/manager   CREATE OR REPLACE DIRECTORY my_dir as 'D:\DataPump';   CREATE OR REPLACE DIRECTORY my_logdir as 'E:\logs';   GRANT read, write ON DIRECTORY my_dir TO scott;   GRANT read, write ON DIRECTORY my_logdir TO scott;

Unix平台

CONNECT system/manager   GRANT CREATE ANY DIRECTORY TO scott;   CONNECT scott/tiger   CREATE OR REPLACE DIRECTORY my_dir as '/usr/DataPump';   CREATE OR REPLACE DIRECTORY my_logdir as '/usr/logs'; 

如果普通用户被赋予了CREATE ANY DIRECTORY权限,那么用户就自动具备目录的READ和WRITE权限。

注意:CREATE DIRECTORY语句不会创建磁盘的真实目录,如果目录是无效的,数据泵作业会报错:

ORA-39002: invalid operation  ORA-39070: Unable to open the log file.  ORA-29283: invalid file operation  ORA-06512: at "SYS.UTL_FILE", line 475  ORA-29283: invalid file operation

(3)、如何查询可用的目录?

可以使用如下SQL查询具有READ和WRITE权限的目录:

SET lines 80  COL grantee FORMAT a20  COL privilege FORMAT a10  SELECT directory_name, grantee, privilege    FROM user_tab_privs t, all_directories d     WHERE t.table_name(+)=d.directory_name     ORDER BY 1,2,3; DIRECTORY_NAME                 GRANTEE              PRIVILEGE  ------------------------------ -------------------- ----------  DATA_PUMP_DIR                  EXP_FULL_DATABASE    READ  DATA_PUMP_DIR                  EXP_FULL_DATABASE    WRITE  DATA_PUMP_DIR                  IMP_FULL_DATABASE    READ  DATA_PUMP_DIR                  IMP_FULL_DATABASE    WRITE  MY_DIR                         SCOTT                READ  MY_DIR                         SCOTT                WRITE  MY_DIR                         SYSTEM               READ  MY_DIR                         SYSTEM               WRITE  MY_LOGDIR                      SCOTT                READ   MY_LOGDIR                      SCOTT                WRITE   MY_LOGDIR                      SYSTEM               READ   MY_LOGDIR                      SYSTEM               WRITE   ...

(4)、需要的操作系统权限。

对目录对象的READ或WRITE权限仅仅表示Oracle将会替你读或写这个文件。你并没有访问Oracle以外文件的权限,除非你具备合适的操作系统权限。

(5)、数据泵如何决定文件的路径

5.1 如果目录对象是文件标示符的一部分,那么目录对象指定的路径就需要使用。在目录MY_DIR创建dump文件的示例:

> expdp scott/tiger DUMPFILE=my_dir:expdp_s.dmp NOLOGFILE=Y

5.2 如果目录对象不代表一个文件,那么就需要使用DIRECTORY变量命名的目录对象。目录MY_DIR中创建dump文件,目录MY_DIR_LOG中创建日志文件的示例:

> expdp scott/tiger DIRECTORY=my_dir DUMPFILE=expdp_s.dmp \  LOGFILE=my_logdir:expdp_s.log

5.3 如果没有明确目录对象,也没有以DIRECTORY变量命名的目录对象,那么环境变量DATA_PUMP_DIR将会使用。环境变量是在在运行导出和导入数据泵应用的客户端系统中使用操作系统命令定义的,分配给基于客户端环境变量的取值必须和基于服务端的目录对象一致,且必须首先在服务器端建立。

目录MY_DIR中创建dump文件和MY_DIR_LOG中创建日志文件的示例:

在使用expdp的客户端机器上,设定环境变量:

-- On windows, place all expdp parameters on one single line: C:\> set DATA_PUMP_DIR=MY_DIR   C:\> expdp scott/tiger@my_db_alias DUMPFILE=expdp_s.dmp  LOGFILE=my_logdir:expdp_s.log

注意环境变量DATA_DUMP_DIR对应的目录名称是大小写敏感的。设定错误的DATA_PUMP_DIR环境变量会报错,例如:DATA_PUMP_DIR=My_Dir:

ORA-39002: invalid operation  ORA-39070: Unable to open the log file.  ORA-39087: directory name My_Dir is invalid

5.4 如果之前三种情况都没有创建目录对象,作为一个具有权限的用户(例如具有EXP_FULL_DATABASE或IMP_FULL_DATABASE角色),那么数据泵试图使用默认的基于服务器端的目录对象,DATA_PUMP_DIR。理解数据泵不会创建DATA_PUMP_DIR目录对象是非常重要的。仅当授权用户未使用任何之前提到的机制创建的目录对象时,才会尝试使用DATA_PUMP_DIR。这个默认的目录对象必须首先由DBA创建。不要将这个和同名的基于客户端的环境变量相混淆。

首先,清空DATA_PUMP_DIR环境变量:

C:\> set DATA_PUMP_DIR=

创建DATA_PUMP_DIR的目录:

CONNECT SYSTEM/MANAGER    CREATE OR REPLACE DIRECTORY data_pump_dir AS 'D:\DataPump';    GRANT read, write ON DIRECTORY data_pump_dir TO scott;

-- On windows, place all expdp parameters on one single line:  C:\> expdp system/manager@my_db_alias DUMPFILE=expdp_s.dmp   LOGFILE=expdp_s.log SCHEMAS=scott

如果SCOTT用户不是授权用户,不能使用默认的DATA_PUMP_DIR。

ORA-39002: invalid operation  ORA-39070: Unable to open the log file.  ORA-39145: directory object parameter must be specified and non-null

用户SCOTT的解决方法:如上面5.3,SCOTT可以设置环境变量DATA_PUMP_DIR为MY_DIR:

-- On windows, place all expdp parameters on one single line: C:\> set DATA_PUMP_DIR=MY_DIR C:\> expdp scott/tiger@my_db_alias DUMPFILE=expdp_s.dmp  LOGFILE=expdp_s.log SCHEMAS=scott

或者这种特定场景下,用户SCOTT也可以有目录DATA_PUMP_DIR的读和写权限:

-- On windows, place all expdp parameters on one single line:  C:\> set DATA_PUMP_DIR=DATA_PUMP_DIR C:\> expdp scott/tiger@my_db_alias DUMPFILE=expdp_s.dmp  LOGFILE=expdp_s.log SCHEMAS=scott

实验:

创建目录:CREATE DIRECTORY UTL_FILE_DIR AS '/oracle/backup';

向用目录对象标识的文件写内容:

SQL> declare   2  fhandle utl_file.file_type;   3  begin   4  fhandle := utl_file.fopen('UTL_FILE_DIR', 'example.txt', 'w');   5  utl_file.put_line(fhandle, 'test write one');   6  utl_file.put_line(fhandle, 'test write two');   7  utl_file.fclose(fhandle);   8  end;   9  / PL/SQL procedure successfully completed. SQL> ! ora10g@vm-vmw4131-t$ more /oracle/backup/example.txt test write one test write two

读取使用目录对象DIRECTORY标识的文件内容:

SQL> declare   2  fhandle utl_file.file_type;   3  fp_buffer varchar2(4000);   4  begin   5  fhandle := utl_file.fopen('UTL_FILE_DIR', 'example.txt', 'R');   6  utl_file.get_line(fhandle, fp_buffer);   7  dbms_output.put_line(fp_buffer);   8  utl_file.get_line(fhandle, fp_buffer);   9  dbms_output.put_line(fp_buffer); 10  utl_file.fclose(fhandle); 11  end; 12  / PL/SQL procedure successfully completed. SQL> / PL/SQL procedure successfully completed. 此时没有任何输出,设置serveroutput:

SQL> set serveroutput on SQL> / test write one test write two PL/SQL procedure successfully completed. 打印文件内容。

DIRECTORY的目就在于可以让我们在Oracle中灵活地对文件系统中的文件进行操作。

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2014年04月28日,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档