有一段時間,在 web 上出現了有關標記未來發展的競爭,即 W3C 的 XHTML 2 和 HTML5 之間的競爭,這是主要浏覽器廠商在其各自組織下進行的競爭。首先,W3C 接管了 Html5,並且它最近宣布了 XHTML 2 的衰退。這就使 web 上的 XML 的未來產生了巨大差異,此外, Html5 現已成為每個 XML 開發人員都會使用的一種技術。
但是,XML 愛好者不必失望:HTML5 支持恰當的 XML 序列化。了解 XML 形式的 Html5 包括與舊式 XHtml 規則的一些主要差別,以及如何在現代 web 浏覽器中實際應用此詞匯。
HTML 的歷史一直存有爭議。即使是 web 架構師盡了最大努力,網頁始終是一個難以駕馭的領域,它具有混亂的、令人費解的,甚至是有時非常惱人的破碎標記(別名為標簽雜燴)。 XML 的一個目標始終是幫助解決這種混亂問題,因此 XML 被定義為 “web 的 SGML”(SGML 是一種原語言,而 HTML 只是其中的一種)。XML 一問世就立刻引起了軒然大波。W3C 期望 XML 在浏覽器中獲得成功,並將 XHTML 作為比 Html 更連貫的最自然的發展。不幸的是,總是出現意想不到的問題破壞這一目標。看似簡單的概念(比如命名空間和鏈接)成為技術政治的夢魇。由此產生的爭議和延遲已足以使浏覽器開發人員確信,XML 可幫助解決現有問題,但是它又提出了更多新的、未知的問題。
即使沒有越來越多的證據表明 XML 並非靈丹妙藥,對於使用標記雜燴的大量舊式網頁來說,當浏覽器開發人員試圖遷移到嚴格的基於 XML 的路徑時,總是會遇到問題。此外,請考慮 Postel's Law(Postel 法則),這一法則根據著名的計算機科學家 John Postel 命名。該法則規定:
像保守派那樣去做,像自由派那樣去接受其他的。
XML 的限制與此法則在服務器或數據庫端是一致的,管理人員在策略方面是保守的。這也是 XML 茁壯成長的原因。web 浏覽器可能是從其他人那裡接收信息的最終示例,所以這也是 XML 和 Postel 法則最關注的地方。
XHtml 的發展
在過去幾年裡形勢已非常嚴峻。浏覽器廠商在很大程度上一直忽略了 W3C,並且成立了一個 Web 超文本應用技術工作組(Web Hypertext Application Technology Working Group,WHAT WG)發展 HTML,創建了 HTML5。但是對 W3C XHTML 的支持卻停滯了。通過提供場所來繼續 HTML5 工作,W3C 第一次認清了現實,並且它在 2009 年停止了 XHTML 工作,接受了失敗這一事實。沒有一種方法來衡量這是否是 XHTML 在實踐中的結束。當然 HTML5 並非是有意設計為 XML 友好的,但它至少以 HTML 的 XML 序列化形式(在本文中是 XHtml5)提供了口惠。然而,事情還遠沒有解決,正如 Html5 FAQ 中的一個問題所述:
如果我在 HTML 文檔中小心地使用語法,是否可以使用 XML 解析器處理它?不可以。HTML 和 XML 有著顯著的差別,尤其是在解析需求方面,並且您無法使用針對一方設計的工具去處理另一方的問題。但是,由於 Html5 是根據 DOM 定義的,所以在大多數情況下,可使用 HTML 或 XHTML 序列化來表示同一文檔。但是,稍後將介紹一些差異,這些差異使 XHTML 無法准確表示一些 Html 文檔,反之亦然。
對於對 web 上的 XML 的未來感興趣的任何開發人員來說,這種情況會讓他們感到非常困惑。本文將提供一個實用指南,闡述在 Html 5 中使用 XML 的情況。本文是為那些被我稱為終極網絡黑客 的人而編寫的,他們不是 W3C 標准大師,但要麼對在 web 上生成 XHTML 5 感興趣,要麼對以簡單的方式使用它感興趣(也就是使用信息而不是擔心龐大復雜的呈現)。我承認,做出其中一些建議對我來說是痛苦的,因為正確處理 XML 已有一個長期主張。記住,Html5 仍然是 W3C 的工作草案,在它成為一個完整的建議之前可能還需要一段時間。盡管其中一些特性很穩定且能在 web 上很好地實現。
將文檔作為 XHtml5 提供
不幸的是,我有更多的壞消息。您可能無法像官方定義的那樣使用 XHTML5。這是因為一些法規規定:為了將文檔轉換為 XHTML5,它必須使用 application/xhtml+xml 或 application/XML MIME 類型提供。但是如果您這樣做,所有發行的 Microsoft® Internet Explorer® 版本都將無法顯示它(但使用其他主流的現代浏覽器則沒有問題)。惟一實用的解決方法是使用 text/html MIME 類型提供語法 XHTML5。從技術上講,這可能違反了一些版本的 Html5 規范,但是除非您可以不支持 Internet Explorer,否則就沒有更多的選擇。說到增加混亂,這在相關的工作組中是一個非常有爭議的話題,並且至少這種語言已緩和了一些草案。 Internet Explorer 9 測試版(也稱為 “平台預覽”)完全支持使用 XML MIME 類型提供的 XHTML,所以一旦用戶可普遍使用此版本時,此問題就不存在了。同時,如果您需要支持 Internet Explorer 6 或更早的版本,則本文中介紹的解決方法就不夠用了。您就只能使用 Html 4.x 了。
對終極 web 黑客的建議:使用 text/html MIME 類型提供語法 XHtml5。
DOCTYPE 的樂趣
從終極 web 黑客的角度來說,一個好消息是,XHtml5 使文檔類型聲明(DTDecl)問題變得更少。XHTML 1.x 和 2 需要臭名昭著的構造,比如 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xHtml11.dtd">。這樣做的最大問題是新型的處理器很可能加載此 DTD URL,而這可能是一種不必要的網絡操作。此外,一個 URL 包括許多其他 URL,並且您通常不需要從 W3C 站點下載多個文件。有時 W3C 上放置的文件甚至會有一些問題,這會導致一些很難調試的問題。
在 XHTML5 中,文件的 XML 性質完全由 MIME 類型決定,並且實際上任何 DTDecl 都會被忽略,所以您可以忽略它。但是 HTML5 提供了最小化的 DTDecl <!DOCTYPE html>。如果您使用此 DTDecl,那麼幾乎所有浏覽器都會切換到 “標准” 模式,即使是完整的 HTML5,這通常更一致且更可預測。注意,Html5 DTDecl 不會引用任何單個文件,所以可避免早期的一些 XHtml 問題。
對終極 web 黑客的建議:在 XHtml5 中使用 HTML 最小化的文檔類型聲明 <!DOCTYPE Html> 。
由於您不使用任何外部 DTD 組件,因此您無法使用常見的 HTML 實體,比如 或 ©。這些都是在那些您未聲明的 XHtml DTD 中定義的。如果您想使用它們,XML 處理器將失敗並出現一個 undefined entity 錯誤。惟一安全的命名字符實體是:<、>、&、" 和 '。使用數值等效代替。例如,使用   而不是 ;使用 © 而不是 ©。
對終極 web 黑客的建議:不要使用任何命名字符實體,以下實體除外:<、>、&、" 和 '
從技術上講,如果您將文檔作為 text/html 提供,根據第一個建議,使用 Html 命名字符實體,在大多數浏覽器上都不會出錯,但是依靠這一意外是非常脆弱的。此外,記住,浏覽器並不是 XML 的惟一使用者。其他 XML 處理器被此類文檔弄得不知如何是好。
命名空間的樂趣
認識 XML 格式的復雜機制的最後一層是命名空間,前兩個是 MIME 類型和 DTDecl。可能您過去經常使用類似下列行的內容開始 XHtml 文檔。
<html XMLns="http://www.w3.org/1999/xHtml" XML:lang="en" >
黑體部分(XMLns="http://www.w3.org/1999/xhtml")是命名空間。在 XHtml5 中,此命名空間仍然是必需的。如果您包含了其他 XML 詞匯,比如可縮放的向量圖形(Scalable Vector Graphics,SVG),則將他們放置在其各自的必需命名空間中。
對終極 web 黑客的建議:在 XHtml5 文檔的頂部始終包含默認的命名空間,並為其他嵌入的 XML 格式使用相應的命名空間。
如果您包含了其他詞匯,則他們的命名空間聲明必須在嵌入部分最外面的開始標記中。如果您在 html 元素中聲明了它們,則會遇到一個 text/Html 文檔一致性錯誤。
處理 XHtml5 內容
XHtml5 支持您使用以下方式指定介質類型:用協議頭,比如 HTTP Content-Type 頭;使用名為 “字節順序標記 (BOM)” 的特殊字符標記,或者是使用 XML 聲明。只要不互相沖突,您可以隨意組合使用這些方法,但避免問題的最好方式是在選擇組合方法時要謹慎。不幸的是,使用 XML 聲明存在潛在問題,因為它會使 Internet Explorer 8 及更早版本都切換到怪異模式,這會導致臭名昭著的顯示異常,也正是因為這種情況才使浏覽器聞名於世。
對終極 web 黑客的建議:對 XHtml5 文檔僅使用 Unicode 編碼。在文檔的開頭部分,省略 XML 聲明,並使用 UTF-8 編碼,或者使用 UTF-16 Unicode 字節順序標記(Byte Order Mark,BOM)。如果可以,可在提供文檔時使用 Content-Type HTTP 頭。
下面是此類 HTTP 頭的一個示例:
Content-Type: "text/Html; charset=UTF-8"
新的語義標記元素
Html5 引入了一些新元素,提供語義更明確的內容結構,比如 section 和 article。這些元素是 Html5 的一部分,可能會發生變化,但是變化不會太大,並且這些新元素提供的改進表達式也降低了風險。一個問題是 Internet Explorer 不是在 DOM 中構造這些元素,所以如果使用 Javascript,您就需要采用另一個解決方法。Remy Sharp 通過在文檔頭包含下列代碼段來維護 JavaScript 修復。
<!--[if IE]>
<script src="http://Html5shim.googlecode.com/svn/trunk/Html5.JS"></script>
<![endif]-->
您還可能需要定義元素的 CSS 規則,以免任何浏覽器以 HTML 4 形式顯示文檔,Html 4 形式以內聯呈現方式顯示未知元素。下列 CSS 應該有效。
header, footer, nav, section, article, figure, aside {
display:block;
}
對終極 web 黑客的建議: 使用新 Html5 元素,但是請包含 Html5 shiv JavaScript 和默認 CSS 規則以支持它們。
將它們組合起來
我已經給出了許多單獨的建議,我將把它們組合起來形成一個完整的示例。清單 1 是滿足這些建議的 XHtml5。通過 HTTP 提供它時,除非您可以不支持 Internet Explorer,否則請使用頭 Content-Type: "text/html; charset=UTF-8";當不支持 Internet Explorer 時,請使用頭 Content-Type: "application/xHtml+XML; charset=UTF-8"。
清單 1. 完整的 XHtml5 示例
<!DOCTYPE Html>
<Html XMLns="/School/UploadFiles_7810/201104/20110401131101497.png"/>
</p>
</section>
</article>
<aside>
<header>Archives</header>
<ul>
<li><a href="/2010/04">April 2010</a></li>
<li><a href="/2010/05">May 2010</a></li>
<li><a href="/2010/06">June 2010</a></li>
</ul>
</aside>
<footer>© 2010 by Uche Ogbuji</footer>
<nav>
<ul>
<li><a href="/">Home</a></li>
<li><a href="/about">About</a></li>
<li><a href="/2010/06">Home</a></li>
</ul>
</nav>
</body>
</Html>
清單 1 使用 Html5 DTDecl,並在頂部聲明默認命名空間。本例中的 style 和 script 元素僅提供實際浏覽器問題的解決方法。只有在使用其他 JavaScript 時才需要 script 元素。該文檔使用了大量新 Html5 元素,我不會詳細介紹這些元素,因為它們不是 XML 特有的。注意,img 元素使用的是 “自閉合” 語法(換句話說,它以 /> 結束),版權符號使用的是數值實體形式 ©。
可參閱 表 1 了解上述示例在不同浏覽器中的行為概述。
表 1. 滿足本文建議的 XHtml5 的浏覽器支持
浏覽器 行為 舊版浏覽器(例如,Internet Explorer 6.x 或更早版本、 Netscape、Firefox 1.x) 呈現將是不可預測的。例如,“自閉合” 元素的結束標記可能是錯誤的。如果您使用 Html 命名實體則不會出現任何錯誤。 Internet Explorer 7 或 8 由於使用的是 text/html MIME 類型,因此呈現將是常規的 “標記雜燴”,但是任何 DTDecl 都將觸發 “標准模式”,比如 Internet Explorer 提供它。Html 命名實體不會出現任何錯誤報告。 現代的、支持 Html5 的浏覽器,比如 Firefox 3.x、Safari 4 或最新的 Opera 或 Google Chrome 由於使用的是 MIME 類型,因此呈現將是 HTML5(而不是 XHtml5),但是會是在 “標准模式” 下。Html 命名實體不會出現任何錯誤報告。 任何標准的 XML 1.x 處理器 將不會考慮 MIME 類型。解析器將會在 XHTML 命名空間看到所有元素。如果使用任何假的 Html 命名實體,都會收到錯誤信息。結束語
最近的一個重要情況是 W3C HTML 工作組發布了第一份公共工作草案 "Polyglot Markup: HTML-Compatible XHTML Documents",目的是提供有關 XHtml5 的更全面、准確和最新的消息。
此外,對我來說,做出本文中的一些建議來說很痛苦。這些解決方法來自長期的痛苦體驗,並且在將 XML 混合進現實 HTML 世界時,這是避免難以重現的 bug 和奇怪的不兼容性的惟一方法。這當然不是說我已經停止了提倡仔細的 XML 設計和最佳實踐。最好將連接浏覽器的最外面的組件保存為 XHTML5。所有類型的 XHTML 都能更好地呈現語言而不是攜帶信息的語言。您應該以其他 XML 格式傳輸大多數系統的主要信息。然後在最後將其轉換為 XHTML5。您可能會好奇在最後時刻創建 XHtml5 的意義,但是請記住 Postel 法則,它建議嚴格執行生成的內容。通過為浏覽器生成 XHtml5,其他人會很容易從您的網站和應用程序中提取信息。在這個混搭、web API 和數據項目時代,這是一個重要特性。