【问题标题】:DBMS_METADATA.GET_DDL don't work inside a PROCEDUREDBMS_METADATA.GET_DDL 在 PROCEDURE 中不起作用
【发布时间】:2019-10-10 21:27:06
【问题描述】:

我创建了一个脚本来从 DEVBASE 用户复制一个表:

DECLARE
  YTABLE_NAME   CONSTANT VARCHAR2 (50) := 'TABLE_NAME';
  YRECREATE     CONSTANT BOOLEAN       := FALSE;
--
  XCOMMAND               CLOB;

  FUNCTION TABLE_EXISTS (ZTABLE_NAME IN VARCHAR2)
    RETURN BOOLEAN IS
    XCOUNT   NUMBER;
  BEGIN
    SELECT COUNT (*)
      INTO XCOUNT
      FROM USER_TABLES A
     WHERE A.TABLE_NAME = ZTABLE_NAME;

    RETURN XCOUNT > 0;
  END;
BEGIN
  IF TABLE_EXISTS (YTABLE_NAME) THEN
    IF YRECREATE THEN
      EXECUTE IMMEDIATE 'DROP TABLE ' || YTABLE_NAME || ' CASCADE CONSTRAINTS';
    ELSE
      RAISE_APPLICATION_ERROR (-20000, 'TABLE ' || YTABLE_NAME || ' ALREADY EXISTS');
    END IF;
  END IF;

  DBMS_METADATA.SET_TRANSFORM_PARAM (DBMS_METADATA.SESSION_TRANSFORM, 'SQLTERMINATOR', FALSE);
  DBMS_METADATA.SET_TRANSFORM_PARAM (DBMS_METADATA.SESSION_TRANSFORM, 'PRETTY', FALSE);
  DBMS_METADATA.SET_TRANSFORM_PARAM (DBMS_METADATA.SESSION_TRANSFORM, 'SEGMENT_ATTRIBUTES', FALSE);
  DBMS_METADATA.SET_TRANSFORM_PARAM (DBMS_METADATA.SESSION_TRANSFORM, 'STORAGE', FALSE);
  DBMS_METADATA.SET_TRANSFORM_PARAM (DBMS_METADATA.SESSION_TRANSFORM, 'EMIT_SCHEMA', FALSE);
  DBMS_METADATA.SET_TRANSFORM_PARAM (DBMS_METADATA.SESSION_TRANSFORM, 'SEGMENT_CREATION', FALSE);
  DBMS_METADATA.SET_TRANSFORM_PARAM (DBMS_METADATA.SESSION_TRANSFORM, 'CONSTRAINTS_AS_ALTER', FALSE);
  XCOMMAND := DBMS_METADATA.GET_DDL ('TABLE', YTABLE_NAME, 'DEVUSER');

  EXECUTE IMMEDIATE XCOMMAND;
END;

它可以工作,但是如果我使用此代码创建一个过程,我会收到错误“ORA-31603:在模式 DEVUSER 中找不到 TABLE 类型的对象 {table name}”。

CREATE OR REPLACE PROCEDURE COPY_TABLE (YTABLE_NAME IN VARCHAR2, YRECREATE IN BOOLEAN) IS
BEGIN
  -- exact same code
END;

为什么会这样?

【问题讨论】:

  • 这是因为程序不使用通过角色授予的用户权限。我认为 dev_user 可以获得代码,因为 SELECT_CATALOG_ROLE 被授予,但这对程序没有帮助。

标签: oracle plsql


【解决方案1】:

Oracle Documentation 声明:

在存储过程、函数和 定义者权限包,角色被禁用。 因此,这样的 PL/SQL 程序可以 仅获取其对象的元数据 自己的架构。如果你想写一个 获取元数据的 PL/SQL 程序 对于不同模式中的对象 ,你必须使 程序调用者权限。

为此,您必须将authid 添加到您的过程中。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-03-30
    • 2014-02-18
    • 1970-01-01
    • 2016-05-29
    • 2013-01-16
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多