2025年9月25日: PostgreSQL 18 釋出!
支援的版本: 當前 (18) / 17 / 16 / 15 / 14 / 13
開發版本: devel
不支援的版本: 12 / 11 / 10 / 9.6 / 9.5 / 9.4 / 9.3 / 9.2 / 9.1 / 9.0 / 8.4 / 8.3 / 8.2 / 8.1 / 8.0 / 7.4 / 7.3 / 7.2 / 7.1

34.17. 內部結構 #

本節介紹 ECPG 如何在內部工作。這些資訊有時有助於使用者理解如何使用 ECPG

ecpg 寫入輸出的前四行是固定行。其中兩行是註釋,兩行是與庫介面所需的 include 行。然後預處理器逐行讀取檔案並寫入輸出。通常它只是將所有內容回顯到輸出。

當它看到 EXEC SQL 語句時,它會介入並進行更改。命令以 EXEC SQL 開頭,以 ; 結尾。其間的所有內容都被視為一個SQL語句,並被解析用於變數替換。

變數替換髮生在符號以冒號 (:) 開頭時。該名稱的變數會在 EXEC SQL DECLARE 部分中先前宣告的變數中查詢。

庫中最重要函式是 ECPGdo,它負責執行大多數命令。它接受可變數量的引數。這很容易加到 50 個左右的引數,我們希望這在任何平臺上都不會有問題。

引數是

行號 #

這是原始行的行號;僅用於錯誤訊息。

字串 #

這是要發出的SQL命令。它會被輸入變數修改,即在編譯時未知但要輸入到命令中的變數。變數應該去的位置,字串包含 ?

輸入變數 #

每個輸入變數都會建立十個引數。(見下文。)

ECPGt_EOIT #

一個 enum,表示沒有更多的輸入變數。

輸出變數 #

每個輸出變數都會建立十個引數。(見下文。)這些變數由函式填充。

ECPGt_EORT #

一個 enum,表示沒有更多的變量了。

對於作為命令一部分的每個變數,SQL函式會獲得十個引數

  1. 作為特殊符號的型別。

  2. 指向值或指向指標的指標。

  3. 如果變數是 charvarchar,則為變數的大小。

  4. 陣列中的元素數量(用於陣列提取)。

  5. 陣列中下一個元素的偏移量(用於陣列提取)。

  6. 指示變數的型別作為特殊符號。

  7. 指向指示變數的指標。

  8. 0

  9. 指示陣列中的元素數量(用於陣列提取)。

  10. 指示陣列中下一個元素的偏移量(用於陣列提取)。

請注意,並非所有 SQL 命令都以這種方式處理。例如,開啟遊標語句如

EXEC SQL OPEN cursor;

不會被複制到輸出。相反,遊標的 DECLARE 命令會在 OPEN 命令的位置使用,因為它確實打開了遊標。

這是一個完整的示例,描述了檔案 foo.pgc 的預處理器輸出(具體細節可能因預處理器版本而異)

EXEC SQL BEGIN DECLARE SECTION;
int index;
int result;
EXEC SQL END DECLARE SECTION;
...
EXEC SQL SELECT res INTO :result FROM mytable WHERE index = :index;

被翻譯為

/* Processed by ecpg (2.6.0) */
/* These two include files are added by the preprocessor */
#include <ecpgtype.h>;
#include <ecpglib.h>;

/* exec sql begin declare section */

#line 1 "foo.pgc"

 int index;
 int result;
/* exec sql end declare section */
...
ECPGdo(__LINE__, NULL, "SELECT res FROM mytable WHERE index = ?     ",
        ECPGt_int,&(index),1L,1L,sizeof(int),
        ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, ECPGt_EOIT,
        ECPGt_int,&(result),1L,1L,sizeof(int),
        ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, ECPGt_EORT);
#line 147 "foo.pgc"

(這裡的縮排是為了提高可讀性,並不是預處理器所做的。)

提交更正

如果您在文件中看到任何不正確、與您對特定功能的體驗不符或需要進一步澄清的內容,請使用 此表單 報告文件問題。