Wednesday, October 04, 2006

XQuery

ช่วงนี้มีโปรเจคที่ต้องยุ่งกับ XML เยอะๆอยู่ตัว
ก็เลยมองหา solution ที่มาช่วยจัดการ
หนึ่งใน solution นั้นก็คือ XQuery

query language ของ Relational Database คือ SQL
query language ของ XML ก็คือ XQuery

ตัว syntax ของ XQuery มีบางคนเรียกย่อๆว่า FLWOR
ซื่อย่อมาจาก causes หลักๆที่ XQuery support นั่นคือ
  • F -> For
  • L -> Let
  • W -> Where
  • O -> Order by
  • R -> Return

มาตรฐานของ XQuery จะ depend อยู่บน มาตรฐานของ XPath 2.0
นั่นคือการอ้างถึง element ต่างๆ จะทำผ่าน XPath expression
ใครอยากเห็นว่าหน้าตา syntax เป็นอย่างไร ให้ดูที่ link นี้
Blooming FLWOR - An Introduction to the XQuery FLWOR Expression

ตัว language เห็นบางคนก็บอกว่า มีแนวทางไปในทางเดียวกับ Functional Language
อ่านดูได้ใน XQuery: a typed functional language for querying XML
ส่วนบางคนก็บอกว่า XQuery is imperative
ถ้ามีสองความคิดเห็นอย่างนี้ แสดงว่า xquery มันน่าอยู่กลางๆ spectrum ที่ฝั่งซ้ายเป็น declarative
ส่วน ฝั่งขวาเป็น imperative
(ไม่ว่าจะเป็นอะไร ก็ช่างหัวมันเถิด ใช้งานได้ดีก็พอแล้ว)

ผมชอบความ powerful ของมัน ลองดูตัวอย่างนี้
สมมติเรามี xml ที่ present Part ในลักษณะ Flat อยู่
<?xml version="1.0" encoding="ISO-8859-1"?>
<partlist>
<part partid="0" name="car"/>
<part partid="1" partof="0" name="engine"/>
<part partid="2" partof="0" name="door"/>
<part partid="3" partof="1" name="piston"/>
<part partid="4" partof="2" name="window"/>
<part partid="5" partof="2" name="lock"/>
<part partid="10" name="skateboard"/>
<part partid="11" partof="10" name="board"/>
<part partid="12" partof="10" name="wheel"/>
<part partid="20" name="canoe"/>
</partlist>

ถ้าเราต้องการ convert ให้เป็นแบบนี้
<parttree>
<part partid="0" name="car">
<part partid="1" name="engine">
<part partid="3" name="piston"/>
</part>
<part partid="2" name="door">
<part partid="4" name="window"/>
<part partid="5" name="lock"/>
</part>
</part>
<part partid="10" name="skateboard">
<part partid="11" name="board"/>
<part partid="12" name="wheel"/>
</part>
<part partid="20" name="canoe"/>
</parttree>

เราสามารถทำได้ โดยเขียน XQuery ในแบบนี้
declare function local:one_level($p as element()) as element()
{
<part partid="{ $p/@partid }"
name="{ $p/@name }" >
{
for $s in doc("partlist.xml")//part
where $s/@partof = $p/@partid
return local:one_level($s)
}
</part>
};

<parttree>
{
for $p in doc("partlist.xml")//part[empty(@partof)]
return local:one_level($p)
}
</parttree>

ช่วงนี้เพื่อทดสอบความเป็นไปได้ต่างๆ ผมก็เลยลองหา Opensource มาเล่นก่อน
ตัวที่น่าสนใจก็คือ eXist
ซึ่งเจ้านี้ claim ว่า XQuery ของเขา test ตามมาตรฐานของ w3c ผ่านกว่า 80% แล้ว

Architecture ของ eXist (ในแง่ implement) ก็น่าสนใจ ตรงที่ Framework ที่เขาใช้เขียน server
base อยู่บน Cocoon ซึ่งเป็น Development Framework ที่อิงกับ XML อย่างแนบแน่น

Related link from Roti

No comments: