式:模板驅動和模式驅動。
1 模板驅動
在以模板驅動的映射中,沒有預先定義文檔結構和數據庫結構之間的映射關系,而是使用將命令語句內嵌入模板的方法,讓數據傳輸中間件來處理該模板。例如,下面的模板,在<SelectStmt>元素中內嵌了SELECT語句:
<?XML version="1.0"?>
<FlightInfo>
<Intro>The following flights have available seats:</Intro>
<SelectStmt>SELECT Airline, FltNumber, Depart, Arrive FROM
Flights</SelectStmt>
<Conclude>We hope one of these meets your needs</Conclude>
</FlightInfo>
當數據傳輸中間件處理到該文檔時,每個SELECT語句都將被各自的執行結果所替換,得到下面的XML格式:
<?XML version="1.0"?>
<FlightInfo>
<Intro>The following flights have available seats:</Intro>
<Flights>
<Row>
<Airline>ACME</Airline>
<FltNumber>123</FltNumber>
<Depart>Dec 12, 1998 13:43</Depart>
<Arrive>Dec 13, 1998 01:21</Arrive>
</Row>
...
</Flights>
<Conclude>We hope one of these meets your needs</Conclude>
</FlightInfo>
這種以模板驅動的映射可以相當的靈活。例如,有些產品可以允許你在任何結果集合中替換你想要的內容(包括在SELECT中使用參數),而不是象上面的例子中簡單地格式化結果。另外它還支持使用編程來進行構造,例如循環和條件判斷結構。還有一些還支持SELECT語句的參數化,例如通過HTTP來傳遞參數。
目前,以模板驅動的映射只支持從一個關系型數據庫轉換成XML文檔的情況。
2 模型驅動
在以模型驅動的映射中,利用XML文檔結構對應的數據模型顯式或隱式地將映射成數據庫的結構,而且反之亦然。它的缺點是靈活性不夠,但是卻簡單易用,這是因為它是基於具體的數據模型來進行映射的,通常能夠為用戶實現很多地轉換工作。由於將數據從數據庫轉換成XML的結果依照了單個模型,
因此通常在這種方式下通常結合XSL來提供模板驅動的系統中所具有的靈活性。
在XML文檔中的數據視圖通常有兩種模型:表格模型和特定數據對象模型。有時候也可能會出現其他的模型。例如,通過采用ID和IDREF屬性,一個XML文檔可以用來一個指定的圖形。不過,很多現有的中間件並不支持這些模型。
2.1 表格模型
許多中間件軟件包都采用表格模型在XML和關系型數據庫之間進行轉換。它把XML的模型看成是一個單獨的表格或者是一系列的表格。也就是說,XML的文檔的結構和下面的例子相類似,其中在單個表格的情況下,<database>並不出現:
<database>
<table>
<row>
<column1>...</column1>
<column2>...</column2>
...
</row>
...
</table>
...
</database>
其中的術語"table"可理解為單個的結果集(當從數據庫向XML中轉換數據時),或者是一個單獨的表格或可更新的視圖(當從XML向數據庫轉換數據時)。如果數據需要來自多個結果集(當數據來自數據庫中時)或者與僅僅表達成一系列表格的集合(當轉換數據到數據庫時)相比,XML的文檔包含有更深層次的嵌套元素,那麼類似的轉換幾乎是不可能的。
2.2 特定數據對象模型
XML文檔中第二種普遍的數據模型是特定數據對象的樹型結構。在該模型中,元素類型通常對應對象,而XML中的內容模型、屬性和PCDATA則對應對象的屬性。這種模型直接映射成面向對象的數據庫和層次型數據庫,當然借助於傳統的對象-關系映射技術和SQL
3 從數據庫的結構生成DTD及其互逆過程
在XML文檔和數據庫之間轉換數據時,一個普遍問題是:如何從數據庫的結構(Schema)生成XML的DTD,如果從XML的DTD產生數據庫的結構。簡而言之,這是非常直接的操作,但是產生的結果通常離許多用戶的期望值還有一些距離。
(還要注意這通常是一次性操作,而大多數應用,尤其是所有的垂直性應用都結合了已知的DTD和關系型Schema的集合。顯而易見的特例是在關系數據庫中存儲隨機XML文檔或者將關系型數據發布為XML文檔的工具;而在後面的情況中,DTD的作用並不明顯。)
對於元素類型中每個有單一數值的屬性和只包含有PCDATA內容的子元素類型在該table中新建立一列(字段)。如果子元素類型或則屬性是可選的,讓該字段允許為空。
對於每個有多值的屬性或則多僅含有PCDATA內容的子元素類型,再建立一個分開的table來保存他們的值,通過它們的父表的主關鍵字連接到父表。
對於每個子元素,這些子元素本身還有元素或則混合內容,使用父表中的關鍵字將父元素表連接到子元素表中。
而下面則是一個從關系數據庫的結構生成XML文檔的過程(簡化過的):
對每個table,新建一個元素。
對表中的每列,建立一個屬性或則只含PCDATA的子元素
對每個包含有在主鍵/外鍵關鍵字關系中主鍵值的列,新建一個子元素。
例如,下面的過程(經簡化)說明了如何從一個DTD生成一個關系型結構:
對於每種包含元素或者混合內容的元素類型,新建一個表格和一個主鍵字段。
對於每個包含混合內容的元素類型,創建一個單獨的表格,其中存放未析數據,通過父元素主鍵鏈接到父表格。
對於此元素類型的每個單值屬性和只包含未析數據內容、只出現一次的子元素,在該表格中創建一個字段。如果元素類型或者屬性是可選的,可以讓設置該字段為空值。
對於每個多值屬性和多次出現的子元素,創建一個單獨的表格來存儲數值,並且通過父元素主鍵鏈接到父表格。
對每個有元素或者混合內容的子元素,通過父元素主鍵將父元素表格和子元素表格相連接。
下面的過程(經簡化)說明了如何從一個關系型的結構生成一個DTD:
對於每個表格,新建一個元素;
對於表格中的每個字段,新建一個屬性或者是只包含未析數據的子元素;
對於每個表格字段中提供主鍵的主鍵/外鍵的關系都新建一個子元素。
不幸的是,這些過程還存在著一些缺陷。例如,DTD中沒有方法預先准確地規定數據類型或者字段長度。
因為任何的預先定義(例如通過讀取一個示例文檔)在讀取其它“類型”的文檔或者其他文檔中包含有超過字長內容的文檔時就會產生錯誤。(長久之策是使用XML schema文檔的數據類型。)簡單來說,當從一關系型結構生成DTD時,是沒有辦法預先判斷子元素“應該”出現的順序或者字段(如數據庫內部的行標識)是否該進行完全轉換。
在以上兩種情況中都可能產生命名的沖突。
盡管有這樣那樣的缺陷,但是這些方法仍然能夠很好地奠定在關系型結構和DTD之間互相轉換的起點。