Scala: конвертировать org.w3c.dom.Document в scala.xml.NodeSeq - PullRequest
12 голосов
/ 13 октября 2010

Название довольно очевидно.Как я могу преобразовать экземпляр org.w3c.dom.Document в Scala NodeSeq, чтобы пользоваться его поддержкой?

Cheers
Parsa

Ответы [ 4 ]

12 голосов
/ 13 октября 2010
  def asXml(dom: org.w3c.dom.Node): Node = {
    val dom2sax = new DOM2SAX(dom)
    val adapter = new NoBindingFactoryAdapter
    dom2sax.setContentHandler(adapter)
    dom2sax.parse()
    return adapter.rootElem
  }
5 голосов
/ 18 мая 2011

Ответ IttayD подходит для всех XML-файлов w3c, кроме xmls, совместимых с dom4j w3c.Следующие работы для всех типов W3C:

def asXml(dom: _root_.org.w3c.dom.Node): Node = {
    val source = new DOMSource(dom)
    val adapter = new NoBindingFactoryAdapter
    val saxResult = new SAXResult(adapter)
    val transformerFactory = javax.xml.transform.TransformerFactory.newInstance()
    val transformer = transformerFactory.newTransformer()
    transformer.transform(source, saxResult)
    adapter.rootElem
  }
3 голосов
/ 13 октября 2010

Я написал этот код некоторое время назад, чтобы идти в другом направлении, от узла Scala до узла Dom4J. Он показывает основную идею повторения по дереву и должен быть достаточно простым для адаптации:

implicit def scalaToDom4j(n : Node) : DElem = {

  def inner(n : Node) : Option[DNode] = {
    n match {
      case e : Elem =>
        val elem = DocumentHelper.createElement(e.label)
        for(c <- e.child) yield inner(c) collect {
          case Some(child) => elem.add(child)
        }
        Some(elem)
        //as Scala's xml is type-aware, text might not actually be a Text node,
        //but an Atom of some other type
      case t : Atom[_] =>
        Some(DocumentHelper.createText(t.data.toString))
      case x => None
    }
  }

  //Attempt the conversion. Throw an exception if something has gone badly wrong
  //inner returns an Option[DNode], but the expected top-level type is a DElem
  // (which is a subclass of DNode)
  //so we also validate this.
  inner(trim(n)) map (_.asInstanceOf[DElem]) getOrElse (error("xml failed"))
}
0 голосов
/ 11 декабря 2010

У меня есть рекурсивный код сопоставления с образцом, аналогичный приведенной выше функции scalaToDom4j (n), только в направлении от саксонского XdmNode к Scala-узлу вверх: https://github.com/LeifW/MusicPath/blob/master/src/main/scala/org/musicpath/saxon2scala/Saxon2Scala.scala

В настоящее время он просто делает текст, элемент иузлы атрибутов без пространства имен, но их должно быть легко обобщить / завершить.

...