簡體   English   中英

Oracle 12c以一種奇怪的方式解釋SQL(內部查詢)

[英]Oracle 12c interprets SQL in a strange way (Inner Query)

我們最近將Oracle數據庫從10g遷移到12c(12.1.0.1.0)。 在考慮了某些查詢的問題后,我們決定進一步清理數據庫並刪除所有不需要的對象。
因此,我編寫了一個查詢,在數據庫DDL中搜索要顯示的特定文本,其中使用了特定的視圖或函數。

SELECT 
  object_name, object_type, DBMS_METADATA.GET_DDL(object_type, object_name) as ddl_txt 
FROM user_objects 
WHERE object_type IN ( 'FUNCTION', 'VIEW', 'PROCEDURE', 'TRIGGER') 
  AND UPPER( DBMS_METADATA.GET_DDL(object_type, object_name) ) LIKE upper('%myFunction%')

這導致以下異常:

ORA-31600: invalid input value TYPE BODY for parameter OBJECT_TYPE in function GET_DDL
ORA-06512: at "SYS.DBMS_METADATA", line 5746
ORA-06512: at "SYS.DBMS_METADATA", line 8333
ORA-06512: at line 1
31600. 00000 -  "invalid input value %s for parameter %s in function %s"
*Cause:    A NULL or invalid value was supplied for the parameter.
*Action:   Correct the input value and try the call again.

因為我們的數據庫中有'Body Type'對象,並且它們沒有提供帶有DBMS_METADATA.GET_DDL()的ddl,所以會發生這種情況。 運行下面的查詢會顯示與初始查詢完全相同的異常。

select dbms_metadata.get_ddl('TYPE BODY', 'myBodyStringType') from dual

所以,我嘗試創建一個內部列表,首先將所有用戶對象的列表減少到我真正關心的一次,重寫我的查詢如下:

select
  lst.*,
  DBMS_METADATA.GET_DDL(lst.object_type, lst.object_name) as ddl_txt 
from (
      SELECT 
        object_name, object_type
      FROM user_objects 
      WHERE object_type IN ( 'FUNCTION', 'VIEW', 'PROCEDURE', 'TRIGGER') 
) lst
where upper(DBMS_METADATA.GET_DDL(lst.object_type, lst.object_name)) like upper('%myFunction%')

有趣的是,它帶來了如上所示的相同異常。 我不明白為什么會這樣。

我希望Oracle首先創建內部列表並僅使用剩余值來使用DBMS_METADATA.GET_DLL()函數,因為相同的值將導致異常。 為什么Oracle在這里做其他事情?

要解決這個特定的問題,我必須在內部查詢中添加一個看起來很愚蠢的ORDER BY 為什么我必須首先使用ORDER BY強制Oracle創建內部查詢?

select
  lst.*,
  DBMS_METADATA.GET_DDL(lst.object_type, lst.object_name) as ddl_txt 
from (
      SELECT 
        object_name, object_type
      FROM user_objects 
      WHERE object_type IN ( 'FUNCTION', 'VIEW', 'PROCEDURE', 'TRIGGER')
      ORDER BY ROWNUM ASC
) lst
where upper(DBMS_METADATA.GET_DDL(lst.object_type, lst.object_name)) like upper('%myFunction%')

在此先感謝有關為何會發生這種情況的任何解釋? - 我記得,后來的查詢在Oracle 10g上運行沒有任何問題。
(我擔心在其他報告中會有相同的行為,因為這種行為可能會導致計算錯誤!)。

這是一個錯誤。 Oracle Support剛剛向我確認由於Oracle Version 12.1.0中的錯誤而發生異常。 僅限1

有兩種選擇可供選擇:
1)更新到Oracle Version 12.1.0。 2 ,錯誤是固定的。
2)等待幾周的Oracle即將開始工作的補丁。 該補丁將在Oracle Version 12.1.0中解決此問題。 1

我們沒有決定采用哪種方案,但我非常有信心,因為Oracle支持確實重現了我的問題,所以其中一種方法可行。

最有可能是謂詞推(我找不到一個簡單的解釋抱歉)

它首先沒有運行內部記錄集然后評估剩余部分。 它正在推動外部進入內部派生表。 查詢計划將確保告訴您。

通過使用ROWNUM您將強制它首先評估內部記錄集。 這不是ROWNUMORDER BY 除了ORDER BY您還可以執行AND ROWNUM > 0並且它將執行相同的操作,因為它必須在評估ROWNUM表達式之前評估每一行。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM