文章詳情頁
將XML應(yīng)用程序從DB2 8.x遷移到Viper(1)
瀏覽:5日期:2023-11-10 18:43:53
簡介DB2 Universal Database (UDB) Version 8.x 中的 XML 支持基于 DB2 的關(guān)系基礎(chǔ)設(shè)施。在 DB2 Viper 版本之前,XML 數(shù)據(jù)要么原樣存儲(chǔ)為字符大對(duì)象 (CLOB),要么被分解到關(guān)系表中。相反,DB2 UDB Version 9.1 具有對(duì) XML 數(shù)據(jù)的真正本機(jī)支持。XML 現(xiàn)在被當(dāng)作新的數(shù)據(jù)類型,XML 數(shù)據(jù)存儲(chǔ)在經(jīng)過解析的帶注釋的樹中,獨(dú)立于關(guān)系數(shù)據(jù)存儲(chǔ)。基于 XML 模式的 XML 索引已經(jīng)引入,同時(shí)還引入了對(duì)用于查詢和發(fā)布 XML 數(shù)據(jù)的語言 XQuery 和 SQL/XML 的支持。為了理解這些新的 XML 特性對(duì)遷移的重大意義,需要將 DB2 8.x 中用于存儲(chǔ)和查詢 XML 數(shù)據(jù)的不同技術(shù)與 DB2 UDB Version 9 中可用的類似的或新的 XML 功能相比較。本文是關(guān)于將 XML 應(yīng)用程序從 DB2 8.x 遷移到 DB2 Viper 的三篇系列文章中的第一篇。該系列從描述一個(gè)基于 Java 的存儲(chǔ)過程開始,您可以使用該存儲(chǔ)過程來對(duì) XML 數(shù)據(jù)執(zhí)行子文檔更新。您可以下載更新后的存儲(chǔ)過程的源代碼和 jar 文件,并根據(jù)說明安裝它。第二篇文章比較 DB2 Version 8.x 中和 DB2 Viper 中的 XML 特性。然后簡要討論 DB2 Viper 中引入的新 XML 特性,并具體介紹新 XML 支持對(duì)于遷移現(xiàn)有基于 XML 的應(yīng)用程序的重大意義。這篇文章還包括基于 Java 的實(shí)用工具的源代碼,該工具用于幫助生成遷移數(shù)據(jù)庫對(duì)象時(shí)所需的腳本。本系列的最后一篇文章介紹分步示例遷移場(chǎng)景。它包括示例場(chǎng)景的源代碼。更新存儲(chǔ)過程對(duì)于本機(jī)存儲(chǔ)在 DB2 中的 XML 文檔,不存在用于執(zhí)行子文檔更新的開箱即用的功能。缺少該功能的原因是,目前還沒有定義 Xquery 中更新的標(biāo)準(zhǔn)。該問題的一種解決方案是,將文檔交給客戶機(jī),修改它,然后再將其保存到數(shù)據(jù)庫中。該方法受到客戶機(jī)環(huán)境的 XML 功能的限制,并且還要求專家級(jí)的人員編寫基于文檔對(duì)象模型 (DOM) 的客戶機(jī)。 12345678910下一頁 通過創(chuàng)建更新存儲(chǔ)過程,可以更新數(shù)據(jù)庫中的 XML 文檔而無需將其交給客戶機(jī)。該存儲(chǔ)過程支持對(duì)本機(jī)存儲(chǔ)在數(shù)據(jù)庫中的 XML 文檔進(jìn)行部分更新。存儲(chǔ)過程答應(yīng):更改目標(biāo) XML 文檔中任何文本或?qū)傩怨?jié)點(diǎn)的值使用另一個(gè) XML 元素替換 XML 文檔中的元素節(jié)點(diǎn)(及其所有子節(jié)點(diǎn))刪除 XML 文檔中的節(jié)點(diǎn)插入新元素多次更新源文檔更新多個(gè)源文檔使用修改的 XML 文檔替換另一個(gè) XML 文檔將修改的文檔插入新記錄更新信息可以:靜態(tài)地嵌入更新調(diào)用中使用 SQL 在運(yùn)行時(shí)動(dòng)態(tài)地創(chuàng)建使用算術(shù)表達(dá)式基于初始文本或?qū)傩灾颠M(jìn)行計(jì)算注重:在后臺(tái),更新存儲(chǔ)過程仍然執(zhí)行完整的文檔更新。XMLUPDATE 命令DB2XMLFUNCTIONS.XMLUPDATE (commandXML、querySQL、updateSQL、errorCode、errorMsg)commandXML —— 該參數(shù)是一個(gè)用于封裝更新命令的 XML 字符串。這些命令將應(yīng)用到由 querySQL 所選擇的 XML 文檔。該命令的結(jié)構(gòu)是:<updates namespaces=""><update using="" col="" action="" path="">update value</update></updates>—— 這是用于包裝所有更新命令元素的根元素。@namespace —— 該屬性的值應(yīng)該是由分號(hào)分隔的 “前綴:名稱空間 字符串。前綴然后用于在 XML 文檔中導(dǎo)航時(shí)使用的任何路徑表達(dá)式中。Essential —— 否(僅當(dāng)在任何路徑中使用名稱空間時(shí)才需要它)。即使是默認(rèn)名稱空間也必須用一個(gè)前綴進(jìn)行限定。 上一頁1234567下一頁 —— 該元素定義需要在目標(biāo) XML 文檔上執(zhí)行的每個(gè)修改。Occurrence —— 可以定義這些元素中的一個(gè)或多個(gè)。每次出現(xiàn)處理文檔的一個(gè)修改。@col —— 該屬性的值應(yīng)該是對(duì)應(yīng)于要在 querySQL 中修改的列位置的編號(hào)。Essential —— 是。Valid value —— 列位置從 1 開始。@path —— 該屬性的值是目標(biāo) XML 文檔中節(jié)點(diǎn)的 XPath 位置。假如路徑無效,則存儲(chǔ)過程將中止。Essential —— 是。Valid value —— XPath 表達(dá)式。假如要在 Xpath 中使用名稱空間,請(qǐng)確保設(shè)置名稱空間屬性。不能將通配符用于名稱空間。@using —— 該屬性的惟一有效值是 SQL。假如該屬性存在并設(shè)置為 SQL,那么 update value( 元素的子節(jié)點(diǎn))被視為一個(gè) SQL 查詢。查詢結(jié)果的第一行中的第一列將用作新的 update value。假如查詢失敗,那么存儲(chǔ)過程將中止。Essential —— 否。Valid value —— SQL。對(duì)于 Xquery,可以使用要害字 Xquery,也可以使用 SQL/XML 函數(shù)將 XQuery 嵌入 SQL。@action —— 該屬性定義將在 XML 文檔中的目標(biāo)節(jié)點(diǎn)(使用 @path 屬性中定義的 XPath 來定位)上進(jìn)行的操作。假如操作失敗,那么存儲(chǔ)過程將中止。Essential —— 否。假如未設(shè)置操作,則假定是一個(gè)替換操作。Valid value —— 替換、追加、刪除和計(jì)算:replace —— 使用 update value 替換目標(biāo)節(jié)點(diǎn)。append —— 將 update value 作為子節(jié)點(diǎn)追加到目標(biāo)節(jié)點(diǎn)。 上一頁12345678下一頁 delete —— 刪除目標(biāo)節(jié)點(diǎn)。compute —— 將 update value 當(dāng)作參數(shù)化的表達(dá)式。表達(dá)式中的問號(hào) (?) 將由目標(biāo)節(jié)點(diǎn)的現(xiàn)有文本值替換。然后,計(jì)算表達(dá)式,得到的值將替換目標(biāo)節(jié)點(diǎn)中的現(xiàn)有值。計(jì)算出的值的 XPath 只能是葉節(jié)點(diǎn)。update value —— 這為每個(gè)更新命令 (//update/*) 的子節(jié)點(diǎn)。它可以是文本節(jié)點(diǎn),也可以是元素。Essential —— 否。對(duì)于 action=delete,不需要它。Valid value —— 當(dāng) @using 屬性被設(shè)置為 SQL 時(shí),子節(jié)點(diǎn)應(yīng)該是文本值。它被當(dāng)作 SQL 表達(dá)式。當(dāng) @action 屬性被設(shè)置為 compute 時(shí),子節(jié)點(diǎn)應(yīng)該是文本值。它被當(dāng)作參數(shù)化表達(dá)式。在所有其他情況下,子節(jié)點(diǎn)都視為要替換的值。querySQL —— 任何用于檢索需要更新的 XML 文檔的有效 SQL 選擇語句。Essential —— 是。Valid value —— 只能選擇 XML 文檔。假如選擇了其他列,存儲(chǔ)過程就會(huì)中止。updateSQL —— 它表示參數(shù)化的更新 SQL。修改的 XML 文檔作為運(yùn)行時(shí)參數(shù)被綁定到更新 SQL。它答應(yīng)將修改的 XML 文檔保存到數(shù)據(jù)庫中的其他 XML 列中。Essential —— 否。假如該參數(shù)為 null,則使用可更新的游標(biāo)來修改所選的列。重要事項(xiàng):從命令行處理器 (CLP) 執(zhí)行更新存儲(chǔ)過程時(shí),始終需要設(shè)置 updateSQL 參數(shù)的值。假如將這個(gè)值設(shè)置為 null 或空字符串,CLP 會(huì)拋出 JCC 異常:Column not updatable。當(dāng)您從應(yīng)用程序代碼 (Java) 內(nèi)部調(diào)用更新存儲(chǔ)過程時(shí),將發(fā)生此情況(即 updateSQL 設(shè)置為 null)。errorCode —— 值為 -1 指示存儲(chǔ)過程因發(fā)生某種錯(cuò)誤而中止。假如更新成功,則返回指示已更新的記錄數(shù)的正值。 上一頁123456789下一頁 errorMsg —— 錯(cuò)誤消息,包括 XML 解析器和 JCC 驅(qū)動(dòng)程序拋出的任何異常。注重:假如得到 java.lang.OutOfMemoryError,應(yīng)該增加 java 堆大小:db2 update dbm cfg using JAVA_HEAP_SZ 1024設(shè)置存儲(chǔ)過程首先需要將更新存儲(chǔ)過程 jar 安裝到 DB2 中。這個(gè)過程僅需執(zhí)行一次。下一步,對(duì)于每個(gè)數(shù)據(jù)庫,需要分別注冊(cè)存儲(chǔ)過程。重要事項(xiàng):假如希望在存儲(chǔ)過程中執(zhí)行 Xqueries,那么需要為 DB2 設(shè)置 JCC 驅(qū)動(dòng)程序。確保 DB2 在運(yùn)行,然后從 DB2 命令窗口執(zhí)行以下命令:db2set DB2_USE_DB2JCCT2_JROUTINE=on設(shè)置更新存儲(chǔ)過程的步驟通過執(zhí)行以下步驟編譯 java 代碼并創(chuàng)建 db2xmlfunctions.jar 文件。注重:db2xmlfunctions.jar 還可以從 下載 部分下載。假如您選擇下載該文件,則跳過 第 2 步。創(chuàng)建目錄 /temp/samples。將 XMLUpdate_code.zip(可以在 下載 部分找到)復(fù)制到 temp 目錄。將 XMLUpdate.java 和 XMLParse.java 文件解壓到 /temp/samples 目錄。編譯 java 文件并為 UDF 創(chuàng)建 jar 文件。在 Microsoft Windows 上,打開 DB2 命令窗口:SET CLASSPATH= .;%DB2PATH%javadb2java.zip;%DB2PATH%javadb2jcc.jar;%DB2PATH%javadb2jcc_license_cisuz.jar;"%DB2PATH%javajdkinjavac.exe" -d . *.java"%DB2PATH%javajdkinjar" cvf db2xmlfunctions.jar com/ibm/db2/xml/functions/*.class在 AIX 上,將 DB2PATH 設(shè)置為 DB2 SQLLIB 目錄:CLASSPATH=$DB2PATH/java/sqlj.zip:$DB2PATH/java/db2java.zip$DB2PATH/java/jdk/bin/javac.exe" -d . *.java$DB2PATH/java/jdk/bin/jar" cvfdb2xmlfunctions.jar com/ibm/db2/xml/functions/*.class 上一頁12345678910下一頁 注重:上述命令假定使用 sh 或 bash shell。根據(jù)需要更改為 csh、tsh 等。在 DB2 中安裝存儲(chǔ)過程:DB2 -tconnect to your_dbnameÿCALL SQLJ.INSTALL_JAR('file:/temp/samples/db2xmlfunctions.jar' ,db2xmlfunctions,0);在數(shù)據(jù)庫中注冊(cè)存儲(chǔ)過程:CREATE PROCEDURE db2xmlfunctions.XMLUPDATE(IN COMMANDSQL VARCHAR(32000),IN QUERYSQL VARCHAR(32000),IN UPDATESQL VARCHAR(32000),OUT errorCode INTEGER, OUT errorMsg VARCHAR(32000))DYNAMIC RESULT SETS 0LANGUAGE JAVAPARAMETER STYLE JAVANO DBINFOFENCEDNULL CALL MODIFIES SQL DATAPROGRAM TYPE SUBEXTERNAL NAME 'db2xmlfunctions:com.ibm.db2.xml.functions.XMLUpdate.Update' ;TERMINATE;刪除存儲(chǔ)過程假如更改了存儲(chǔ)過程,那么在注冊(cè)新版本之前應(yīng)該首先從 DB2 卸載它:DROP PROCEDURE DB2XMLFUNCTIONS.XMLUPDATE(VARCHAR(32000),VARCHAR(32000),VARCHAR(32000),INTEGER, VARCHAR(32000));CALL SQLJ.REMOVE_JAR(DB2XMLFUNCTIONS);XMLUpdate 示例對(duì)于 XMLUpdate 示例,請(qǐng)執(zhí)行以下步驟:創(chuàng)建測(cè)試表:Create table XMLCustomer(cid integer not null PRIMARY KEY, info XML );將示例 XML 文檔插入表中:Insert into XMLCustomer (cid, info ) values (1006 ,XMLPARSE ( DOCUMENT '<customerinfo xmlns="http://posample.org" Cid="1006"><name>Hardeep Singh</name><addr country="United States"><street>555 Bailey Ave</street><city/><prov-state>CA</prov-state><pcode-zip> 95141</pcode-zip></addr><phone type="">543-4610</phone></customerinfo>'PRESERVE WHITESPACE ) ); 上一頁234567891011下一頁 注重:由于更新調(diào)用修改了初始的 XML 文檔,所以您需要為某些查詢而刪除插入的文檔,并重新插入它。示例查詢下面是示例查詢:替換節(jié)點(diǎn):action=replace。通過使用復(fù)雜名稱元素替換簡單名稱元素來更新測(cè)試文檔:Call DB2XMLFUNCTIONS.XMLUPDATE ('<updates namespaces="x:http://posample.org"><update action="replace" col="1" path="/x:customerinfo/x:name"><name><fname>Hardeep</fname><lname>Singh</lname></name></update></updates>','Select info from XMLCustomer where cid=1006','update XMLCustomer set info=? where cid=1006',?,?);使用 SQL 查詢獲取新值以進(jìn)行更新:using=SQL。Call DB2XMLFUNCTIONS.XMLUPDATE ('<updates namespaces="x:http://posample.org"><update using="sql" action="replace" col="1"path="http://x:customerinfo[@Cid=1006]/x:addr/x:pcode-zip/text()">select cid from XMLCustomer where cid=1006</update></updates>','Select info from XMLCustomer where cid=1006','update XMLCustomer set info=? where cid=1006',?,?);使用給定表達(dá)式來計(jì)算值:action=compute。Call DB2XMLFUNCTIONS.XMLUPDATE ('<updates namespaces="x:http://posample.org"><update action="compute" col="1"path="/x:customerinfo/x:addr/x:pcode-zip/text()">(20+?)*32-?</update></updates>','Select info from XMLCustomer where cid=1006','update XMLCustomer set info=? ÿhere cid=1006',?,?); 上一頁34567891011下一頁 對(duì)目標(biāo) XML 文檔執(zhí)行多個(gè)操作:Call DB2XMLFUNCTIONS.XMLUPDATE ('<updates namespaces="x:http://posample.org"><update using="sql" action="replace" col="1"path="/x:customerinfo/x:addr/x:pcode-zip/text()">select cid from XMLCustomer where cid=1006</update><update action="compute" col="1"path="/x:customerinfo/x:addr/x:pcode-zip/text()">(2+?)*10-?</update><update action="delete" col="1" path="/x:customerinfo/x:name"/></updates>','Select info from XMLCustomer where cid=1006','update XMLCustomer set info=? where cid=1006',?,?);更新文檔時(shí)對(duì)其進(jìn)行驗(yàn)證。為此,您需要?jiǎng)?chuàng)建模式并在 XSR 中注冊(cè)。Call DB2XMLFUNCTIONS.XMLUPDATE ('<updates namespaces="x:http://posample.org"><update using="sql" action="replace" col="1"path="/x:customerinfo/x:addr/x:pcode-zip/text()">select cid from XMLCustomer where cid=1006</update></updates>','Select info from XMLCustomer where cid=1006','update XMLCustomer set info=xmlvalidate(? according to XMLSCHEMA ID test.schema2) where cid=1006',?,?) 上一頁4567891011下一頁 使用 XMLUpdate 替換屬性值。Call DB2XMLFUNCTIONS.XMLUPDATE ('<updates namespaces="x:http://posample.org"><update action="replace" col="1"path="/x:customerinfo/x:phone/@type">tie line</update></updates>','Select info from XMLCustomer where cid=1006','update XMLCustomer set info=? where cid=1006',?,?);使用 XMLUpdate 替換文本值。Call DB2XMLFUNCTIONS.XMLUPDATE ('<updates namespaces="x:http://posample.org"><update action="replace" col="1"path="/x:customerinfo/x:addr/x:city/text()">San Jose</update></updates>','Select info from XMLCustomer where cid=1006','update XMLCustomer set info=? where cid=1006',?,?);重要事項(xiàng):必須在路徑的末尾指定 text()。這一步確保即使是空元素(即不具有現(xiàn)有文本節(jié)點(diǎn)的元素)也進(jìn)行更新。假如省略了 text() 且不存在要替換的現(xiàn)有文本值,更新命令就會(huì)失敗。使用 XMLUpdate 追加子節(jié)點(diǎn)。Call DB2XMLFUNCTIONS.XMLUPDATE ('<updates namespaces="x:http://posample.org"><update action="append" col="1" path="/x:customerinfo/x:addr"><county>Santa Clara</county></update></updates>','Select info from XMLCustomer where cid=1006','update XMLCustomer set info=? where cid=1006',?,?); 上一頁567891011下一頁 注重:新節(jié)點(diǎn) 不在任何名稱空間中。使用 XMLUpdate 將更新的 XML 插入新行。Call DB2XMLFUNCTIONS.XMLUPDATE ('<updates namespaces="x:http://posample.org"><update action="replace" col="1"path="/x:customerinfo/x:name"><name>Marja Soininen</name></update><update action="replace" col="1"path="/x:customerinfo/@Cid">1008</update></updates>','Select info from XMLCustomer where cid=1006','insert into XMLCustomer (cid, info ) values (1008, cast( ? as xml))',?,?);使用 XMLUpdate 刪除節(jié)點(diǎn)。Call DB2XMLFUNCTIONS.XMLUPDATE ('<updates namespaces="x:http://posample.org"><update action="delete" col="1" path="/x:customerinfo/x:name"/></updates>','Select info from XMLCustomer where cid=1006','update XMLCustomer set info=? where cid=1006',?,?);當(dāng)更新元素中沒有設(shè)置 @action 時(shí),就默認(rèn)執(zhí)行替換操作。Call DB2XMLFUNCTIONS.XMLUPDATE ('<updates namespaces="x:http://posample.org"><update col="1" path="http://x:customerinfo[@Cid=1006]/x:phone"><phone><areacode>910</areacode></phone></update></updates>','Select info from XMLCustomer where cid=1006','update XMLCustomer set info=? where cid=1006',?,?); 上一頁67891011下一頁
標(biāo)簽:
DB2
數(shù)據(jù)庫
排行榜
