2016-10-27 83 views
1

我有一個問題,我需要在定義中將一個包含ENTITY的實體包含在一個現有的XML文檔中。在Java中有一些與Ruby的Nokogiri :: XML :: EntityDecl等價的東西嗎?

例如,在DAISY的規範MATHML工作在http://www.daisy.org/projects/mathml/mathml-in-daisy-spec.html,說我通過外部源給出這個XML:

<?xml version="1.0" encoding="UTF-8"?> 
<!DOCTYPE dtbook PUBLIC "-//NISO//DTD dtbook 2005-2//EN" 
"http://www.daisy.org/z3986/2005/dtbook-2005-2.dtd"> 
<dtbook xmlns="http://www.daisy.org/z3986/2005/dtbook/" xmlns:m="http://www.w3.org/1998/Math/MathML" 
    version="2005-3" xml:lang="eng"> 
    <m:math xmlns:dtbook="http://www.daisy.org/z3986/2005/dtbook/" 
    id="math0001" dtbook:smilref="nativemathml.smil#math0001" 
    altimg="nativemathml0001.png" 
    alttext="sigma-summation UnderScript i equals zero OverScript infinity EndScripts x Subscript i"> 
     <m:mrow> 
     <m:mstyle displaystyle='true'> 
      <m:munderover> 
      <m:mo>&#x2211;</m:mo> 
      <m:mrow> 
       <m:mi>i</m:mi><m:mo>=</m:mo><m:mn>0</m:mn> 
      </m:mrow> 
      <m:mi>&#x221E;</m:mi> 
      </m:munderover> 
      <m:mrow> 
      <m:msub> 
       <m:mi>x</m:mi> 
       <m:mi>i</m:mi> 
      </m:msub> 
      </m:mrow> 
     </m:mstyle> 
     </m:mrow> 
</m:math> 
</dtbook> 

我想從規範添加實體定義,以使這本書支持MathML的,這樣的結果是這樣的:

<?xml version="1.0" encoding="UTF-8"?> 
<!DOCTYPE dtbook PUBLIC "-//NISO//DTD dtbook 2005-2//EN" 
"http://www.daisy.org/z3986/2005/dtbook-2005-2.dtd" 
[ 
    <!ENTITY % MATHML.prefixed "INCLUDE" > 
    <!ENTITY % MATHML.prefix "m"> 
    <!ENTITY % MATHML.Common.attrib 
      "xlink:href CDATA  #IMPLIED 
      xlink:type  CDATA  #IMPLIED 
      class   CDATA  #IMPLIED 
      style   CDATA  #IMPLIED 
      id    ID   #IMPLIED 
      xref   IDREF  #IMPLIED 
      other   CDATA  #IMPLIED 
      xmlns:dtbook CDATA  #FIXED 'http://www.daisy.org/z3986/2005/dtbook/' 
      dtbook:smilref CDATA  #IMPLIED" 
    > 
    <!ENTITY % mathML2 PUBLIC "-//W3C//DTD MathML 2.0//EN" 
      "http://www.w3.org/Math/DTD/mathml2/mathml2.dtd" 
    > 
    %mathML2; 
    <!ENTITY % externalFlow "| m:math"> 
    <!ENTITY % externalNamespaces "xmlns:m CDATA #FIXED 
    'http://www.w3.org/1998/Math/MathML'"> 
] 
> 
<dtbook xmlns="http://www.daisy.org/z3986/2005/dtbook/" xmlns:m="http://www.w3.org/1998/Math/MathML" 
    version="2005-3" xml:lang="eng"> 
    <m:math xmlns:dtbook="http://www.daisy.org/z3986/2005/dtbook/" 
    id="math0001" dtbook:smilref="nativemathml.smil#math0001" 
    altimg="nativemathml0001.png" 
    alttext="sigma-summation UnderScript i equals zero OverScript infinity EndScripts x Subscript i"> 
     <m:mrow> 
     <m:mstyle displaystyle='true'> 
      <m:munderover> 
      <m:mo>&#x2211;</m:mo> 
      <m:mrow> 
       <m:mi>i</m:mi><m:mo>=</m:mo><m:mn>0</m:mn> 
      </m:mrow> 
      <m:mi>&#x221E;</m:mi> 
      </m:munderover> 
      <m:mrow> 
      <m:msub> 
       <m:mi>x</m:mi> 
       <m:mi>i</m:mi> 
      </m:msub> 
      </m:mrow> 
     </m:mstyle> 
     </m:mrow> 
</m:math> 
</dtbook> 

在Ruby中,存在引入nokogiri的方法可用於添加這些實體定義,看起來像這樣: 引入nokogiri :: XML :: EntityDecl。 ñ ew(「MATHML.prefixed」,doc,MATHML_ENTITY_DECL_TYPE,nil,nil,「INCLUDE」)

在Java中是否有與此相當的內容?我們使用JDOM來操作我們的XML文檔,但JDOM DocType類似乎不支持這些實體定義。

回答

1

使用JDOM,您應該能夠解析原始文檔,並從文檔中提取DTDContent節點。

您的代碼看起來是這樣的:

Document doc = saxBuilder.build(myxmlfile); 
DocType dtd = doc.getDocType(); 

dtd內容應該是參考dtbook參考。

您現在可以採用mathml聲明的字符串表示形式,並將它們作爲DocType的internalsubset(也許您想從文件或系統資源中讀取它)。

String internal = " <!ENTITY % MATHML.prefixed \"INCLUDE\" >\n" 
    + " <!ENTITY % MATHML.prefix \"m\">\n" 
    + ...... 

dtd.setInternalSubset(internal); 

參見:http://www.jdom.org/docs/apidocs/org/jdom2/DocType.html#setInternalSubset(java.lang.String)

這將修改的聲明,並且,如果你輸出的XML,你應該有你期望的內容:

XMLOutputter xout = new XMLOutputter(); 
xout.output(doc, System.out); 
+0

這很有趣。我用DAISY/MathML DTD加載了一個示例文件,在調試器中,我可以看到DocType的internalSubset是空的。當我使用XMLOutputter將文檔打印出來時,類似於您在這裏的內容,將內部的ENTITY定義剝離出來。我們使用的是JDOM 1,所以我想知道這是否是該版本的問題,或者我在使用中缺少某些內容。我會嘗試設置internalSubset作爲下一個實驗。 –

+0

你應該使用JDOM 2.x ;-)這是十年前的十年老 – rolfl

+0

相信我,當我們的預算和時間允許時,我們會。但這不是真的取決於我。這個代碼庫大約有10年的歷史,並且到處都有很多對JDOM 1.1.3的小引用。 –

相關問題