Hãy tìm hiểu cách để mở rộng mô hình XML nhằm tạo ra các trình khách đầy đủ (rich client) bằng cách sử dụng dữ liệu XML được chuyển đến từ máy chủ ứng dụng của bạn. Hãy khám phá cách sử dụng HTML động (DHTML) để biểu diễn XML, XPath để dẫn hướng trong XML và mô hình đối tượng tài liệu (DOM) để sửa đổi và tuần tự hóa XML trở lại máy chủ ứng dụng.
                
              
                                            
                                
            
                       
            
                 24 trang
24 trang | 
Chia sẻ: haohao89 | Lượt xem: 1928 | Lượt tải: 1 
              
            Bạn đang xem trước 20 trang tài liệu Lập trình với XML cho DB2: Lập trình với XML ở phía khách, để xem tài liệu hoàn chỉnh bạn click vào nút DOWNLOAD ở trên
Lập trình với XML cho DB2, Phần 3: Lập trình với XML ở phía khách 
Hardeep Singh, Kiến trúc sư các công nghệ nâng cao, IBM 
Tóm tắt: Hãy tìm hiểu cách để mở rộng mô hình XML nhằm tạo ra các trình 
khách đầy đủ (rich client) bằng cách sử dụng dữ liệu XML được chuyển đến từ 
máy chủ ứng dụng của bạn. Hãy khám phá cách sử dụng HTML động (DHTML) 
để biểu diễn XML, XPath để dẫn hướng trong XML và mô hình đối tượng tài liệu 
(DOM) để sửa đổi và tuần tự hóa XML trở lại máy chủ ứng dụng. 
Giới thiệu 
Sự phổ biến ngày một tăng của Web 2.0 phần lớn là nhờ tính linh hoạt của các thế 
hệ trình duyệt web hiện nay. Các trình duyệt này sử dụng Ajax để giao tiếp với 
máy chủ để trao đổi dữ liệu XML và sau đó sử dụng DHTML để dẫn hướng XML 
và trình bày nó cho người dùng. Các tính năng trình duyệt cho phép chúng được 
sử dụng như là các trình khách đầy đủ trong các ứng dụng dựa trên web. 
Các công nghệ cơ sở đã sản sinh một số công nghệ và sáng kiến mới để đáp ứng 
sự phổ biến ngày càng tăng của Web 2.0. Các thư viện trình trợ giúp như Dojo và 
Sarissa đã được tạo ra nhằm làm cho việc sử dụng XML ít khó khăn hơn, và các 
hỗ trợ cho Đồ họa véc tơ co giãn được (Scalable Vector Graphics -SVG) cũng đã 
tăng thêm. Các trình tiện ích (widget) nhúng được như Google và Yahoo Maps, 
các phương thức chia sẻ và tích hợp dữ liệu như nguồn cấp dữ liệu RSS và Atom, 
và mẫu hình phát triển mới bằng cách sử dụng hỗn hợp dữ liệu đã được phát triển 
để đáp ứng các nhu cầu ngày càng tăng của văn hóa Web 2.0. 
Như hình 1 minh hoạ, chất keo chung để kết dính tất cả các công nghệ là XML. 
XML trong nguồn cấp dữ liệu làm cho có thể xuất bản và xử lý các cấu trúc dữ 
liệu phức tạp trên web. Giao diện lập trình ứng dụng DOM (API) trong DHTML 
và sự hỗ trợ XPath trong Sarissa cho phép điều hướng XML một cách có hiệu quả 
để đọc và viết ở phía máy khách. 
Hình 1. Kiến trúc hướng Web 
Ghi chú : Trong thế giới Web 2.0, nơi mà các nguồn dữ liệu được xem như là 
nguồn cấp dữ liệu và dịch vụ, thì trình điều khiển cơ sở dữ liệu được mở rộng để 
hỗ trợ các cuộc gọi REST, SOAP và FEED. Một khi vấn đề bảo đảm an ninh được 
giải quyết, thì bạn có thể truy cập trực tiếp các thường trình của cơ sở dữ liệu bằng 
cách sử dụng các cuộc gọi SOAP hoặc REST không chỉ từ máy chủ ứng dụng, mà 
còn từ một trình khách web, mà không cần phải tạo ra các ánh xạ không cần thiết. 
Trong bài tiếp theo, tôi sẽ tạo một mẫu trình điều khiển (driver) SOAP cho DB2. 
Sử dụng mô hình XML ở phía khách 
Vì nhiều công nghệ xung quanh XML là chung cho các máy chủ ứng dụng và 
trình duyệt, nên bạn cũng có thể mở rộng mô hình dữ liệu XML được trình bày 
trong bài viết đầu tiên tới phía máy khách. Trong bài viết này, bạn hãy tìm hiểu 
cách để mở rộng mô hình XML nhằm tạo ra các trình khách đầy đủ bằng cách sử 
dụng dữ liệu XML được chuyển đến từ các máy chủ ứng dụng. Hãy khám phá 
cách làm thế nào sử dụng DHTML để biểu diễn XML, sử dụng XPath để dẫn 
hướng XML và DOM để sửa đổi và tuần tự hóa XML trở lại máy chủ ứng dụng. 
Tương tự như lớp bao bọc DOM mà bạn đã tạo ra trong máy chủ ứng dụng, bạn sẽ 
tạo ra một lớp bao bọc DOM cho phía máy khách. Lớp bao bọc này không chỉ tách 
biệt việc trực quan hóa của JavaScript và mã logic nghiệp vụ khỏi các API DOM, 
mà còn làm cho mã lệnh rất giống với mã Java trong tầng máy chủ ứng dụng. Để 
đạt được điều này, bạn sẽ sử dụng thư viện nguồn mở Sarissa, nó cung cấp các 
API XPath cho mã JavaScript chạy trong trình duyệt. Mã của lớp bao bọc có sẵn 
trong bài viết này (xem phần Tài nguyên). 
Kịch bản 
Các phần sau xây dựng trên các ví dụ về bảo hiểm được tạo ra trong các bài viết 
trước của loạt bài này (xem phần Tài nguyên). Các chức năng sau được trình 
khách web cung cấp. 
1. Cho phép người dùng xem và chỉnh sửa tên và họ trong hồ sơ của họ. 
2. Tính toán mức bảo hiểm cho mỗi mục bảo hiểm dựa vào nhà cung cấp bảo hiểm 
mà người sử dụng lựa chọn. 
Điều quan trọng cần lưu ý: Mã trong bài viết này và các bài viết trước đây chỉ 
nhằm mục đích giải thích. Chỉ có phần giải thích sự liên quan của mô hình XML 
là được mã hóa đầy đủ. Các phần còn lại của logic được viết bằng mã giả với giả 
định rằng người đọc có thể ngoại suy ra mã lệnh tiêu chuẩn dự kiến cho chức năng 
đó. Bài viết tiếp theo thảo luận về một kịch bản hoàn chỉnh sẽ được mã hóa đầy 
đủ. 
Cho phép người sử dụng xem và chỉnh sửa tên của mình 
Lấy thông tin của khách hàng từ máy chủ ứng dụng và trình bày nó cho phía khách 
để sửa đổi. 
Mã JavaScript của trình khách 
Lớp profilediv được sử dụng để xuất bản chuỗi ký tự HTML được tạo ra từ dữ liệu 
XML cho người sử dụng. 
ID của khách hàng (cid) được nhập vào khi người dùng đăng nhập vào trang web. 
ID của khách hàng này được chuyển tới hàm getCustomerInfo khi người sử dụng 
chọn Cập nhật bản lược kê từ phía khách. Trình khách gửi yêu cầu HTTP đến máy 
chủ bằng cách sử dụng API XMLHttpRequest mà thư viện Sarissa cung cấp. Là 
một phần của yêu cầu, hàm Callback cũng được định nghĩa. Hàm 
customerInfoCallback này được gọi ra khi đáp ứng đến từ máy chủ. Liệt kê 1 cho 
thấy cách để lấy thông tin của khách hàng: 
Liệt kê 1. Máy khách yêu cầu thông tin khách hàng 
function getCustomerInfo(cid) 
{ 
 var xmlhttpObj= new XMLHttpRequest(); 
 var addr=hosturl+"?cmd= getuserprofile&msg="+cid; 
 var xmlhttpObj= new XMLHttpRequest(); 
 xmlhttpObj.open('GET', addr, true); 
 xmlhttpObj.onreadystatechange = function() { customerInfoCallback(xmlhttpObj); 
}; 
 xmlhttpObj.send(""); 
 } 
Mã Java của máy chủ ứng dụng 
Liệt kê 2 cho thấy những gì xảy ra trong máy chủ ứng dụng khi nó nhận được yêu 
cầu HTTP từ các trình khách. Trước tiên máy chủ sẽ kiểm tra xem các yêu cầu 
HTTP đó là POST hay là GET, và sau đó, dựa trên thông tin này, nó lấy ra câu 
lệnh và các giá trị dữ liệu từ các thông số của cuộc gọi HTTP. 
Liệt kê 2. Máy chủ ứng dụng lấy ra các thông tin của khách hàng 
public void service( HttpServletRequest _req, HttpServletResponse _res) 
throws ServletException, IOException 
{ 
 String cmd, msgtext, returnvalue; 
 if(_req.getMethod().equalsIgnoreCase("POST")) 
 { 
 String message = getPostBody(_req.getReader()); 
 XMLParse msgxml=new XMLParse(message); 
 cmd= msgxml.getValue("//request/@cmd"); 
 msgtext= msgxml.toString("/request/*"); 
 } 
 else { 
 cmd= _req.getParameter("cmd"); 
 msgtext= _req.getParameter("msg"); 
 } 
} 
Vì rằng câu lệnh là để lấy lược kê thông tin của người dùng, nên máy chủ ứng 
dụng truy cập vào thông tin khách hàng từ cơ sở dữ liệu và trả lại nó cho trình 
khách. Liệt kê 3 chỉ cho thấy câu lệnh SQL cần thiết để lấy thông tin, với mong 
đợi rằng độc giả đã hiểu cách sử dụng các API Java Database Connectivity 
(JDBC) để kết nối với cơ sở dữ liệu và nhận kết quả truy vấn. 
Vì thông tin khách hàng được lưu trữ trong cơ sở dữ liệu như là một tài liệu XML, 
nên bạn không cần thực hiện bất kỳ chuyển đổi nào đối với dữ liệu để gửi lại cho 
trình khách. Xin lưu ý rằng kiểu nội dung của dữ liệu được trả về được đặt là 
XML trong phần đầu của đáp ứng HTTP. 
Liệt kê 3. Đáp ứng của máy chủ ứng dụng 
if(cmd.equalsIgnoreCase("getuserprofile")) 
{ 
 //returnvalue= select CUSTXML from customer_table where customerid =msgtext 
} 
_res.setContentType("text/xml"); 
_res.getWriter().write(returnvalue); 
_res.setHeader("Cache-Control", "no-cache"); 
Mã Java của trình khách 
Khi trình khách nhận được phản hồi từ máy chủ ứng dụng, thì hàm được định 
nghĩa trong sự kiện callback được gọi ra. 
Liệt kê 4 cho thấy yêu cầu lấy UserInfo. Xin lưu ý rằng UserInfo được khai báo là 
một biến toàn cục, bởi vì nó được sửa đổi khi bạn gửi các bản cập nhật họ và tên 
mà người sử dụng thực hiện. 
Liệt kê 4. Yêu cầu lấy UserInfo 
var userinfo=null; 
function customerInfoCallback (xmlhttp) 
{ 
 if (xmlhttp.readyState == 4 && xmlhttp.status == 200) 
{ 
Vì rằng giá trị trả về từ máy chủ là XML, nên bạn chuyển trực tiếp nó cho hàm tạo 
của lớp bao bọc DOM của bạn. 
userinfo= new xmlparse(xmlhttp.responseXML, false); 
Tiếp theo, bạn trích ra họ và tên từ XML bằng cách sử dụng XPath. 
var firstname = userinfo.getValue("/Customer/@firstname",null); 
var lastname = userinfo.getValue("/Customer/@lastname",null); 
Liệt kê 5 cho thấy cách sử dụng DHTML để tạo ra một giao diện người dùng đồ 
họa (GUI) cho việc sửa đổi tên người dùng và chèn nó vào thẻ div là profilediv mà 
bạn đã khai báo trong trang HTML của mình. 
Liệt kê 5. DHTML tạo ra một giao diện người dùng đồ họa 
var htmlstr=""; 
htmlstr+='firstname:'; 
htmlstr+='lastname:'; 
htmlstr+='<input type="button" value="save" 
onClick="javascript:updateCustomer()"/>'; 
htmlstr+=''; 
document.getElementById("profilediv").innerHTML=htmlstr; 
} 
} 
Sau khi bạn đã thực hiện những sửa đổi, hãy nhấp chuột vào nút Save để gọi hàm 
updateCustomer. Các UserInfo của DOM chứa các thông tin khách hàng được cập 
nhật với các sửa đổi của người dùng. Một lần nữa, bạn sử dụng XPath để điều 
hướng đến các nút dữ liệu cần phải được sửa đổi. 
Liệt kê 6. Sử dụng XPath để cập nhật thông tin khách hàng 
function updateCustomer() 
{ 
 var fname=document.getElementById("fname").value; 
 var lname=document.getElementById("lname").value; 
 userinfo.setValue("/Customer/@firstname",null,fname); 
 userinfo.setValue("/Customer/@lastname",null,lname); 
} 
Một yêu cầu mới được tạo ra và DOM đã cập nhật được tuần tự hóa và được gắn 
vào nó. Liệt kê 7 cho thấy chuỗi yêu cầu sau đó được gửi (POST) đến máy chủ. 
Lưu ý rằng vì định dạng thông điệp là XML, nên kiểu nội dung trong phần đầu của 
HTTP của yêu cầu được đặt là XML. 
Liệt kê 7. Chuỗi yêu cầu được gửi tới máy chủ 
var msg=''+userinfo.toString("/")+ 
 ''; 
var xmlhttpObj= new XMLHttpRequest(); 
xmlhttpObj.open('POST', hostname, true); 
xmlhttpObj.onreadystatechange = function() { profileUpdated(xmlhttpObj); }; 
xmlhttpObj.setRequestHeader('content-type', 'text/xml'); 
xmlhttpObj.send(msg); 
} 
Mã Java của máy chủ ứng dụng 
Dữ liệu XML về khách hàng từ yêu cầu gửi tới được phân tích cú pháp bằng cách 
sử dụng lớp bao bọc DOM. 
Vì customerid là một thuộc tính trong lược kê ban đầu của khách hàng được gửi 
đến trình khách, nên không cần phải gửi tham số phụ chứa ID khách hàng trong 
yêu cầu. 
Liệt kê 8 cho thấy cách để trích xuất customerid từ XML và sử dụng nó để tạo ra 
lệnh SQL cập nhật cho cơ sở dữ liệu. Dữ liệu lược kê của khách hàng từ yêu cầu 
HTTP được chuyển như một tham số đến câu lệnh cập nhật, không cần có thay đổi 
gì. 
Liệt kê 8. Tạo một lệnh SQL cập nhật 
else if(cmd.equalsIgnoreCase("updateuserprofile")) 
{ 
 XMLParse custxml=new XMLParse(msgtext); 
 String cid= custxml.getValue("/Customer/@customerid"); 
 //update customer_table set custxml=? where customerid=cid 
 //stmt.setString(1,msgtext); 
} 
Hãy lưu ý sự tương tự trong mã ứng dụng được sử dụng để điều hướng các XML 
trong cả trình khách lẫn máy chủ. Cũng lưu ý rằng máy chủ ứng dụng trong cả hai 
yêu cầu HTTP đã hành động một cách đơn giản như là một người trung gian giữa 
trình khách và cơ sở dữ liệu - không có dữ liệu nào được thao tác trong trao đổi 
này. 
Tính toán mức bảo hiểm cho các hạng mục đã mua 
Người sử dụng lựa chọn một công ty bảo hiểm từ danh sách thả xuống chứa tên 
của tất cả các hãng bảo hiểm. Công ty bảo hiểm có một dịch vụ web có thể truy 
vấn để lấy mức giá bảo hiểm hiện tại. Các thông tin về mức bảo hiểm được cung 
cấp như là một tài liệu XML và được sử dụng bởi ứng dụng để tính toán mức bảo 
hiểm trên mỗi hạng mục. 
Mã Java của trình khách 
URL của dịch vụ web đi kèm mà công ty bảo hiểm cung cấp cũng được chọn từ 
một danh sách. Vì Ajax ngăn ngừa đổi hướng URL, nên bạn cần phải gọi dịch vụ 
web từ máy chủ ứng dụng. Bạn chuyển URL trong yêu cầu đến máy chủ ứng dụng 
để tính toán chi phí bảo hiểm của mỗi hạng mục đã mua. Liệt kê 9 cho thấy quá 
trình này: 
Liệt kê 9. Trình khách lựa chọn URL 
function itemsPurchased(url,cid) 
{ 
 var msg='<data 
customerid="cid"> 
 '; 
 var xmlhttpObj= new XMLHttpRequest(); 
 xmlhttpObj.open('POST', hostname, true); 
 xmlhttpObj.onreadystatechange = function() { temsPurchasedCallback 
(xmlhttpObj); }; 
 xmlhttpObj.setRequestHeader('content-type', 'text/xml'); 
 xmlhttpObj.send(msg); 
} 
} 
Lưu ý : Vì URL có thể chứa các ký tự đặc biệt, chúng ta đã nhúng nó vào bên 
trong một đoạn CDATA để tránh việc yêu cầu XML bị biến dạng 
Mã Java của máy chủ ứng dụng 
Thông điệp yêu cầu được phân tích cú pháp bằng cách sử dụng lớp bao bọc DOM 
và URL của nhà bảo hiểm được tách ra từ nó. Liệt kê 10 cho thấy cách ứng dụng 
sử dụng URL này để thực hiện cuộc gọi đến dịch vụ web của nhà cung cấp bảo 
hiểm để lấy ra tài liệu XML có chứa các mức bảo hiểm. 
Liệt kê 10. Máy chủ ứng dụng lấy ra mức bảo hiểm 
else if(cmd.equalsIgnoreCase("getPurchaseInfoWithInsurance")) 
{ 
 XMLParse dataxml=new XMLParse(msgtext); 
 String url= dataxml.toString("/data/text()"); 
 String insurancestr=callWebServiceUsingHTTPClient(url); 
Lưu ý: Tài liệu XML về mức bảo hiểm được định nghĩa trong bài viết Phần 2, 
trong mục có tên là "Một ví dụ phức tạp hơn". 
ID của khách hàng cũng được trích ra từ thông điệp và được sử dụng để truy vấn 
cơ sở dữ liệu lấy thông tin về các hạng mục đã mua của khách hàng. 
String cid= dataxml.getValue("/data/@customerid"); 
Phần còn lại của logic nghiệp vụ để tạo danh sách các mục đã mua được thực hiện 
theo một trong hai cách: 
1. Thực hiện cuộc gọi đến thủ tục lưu sẵn của cơ sở dữ liệu đã tạo ra trong bài 
viết phần 2 > Liệt kê 6. 
// returnvalue = call customerItemsWithInsurance (cid, insurancestr); 
2. Mã hóa logic này trong máy chủ ứng dụng bằng cách sử dụng đoạn mã 
trong bài viết đầu tiên. Sử dụng customerXML trong Phần 1: Liệt kê 6, lặp 
lần lượt qua từng hạng mục, tính toán chi phí bảo hiểm và bổ xung nó vào 
mục thông tin. 
Hãy thay thế các dòng 9-11 trong mã gốc bằng các dòng sau: 
Liệt kê 11. Thay thế cho các dòng 9-11 
XMLParse insurancexml=new XMLParse(insurancestr); 
customerXML.find("/Customer/Items/item",true); 
String currency= insurancexml.getValue("//rate/@currency"); 
for(int i=0; customerXML.currentFind.getLength()>i;i++) 
{ 
 price = customerXML.getValue("@price",i)); 
 if(price>500) rate= insurancexml.getValue("//rate[@price=""]/@rate")); 
 else If(price>100) rate= insurancexml.getValue("//rate[@price="500"]/@rate")); 
 else rate= insurancexml.getValue("//rate[@price="100"]/@rate")); 
 String iteminsurance=""+price*rate 
 +"" 
 customerXML. appendElement(customerXML.createNode (iteminsurance), 
 customerXML.getNode (null,i), false ) 
} 
// returnvalue = customerXML.toString(); 
Nếu bạn so sánh các mã trên với truy vấn trong thủ tục lưu sẵn 
customerItemsWithInsurance của bài viết thứ 2, bạn sẽ thấy rằng có rất nhiều điểm 
giống nhau giữa chúng, đặc biệt là trong các XPaths đã được sử dụng. Thực tế này 
một lần nữa củng cố lợi thế của việc sử dụng mô hình XML và sự dễ dàng của 
việc đẩy logic nghiệp vụ vào cơ sở dữ liệu. 
Bạn cũng lưu ý sức mạnh của biểu thức XPath để tìm kiếm và điều hướng bên 
trong mô hình dữ liệu XML phân cấp. Việc tái tạo loại tìm kiếm này trong mô 
hình dữ liệu đối tượng bằng cách sử dụng mã java sẽ đòi hỏi rất nhiều nỗ lực. Việc 
sử dụng XPath đơn giản hóa quá trình và cho phép nó được thực hiện bằng chỉ 
một chuỗi ký tự. 
Mã Java của trình khách 
Đáp ứng của máy chủ gọi hàm itemsPurchasedCallback mà trong đó dữ liệu XML 
trả về được phân tách cú pháp bằng cách sử dụng lớp bao bọc DOM. Liệt kê 12 
cho thấy cách để làm điều này: 
 Liệt kê 12. XML được phân tích cú pháp bằng cách sử dụng lớp bao bọc 
DOM 
function itemsPurchasedCallback (xmlhttp) 
{ 
 if (xmlhttp.readyState == 4 && xmlhttp.status == 200) 
 { 
 var itemInfo= new xmlparse(xmlhttp.responseXML, false); 
Đầu tiên bạn hãy trích xuất tên người dùng từ XML đã trả về: 
Liệt kê 13. Trích xuất tên người dùng 
var firstname = userinfo.getValue("/Customer/@firstname",null); 
var lastname = userinfo.getValue("/Customer/@lastname",null); 
 var htmlstr="" 
htmlstr+='firstname:'+firstname 
htmlstr+='lastname:'+lastname 
Sau đó lặp lần lượt qua tất cả các mục trong tài liệu và trích xuất các thông tin liên 
quan để tạo chuỗi HTML được sử dụng để xuất bản thông tin này tới người sử 
dụng. 
Liệt kê 14. Trích xuất HTML cho phép xuất bản 
itemInfo.find("//item",null,true); 
htmlstr+='itemIDdescriptiondatepriceinsurance'; 
for(var j=0;itemInfo.currentFind.length>j ;j++) 
{ 
 var id= itemInfo.getValue("@ID",j); 
 var description= itemInfo.getValue("@description",j); 
 var purchaseDate= itemInfo.getValue("@purchaseDate",j); 
 var price= itemInfo.getValue("@price",j); 
 var insurance= itemInfo.getValue("insurance/text()",j); 
 var currency= itemInfo.getValue("insurance/@currency",j); 
 htmlstr+=''+id+''+description+'' +purchaseDate+ 
 '' +currency+price++'' +insurance; 
} 
document.getElementById("profilediv").innerHTML=htmlstr; 
} 
Hãy lưu ý sự tương tự giữa mã JavaScript trong trình khách đã sử dụng XPath để 
tìm kiếm và lặp lần lượt qua các phần tử mục hàng và mã lệnh Java trong máy chủ 
ứng dụng được định nghĩa từ trước. 
Mô hình dữ liệu đối tượng 
Ngay cả khi bạn đã sử dụng cách tiếp cận mô hình dữ liệu đối tượng tiêu chuẩn, 
các đối tượng dữ liệu tầng ứng dụng của bạn vẫn sẽ cần phải được tuần tự hóa 
thành một định dạng mà trình khách hiểu được. Vì các đối tượng rất phức tạp, nên 
bạn về cơ bản sẽ có hai lựa chọn: 
1. Tạo trang cho trình khách trong tầng ứng dụng và điền dữ liệu vào trong phần 
thích hợp của trang web (cách tiếp cận ASP/JSP). Sau đó đưa ra nhiều API để 
chấp nhận bất kỳ sửa đổi nào của người sử dụng đối với dữ liệu. Các vấn đề với 
cách tiếp cận này là: 
 Nó hòa lẫn mã của trình khách và của máy chủ ứng dụng, tạo ra một kiến 
trúc cẩu thả; 
 Nó đòi hỏi phải tạo ra và viết tư liệu giải thích thêm nhiều API để trình 
khách chuyển trở lại bất kỳ thay đổi dữ liệu đáng kể nào. 
2. Tạo ra một cấu trúc dữ liệu có thể được gửi cho trình khách dưới dạng chuỗi ký 
tự. Định dạng được chấp nhận nhất để biểu diễn một cấu trúc dữ liệu đã tuần tự 
hóa như vậy là XML. Vấn đề với cách làm này là: 
 Bây giờ bạn phải viết thêm mã lệnh để thực hiện việc tuần tự hóa 
 Nếu dữ liệu được cập nhật từ máy khách là XML, thì sau đó cần nhiều mã 
hơn trong máy chủ ứng dụng để diễn giải XML đã sửa đổi trở lại thành đối 
tượng dữ liệu của ứng dụng. 
Một câu hỏi hiển nhiên nảy sinh là: Nếu bạn phải dùng đến mô hình dữ liệu XML 
để giao tiếp với trình khách, thì tại sao không sử dụng nó trong chính tầng ứng 
dụng? 
Bạn vẫn còn cần thao tác các thông tin mà bạn đã nhận như là một kết quả với 
dịch vụ trang web về mức bảo hiểm. Vì rằng các thông tin này ở dạng XML, nên 
đầu tiên bạn cần phải phân rã nó thành mô hình đối tượng của bạn. Nếu dữ liệu 
của bạn đã được lưu trữ trong cơ sở dữ liệu như XML, bạn có thể chuyển XML tới 
cho thủ tục lưu sẵn customerItemsWithInsurance. Vấn đề với cách tiếp cận này là 
nếu bạn đang lưu trữ dữ liệu dưới dạng XML và bạn đang sử dụng mô hình đối 
tượng trong ứng dụng, thì tất cả các loại vấn đề về ánh xạ và biến đổi sẽ phát sinh. 
Nếu dữ liệu được lưu trữ trong cơ sở dữ liệu trong một lược đồ quan hệ, thì các 
truy vấn của bạn vào cơ sở dữ liệu sẽ trở nên phức tạp hơn. Hơn nữa, bạn sẽ phải 
viết mã bổ xung ở tầng giữa để ánh xạ dữ liệu quan hệ tới mô hình dữ liệu đối 
tượng hoặc mô hình dữ liệu XML. 
Kết luận 
Trong kiến trúc hướng Web, dữ liệu cần phải được tuần tự hóa qua các tầng khác 
nhau của ứng dụng. Cách thức dễ được chấp nhận nhất để chuyển các dữ liệu phức 
tạp giữa một trình khách web và máy chủ ứng dụng là XML. Trong mỗi tầng, các 
dữ liệu có thể được truy vấn, chuyển đổi, và cập nhật, vì nếu bản chất XML của dữ 
liệu được duy trì, thì sau đó nó có thể sử dụng các công nghệ dựa trên XML như 
XPath, DOM và XQuery để thao tác dữ liệu. Đây là mô hình dữ liệu XML cho lập 
trình và trong thế giới đầy thách th